comparison src/memory/params.py @ 993:301b342c697a

core: use of the new core.log module: /!\ this is a massive refactoring and was largely automated, it probably did bring some bugs /!\
author Goffi <goffi@goffi.org>
date Sat, 19 Apr 2014 19:19:19 +0200
parents 75f3b3b430ff
children fee00f2e11c2
comparison
equal deleted inserted replaced
992:f51a1895275c 993:301b342c697a
20 from sat.core.i18n import _ 20 from sat.core.i18n import _
21 21
22 from sat.core import exceptions 22 from sat.core import exceptions
23 from sat.core.constants import Const as C 23 from sat.core.constants import Const as C
24 from xml.dom import minidom, NotFoundErr 24 from xml.dom import minidom, NotFoundErr
25 from logging import debug, info, warning, error 25 from sat.core.log import getLogger
26 log = getLogger(__name__)
26 from twisted.internet import defer 27 from twisted.internet import defer
27 from twisted.python.failure import Failure 28 from twisted.python.failure import Failure
28 from sat.tools.xml_tools import paramsXML2XMLUI 29 from sat.tools.xml_tools import paramsXML2XMLUI
29 30
30 31
113 """Remove cache data of a profile 114 """Remove cache data of a profile
114 @param profile: %(doc_profile)s""" 115 @param profile: %(doc_profile)s"""
115 try: 116 try:
116 del self.params[profile] 117 del self.params[profile]
117 except KeyError: 118 except KeyError:
118 error(_("Trying to purge cache of a profile not in memory: [%s]") % profile) 119 log.error(_("Trying to purge cache of a profile not in memory: [%s]") % profile)
119 120
120 def save_xml(self, filename): 121 def save_xml(self, filename):
121 """Save parameters template to xml file""" 122 """Save parameters template to xml file"""
122 with open(filename, 'wb') as xml_file: 123 with open(filename, 'wb') as xml_file:
123 xml_file.write(self.dom.toxml('utf-8')) 124 xml_file.write(self.dom.toxml('utf-8'))
124 125
125 def __init__(self, host, storage): 126 def __init__(self, host, storage):
126 debug("Parameters init") 127 log.debug("Parameters init")
127 self.host = host 128 self.host = host
128 self.storage = storage 129 self.storage = storage
129 self.default_profile = None 130 self.default_profile = None
130 self.params = {} 131 self.params = {}
131 self.params_gen = {} 132 self.params_gen = {}
136 @param profile: name of the profile 137 @param profile: name of the profile
137 @param callback: called when the profile actually exists in database and memory 138 @param callback: called when the profile actually exists in database and memory
138 @return: a Deferred instance 139 @return: a Deferred instance
139 """ 140 """
140 if self.storage.hasProfile(profile): 141 if self.storage.hasProfile(profile):
141 info(_('The profile name already exists')) 142 log.info(_('The profile name already exists'))
142 return defer.fail(Failure(exceptions.ConflictError)) 143 return defer.fail(Failure(exceptions.ConflictError))
143 if not self.host.trigger.point("ProfileCreation", profile): 144 if not self.host.trigger.point("ProfileCreation", profile):
144 return defer.fail(Failure(exceptions.CancelError)) 145 return defer.fail(Failure(exceptions.CancelError))
145 return self.storage.createProfile(profile) 146 return self.storage.createProfile(profile)
146 147
151 @param force: force the deletion even if the profile is connected. 152 @param force: force the deletion even if the profile is connected.
152 To be used for direct calls only (not through the bridge). 153 To be used for direct calls only (not through the bridge).
153 @return: a Deferred instance 154 @return: a Deferred instance
154 """ 155 """
155 if not self.storage.hasProfile(profile): 156 if not self.storage.hasProfile(profile):
156 info(_('Trying to delete an unknown profile')) 157 log.info(_('Trying to delete an unknown profile'))
157 return defer.fail(Failure(exceptions.ProfileUnknownError)) 158 return defer.fail(Failure(exceptions.ProfileUnknownError))
158 if self.host.isConnected(profile): 159 if self.host.isConnected(profile):
159 if force: 160 if force:
160 self.host.disconnect(profile) 161 self.host.disconnect(profile)
161 else: 162 else:
162 info(_("Trying to delete a connected profile")) 163 log.info(_("Trying to delete a connected profile"))
163 return defer.fail(Failure(exceptions.ConnectedProfileError)) 164 return defer.fail(Failure(exceptions.ConnectedProfileError))
164 return self.storage.deleteProfile(profile) 165 return self.storage.deleteProfile(profile)
165 166
166 def getProfileName(self, profile_key, return_profile_keys = False): 167 def getProfileName(self, profile_key, return_profile_keys = False):
167 """return profile according to profile_key 168 """return profile according to profile_key
172 @param return_profile_keys: if True, return unmanaged profile keys (like "@ALL@"). This keys must be managed by the caller 173 @param return_profile_keys: if True, return unmanaged profile keys (like "@ALL@"). This keys must be managed by the caller
173 @return: requested profile name or emptry string if it doesn't exist""" 174 @return: requested profile name or emptry string if it doesn't exist"""
174 if profile_key == '@DEFAULT@': 175 if profile_key == '@DEFAULT@':
175 default = self.host.memory.memory_data.get('Profile_default') 176 default = self.host.memory.memory_data.get('Profile_default')
176 if not default: 177 if not default:
177 info(_('No default profile, returning first one')) # TODO: manage real default profile 178 log.info(_('No default profile, returning first one')) # TODO: manage real default profile
178 try: 179 try:
179 default = self.host.memory.memory_data['Profile_default'] = self.storage.getProfilesList()[0] 180 default = self.host.memory.memory_data['Profile_default'] = self.storage.getProfilesList()[0]
180 except IndexError: 181 except IndexError:
181 info(_('No profile exist yet')) 182 log.info(_('No profile exist yet'))
182 return "" 183 return ""
183 return default # FIXME: temporary, must use real default value, and fallback to first one if it doesn't exists 184 return default # FIXME: temporary, must use real default value, and fallback to first one if it doesn't exists
184 elif profile_key == C.PROF_KEY_NONE: 185 elif profile_key == C.PROF_KEY_NONE:
185 raise exceptions.ProfileNotSetError 186 raise exceptions.ProfileNotSetError
186 elif return_profile_keys and profile_key in ["@ALL@"]: 187 elif return_profile_keys and profile_key in ["@ALL@"]:
187 return profile_key # this value must be managed by the caller 188 return profile_key # this value must be managed by the caller
188 if not self.storage.hasProfile(profile_key): 189 if not self.storage.hasProfile(profile_key):
189 info(_('Trying to access an unknown profile')) 190 log.info(_('Trying to access an unknown profile'))
190 return "" # FIXME: raise exceptions.ProfileUnknownError here (must be well checked, this method is used in lot of places) 191 return "" # FIXME: raise exceptions.ProfileUnknownError here (must be well checked, this method is used in lot of places)
191 return profile_key 192 return profile_key
192 193
193 def __get_unique_node(self, parent, tag, name): 194 def __get_unique_node(self, parent, tag, name):
194 """return node with given tag 195 """return node with given tag
265 @param xml: XML definition of the parameters to be added 266 @param xml: XML definition of the parameters to be added
266 @param security_limit: -1 means no security, 0 is the maximum security then the higher the less secure 267 @param security_limit: -1 means no security, 0 is the maximum security then the higher the less secure
267 @param app: name of the frontend registering the parameters 268 @param app: name of the frontend registering the parameters
268 """ 269 """
269 if not app: 270 if not app:
270 warning(_("Trying to register frontends parameters with no specified app: aborted")) 271 log.warning(_("Trying to register frontends parameters with no specified app: aborted"))
271 return 272 return
272 if not hasattr(self, "frontends_cache"): 273 if not hasattr(self, "frontends_cache"):
273 self.frontends_cache = [] 274 self.frontends_cache = []
274 if app in self.frontends_cache: 275 if app in self.frontends_cache:
275 debug(_("Trying to register twice frontends parameters for %(app)s: aborted" % {"app": app})) 276 log.debug(_("Trying to register twice frontends parameters for %(app)s: aborted" % {"app": app}))
276 return 277 return
277 self.frontends_cache.append(app) 278 self.frontends_cache.append(app)
278 self.updateParams(xml, security_limit, app) 279 self.updateParams(xml, security_limit, app)
279 debug("Frontends parameters registered for %(app)s" % {'app': app}) 280 log.debug("Frontends parameters registered for %(app)s" % {'app': app})
280 281
281 def __default_ok(self, value, name, category): 282 def __default_ok(self, value, name, category):
282 #FIXME: will not work with individual parameters 283 #FIXME: will not work with individual parameters
283 self.setParam(name, value, category) 284 self.setParam(name, value, category)
284 285
285 def __default_ko(self, failure, name, category): 286 def __default_ko(self, failure, name, category):
286 error(_("Can't determine default value for [%(category)s/%(name)s]: %(reason)s") % {'category': category, 'name': name, 'reason': str(failure.value)}) 287 log.error(_("Can't determine default value for [%(category)s/%(name)s]: %(reason)s") % {'category': category, 'name': name, 'reason': str(failure.value)})
287 288
288 def setDefault(self, name, category, callback, errback=None): 289 def setDefault(self, name, category, callback, errback=None):
289 """Set default value of parameter 290 """Set default value of parameter
290 'default_cb' attibute of parameter must be set to 'yes' 291 'default_cb' attibute of parameter must be set to 'yes'
291 @param name: name of the parameter 292 @param name: name of the parameter
293 @param callback: must return a string with the value (use deferred if needed) 294 @param callback: must return a string with the value (use deferred if needed)
294 @param errback: must manage the error with args failure, name, category 295 @param errback: must manage the error with args failure, name, category
295 """ 296 """
296 #TODO: send signal param update if value changed 297 #TODO: send signal param update if value changed
297 #TODO: manage individual paramaters 298 #TODO: manage individual paramaters
298 debug ("setDefault called for %(category)s/%(name)s" % {"category": category, "name": name}) 299 log.debug ("setDefault called for %(category)s/%(name)s" % {"category": category, "name": name})
299 node = self._getParamNode(name, category, '@ALL@') 300 node = self._getParamNode(name, category, '@ALL@')
300 if not node: 301 if not node:
301 error(_("Requested param [%(name)s] in category [%(category)s] doesn't exist !") % {'name': name, 'category': category}) 302 log.error(_("Requested param [%(name)s] in category [%(category)s] doesn't exist !") % {'name': name, 'category': category})
302 return 303 return
303 if node[1].getAttribute('default_cb') == 'yes': 304 if node[1].getAttribute('default_cb') == 'yes':
304 # del node[1].attributes['default_cb'] # default_cb is not used anymore as a flag to know if we have to set the default value, 305 # del node[1].attributes['default_cb'] # default_cb is not used anymore as a flag to know if we have to set the default value,
305 # and we can still use it later e.g. to call a generic setDefault method 306 # and we can still use it later e.g. to call a generic setDefault method
306 value = self._getParam(category, name, C.GENERAL) 307 value = self._getParam(category, name, C.GENERAL)
307 if value is None: # no value set by the user: we have the default value 308 if value is None: # no value set by the user: we have the default value
308 debug ("Default value to set, using callback") 309 log.debug ("Default value to set, using callback")
309 d = defer.maybeDeferred(callback) 310 d = defer.maybeDeferred(callback)
310 d.addCallback(self.__default_ok, name, category) 311 d.addCallback(self.__default_ok, name, category)
311 d.addErrback(errback or self.__default_ko, name, category) 312 d.addErrback(errback or self.__default_ko, name, category)
312 313
313 def _getAttr(self, node, attr, value): 314 def _getAttr(self, node, attr, value):
341 342
342 @return: attribute""" 343 @return: attribute"""
343 #FIXME: looks really dirty and buggy, need to be reviewed/refactored 344 #FIXME: looks really dirty and buggy, need to be reviewed/refactored
344 node = self._getParamNode(name, category) 345 node = self._getParamNode(name, category)
345 if not node: 346 if not node:
346 error(_("Requested param [%(name)s] in category [%(category)s] doesn't exist !") % {'name': name, 'category': category}) 347 log.error(_("Requested param [%(name)s] in category [%(category)s] doesn't exist !") % {'name': name, 'category': category})
347 raise exceptions.NotFound 348 raise exceptions.NotFound
348 349
349 if node[0] == C.GENERAL: 350 if node[0] == C.GENERAL:
350 value = self._getParam(category, name, C.GENERAL) 351 value = self._getParam(category, name, C.GENERAL)
351 return self._getAttr(node[1], attr, value) 352 return self._getAttr(node[1], attr, value)
352 353
353 assert node[0] == C.INDIVIDUAL 354 assert node[0] == C.INDIVIDUAL
354 355
355 profile = self.getProfileName(profile_key) 356 profile = self.getProfileName(profile_key)
356 if not profile: 357 if not profile:
357 error(_('Requesting a param for an non-existant profile')) 358 log.error(_('Requesting a param for an non-existant profile'))
358 raise exceptions.ProfileUnknownError 359 raise exceptions.ProfileUnknownError
359 360
360 if profile not in self.params: 361 if profile not in self.params:
361 error(_('Requesting synchronous param for not connected profile')) 362 log.error(_('Requesting synchronous param for not connected profile'))
362 raise exceptions.NotConnectedProfileError(profile) 363 raise exceptions.NotConnectedProfileError(profile)
363 364
364 if attr == "value": 365 if attr == "value":
365 value = self._getParam(category, name, profile=profile) 366 value = self._getParam(category, name, profile=profile)
366 return self._getAttr(node[1], attr, value) 367 return self._getAttr(node[1], attr, value)
376 @param category: category of the parameter 377 @param category: category of the parameter
377 @param attr: name of the attribute (default: "value") 378 @param attr: name of the attribute (default: "value")
378 @param profile: owner of the param (@ALL@ for everyone)""" 379 @param profile: owner of the param (@ALL@ for everyone)"""
379 node = self._getParamNode(name, category) 380 node = self._getParamNode(name, category)
380 if not node: 381 if not node:
381 error(_("Requested param [%(name)s] in category [%(category)s] doesn't exist !") % {'name': name, 'category': category}) 382 log.error(_("Requested param [%(name)s] in category [%(category)s] doesn't exist !") % {'name': name, 'category': category})
382 return None 383 return None
383 384
384 if not self.checkSecurityLimit(node[1], security_limit): 385 if not self.checkSecurityLimit(node[1], security_limit):
385 warning(_("Trying to get parameter '%(param)s' in category '%(cat)s' without authorization!!!" 386 log.warning(_("Trying to get parameter '%(param)s' in category '%(cat)s' without authorization!!!"
386 % {'param': name, 'cat': category})) 387 % {'param': name, 'cat': category}))
387 return None 388 return None
388 389
389 if node[0] == C.GENERAL: 390 if node[0] == C.GENERAL:
390 value = self._getParam(category, name, C.GENERAL) 391 value = self._getParam(category, name, C.GENERAL)
392 393
393 assert node[0] == C.INDIVIDUAL 394 assert node[0] == C.INDIVIDUAL
394 395
395 profile = self.getProfileName(profile_key) 396 profile = self.getProfileName(profile_key)
396 if not profile: 397 if not profile:
397 error(_('Requesting a param for a non-existant profile')) 398 log.error(_('Requesting a param for a non-existant profile'))
398 return defer.fail() 399 return defer.fail()
399 400
400 if attr != "value": 401 if attr != "value":
401 return defer.succeed(node[1].getAttribute(attr)) 402 return defer.succeed(node[1].getAttribute(attr))
402 try: 403 try:
536 @param profile_key: Profile key which can be either a magic (eg: @DEFAULT@) or the name of an existing profile. 537 @param profile_key: Profile key which can be either a magic (eg: @DEFAULT@) or the name of an existing profile.
537 @return: a SàT XMLUI for parameters 538 @return: a SàT XMLUI for parameters
538 """ 539 """
539 profile = self.getProfileName(profile_key) 540 profile = self.getProfileName(profile_key)
540 if not profile: 541 if not profile:
541 error(_("Asking params for inexistant profile")) 542 log.error(_("Asking params for inexistant profile"))
542 return "" 543 return ""
543 d = self.getParams(security_limit, app, profile) 544 d = self.getParams(security_limit, app, profile)
544 return d.addCallback(lambda param_xml: paramsXML2XMLUI(param_xml)) 545 return d.addCallback(lambda param_xml: paramsXML2XMLUI(param_xml))
545 546
546 def getParams(self, security_limit, app, profile_key): 547 def getParams(self, security_limit, app, profile_key):
552 @param profile_key: Profile key which can be either a magic (eg: @DEFAULT@) or the name of an existing profile. 553 @param profile_key: Profile key which can be either a magic (eg: @DEFAULT@) or the name of an existing profile.
553 @return: XML of parameters 554 @return: XML of parameters
554 """ 555 """
555 profile = self.getProfileName(profile_key) 556 profile = self.getProfileName(profile_key)
556 if not profile: 557 if not profile:
557 error(_("Asking params for inexistant profile")) 558 log.error(_("Asking params for inexistant profile"))
558 return defer.succeed("") 559 return defer.succeed("")
559 560
560 def returnXML(prof_xml): 561 def returnXML(prof_xml):
561 return_xml = prof_xml.toxml() 562 return_xml = prof_xml.toxml()
562 prof_xml.unlink() 563 prof_xml.unlink()
575 @return: node's xml for selected category 576 @return: node's xml for selected category
576 """ 577 """
577 #TODO: manage category of general type (without existant profile) 578 #TODO: manage category of general type (without existant profile)
578 profile = self.getProfileName(profile_key) 579 profile = self.getProfileName(profile_key)
579 if not profile: 580 if not profile:
580 error(_("Asking params for inexistant profile")) 581 log.error(_("Asking params for inexistant profile"))
581 return "" 582 return ""
582 583
583 def returnCategoryXml(prof_xml): 584 def returnCategoryXml(prof_xml):
584 for node in prof_xml.getElementsByTagName("category"): 585 for node in prof_xml.getElementsByTagName("category"):
585 if node.nodeName == "category" and node.getAttribute("name") == category: 586 if node.nodeName == "category" and node.getAttribute("name") == category:
627 """Set a parameter, return None if the parameter is not in param xml""" 628 """Set a parameter, return None if the parameter is not in param xml"""
628 #TODO: use different behaviour depending of the data type (e.g. password encrypted) 629 #TODO: use different behaviour depending of the data type (e.g. password encrypted)
629 if profile_key != C.PROF_KEY_NONE: 630 if profile_key != C.PROF_KEY_NONE:
630 profile = self.getProfileName(profile_key) 631 profile = self.getProfileName(profile_key)
631 if not profile: 632 if not profile:
632 error(_('Trying to set parameter for an unknown profile')) 633 log.error(_('Trying to set parameter for an unknown profile'))
633 return # TODO: throw an error 634 return # TODO: throw an error
634 635
635 node = self._getParamNode(name, category, '@ALL@') 636 node = self._getParamNode(name, category, '@ALL@')
636 if not node: 637 if not node:
637 error(_('Requesting an unknown parameter (%(category)s/%(name)s)') 638 log.error(_('Requesting an unknown parameter (%(category)s/%(name)s)')
638 % {'category': category, 'name': name}) 639 % {'category': category, 'name': name})
639 return 640 return
640 641
641 if not self.checkSecurityLimit(node[1], security_limit): 642 if not self.checkSecurityLimit(node[1], security_limit):
642 warning(_("Trying to set parameter '%(param)s' in category '%(cat)s' without authorization!!!" 643 log.warning(_("Trying to set parameter '%(param)s' in category '%(cat)s' without authorization!!!"
643 % {'param': name, 'cat': category})) 644 % {'param': name, 'cat': category}))
644 return 645 return
645 646
646 if node[0] == C.GENERAL: 647 if node[0] == C.GENERAL:
647 self.params_gen[(category, name)] = value 648 self.params_gen[(category, name)] = value