# HG changeset patch # User souliane # Date 1378405724 -7200 # Node ID ca2cae6b2c6d4726ce1b304f3518e184fc947077 # Parent 6a29a4d574bdde005840845043975520a36a950a core: security attribute added to the parameters - getParams, getParamsUI and getParamsForCategory have a security_limit parameter to filter - parameters with security = 0 can be retrieved/modified from Libervia diff -r 6a29a4d574bd -r ca2cae6b2c6d frontends/src/bridge/DBus.py --- a/frontends/src/bridge/DBus.py Sun Sep 08 18:05:19 2013 +0200 +++ b/frontends/src/bridge/DBus.py Thu Sep 05 20:28:44 2013 +0200 @@ -154,17 +154,17 @@ def getParamA(self, name, category, attribute="value", profile_key="@DEFAULT@"): return unicode(self.db_core_iface.getParamA(name, category, attribute, profile_key)) - def getParams(self, profile_key="@DEFAULT@", callback=None, errback=None): - return unicode(self.db_core_iface.getParams(profile_key, reply_handler=callback, error_handler=lambda err:errback(err._dbus_error_name[len(const_ERROR_PREFIX)+1:]))) + def getParams(self, security_limit=-1, profile_key="@DEFAULT@", callback=None, errback=None): + return unicode(self.db_core_iface.getParams(security_limit, profile_key, reply_handler=callback, error_handler=lambda err:errback(err._dbus_error_name[len(const_ERROR_PREFIX)+1:]))) def getParamsCategories(self, ): return self.db_core_iface.getParamsCategories() - def getParamsForCategory(self, category, profile_key="@DEFAULT@", callback=None, errback=None): - return unicode(self.db_core_iface.getParamsForCategory(category, profile_key, reply_handler=callback, error_handler=lambda err:errback(err._dbus_error_name[len(const_ERROR_PREFIX)+1:]))) + def getParamsForCategory(self, category, security_limit=-1, profile_key="@DEFAULT@", callback=None, errback=None): + return unicode(self.db_core_iface.getParamsForCategory(category, security_limit, profile_key, reply_handler=callback, error_handler=lambda err:errback(err._dbus_error_name[len(const_ERROR_PREFIX)+1:]))) - def getParamsUI(self, profile_key="@DEFAULT@", callback=None, errback=None): - return unicode(self.db_core_iface.getParamsUI(profile_key, reply_handler=callback, error_handler=lambda err:errback(err._dbus_error_name[len(const_ERROR_PREFIX)+1:]))) + def getParamsUI(self, security_limit=-1, profile_key="@DEFAULT@", callback=None, errback=None): + return unicode(self.db_core_iface.getParamsUI(security_limit, profile_key, reply_handler=callback, error_handler=lambda err:errback(err._dbus_error_name[len(const_ERROR_PREFIX)+1:]))) def getPresenceStatus(self, profile_key="@DEFAULT@"): return self.db_core_iface.getPresenceStatus(profile_key) diff -r 6a29a4d574bd -r ca2cae6b2c6d frontends/src/primitivus/primitivus --- a/frontends/src/primitivus/primitivus Sun Sep 08 18:05:19 2013 +0200 +++ b/frontends/src/primitivus/primitivus Thu Sep 05 20:28:44 2013 +0200 @@ -507,7 +507,8 @@ self.addWindow(XMLUI(self,xml_data=params)) def failure(error): self.showPopUp(sat_widgets.Alert(_("Error"), _("Can't get parameters"), ok_cb=self.removePopUp)) - self.bridge.getParamsUI(self.profile, callback=success, errback=failure) + security_limit = -1 + self.bridge.getParamsUI(security_limit, self.profile, callback=success, errback=failure) def onExitRequest(self, menu): diff -r 6a29a4d574bd -r ca2cae6b2c6d frontends/src/wix/main_window.py --- a/frontends/src/wix/main_window.py Sun Sep 08 18:05:19 2013 +0200 +++ b/frontends/src/wix/main_window.py Thu Sep 05 20:28:44 2013 +0200 @@ -363,7 +363,8 @@ def onParam(self, e): debug(_("Param request")) - #xmlui = self.bridge.getParamsUI(self.profile) + #security_limit = -1 + #xmlui = self.bridge.getParamsUI(security_limit, profile_key=self.profile) #XMLUI(self, xml_data = xmlui) param=Param(self) diff -r 6a29a4d574bd -r ca2cae6b2c6d frontends/src/wix/param.py --- a/frontends/src/wix/param.py Sun Sep 08 18:05:19 2013 +0200 +++ b/frontends/src/wix/param.py Thu Sep 05 20:28:44 2013 +0200 @@ -102,7 +102,11 @@ self.notebook.AddPage(panel, category) cat_dom.unlink() - self.host.bridge.getParamsForCategory(category, profile_key = self.host.profile, callback = gotParams, errback = errorGettingParams) + self.host.bridge.getParamsForCategory(category, + security_limit=-1, + profile_key=self.host.profile, + callback=gotParams, + errback=errorGettingParams) def onTextChanged(self, event): """Called when a string paramater is modified""" diff -r 6a29a4d574bd -r ca2cae6b2c6d src/bridge/DBus.py --- a/src/bridge/DBus.py Sun Sep 08 18:05:19 2013 +0200 +++ b/src/bridge/DBus.py Thu Sep 05 20:28:44 2013 +0200 @@ -301,10 +301,10 @@ return self._callback("getParamA", unicode(name), unicode(category), unicode(attribute), unicode(profile_key)) @dbus.service.method(const_INT_PREFIX+const_CORE_SUFFIX, - in_signature='s', out_signature='s', + in_signature='is', out_signature='s', async_callbacks=('callback', 'errback')) - def getParams(self, profile_key="@DEFAULT@", callback=None, errback=None): - return self._callback("getParams", unicode(profile_key), callback=callback, errback=errback) + def getParams(self, security_limit=-1, profile_key="@DEFAULT@", callback=None, errback=None): + return self._callback("getParams", security_limit, unicode(profile_key), callback=callback, errback=errback) @dbus.service.method(const_INT_PREFIX+const_CORE_SUFFIX, in_signature='', out_signature='as', @@ -313,16 +313,16 @@ return self._callback("getParamsCategories", ) @dbus.service.method(const_INT_PREFIX+const_CORE_SUFFIX, - in_signature='ss', out_signature='s', + in_signature='sis', out_signature='s', async_callbacks=('callback', 'errback')) - def getParamsForCategory(self, category, profile_key="@DEFAULT@", callback=None, errback=None): - return self._callback("getParamsForCategory", unicode(category), unicode(profile_key), callback=callback, errback=errback) + def getParamsForCategory(self, category, security_limit=-1, profile_key="@DEFAULT@", callback=None, errback=None): + return self._callback("getParamsForCategory", unicode(category), security_limit, unicode(profile_key), callback=callback, errback=errback) @dbus.service.method(const_INT_PREFIX+const_CORE_SUFFIX, - in_signature='s', out_signature='s', + in_signature='is', out_signature='s', async_callbacks=('callback', 'errback')) - def getParamsUI(self, profile_key="@DEFAULT@", callback=None, errback=None): - return self._callback("getParamsUI", unicode(profile_key), callback=callback, errback=errback) + def getParamsUI(self, security_limit=-1, profile_key="@DEFAULT@", callback=None, errback=None): + return self._callback("getParamsUI", security_limit, unicode(profile_key), callback=callback, errback=errback) @dbus.service.method(const_INT_PREFIX+const_CORE_SUFFIX, in_signature='s', out_signature='a{sa{s(sia{ss})}}', diff -r 6a29a4d574bd -r ca2cae6b2c6d src/bridge/bridge.py --- a/src/bridge/bridge.py Sun Sep 08 18:05:19 2013 +0200 +++ b/src/bridge/bridge.py Thu Sep 05 20:28:44 2013 +0200 @@ -59,7 +59,7 @@ def getParam(self, name, namespace): raise NotImplementedError - def getParams(self, namespace): + def getParams(self, security_limit, namespace): raise NotImplementedError def getHistory(self, from_jid, to_jid, size): diff -r 6a29a4d574bd -r ca2cae6b2c6d src/bridge/bridge_constructor/bridge_template.ini --- a/src/bridge/bridge_constructor/bridge_template.ini Sun Sep 08 18:05:19 2013 +0200 +++ b/src/bridge/bridge_constructor/bridge_template.ini Thu Sep 05 20:28:44 2013 +0200 @@ -436,32 +436,38 @@ async= type=method category=core -sig_in=s +sig_in=is sig_out=s -param_0_default="@DEFAULT@" +param_0_default=-1 +param_1_default="@DEFAULT@" doc=Return a SàT XMLUI for parameters -doc_param_0=%(doc_profile_key)s +doc_param_0=security_limit: -1 means no security then the higher the most secure +doc_param_1=%(doc_profile_key)s [getParams] async= type=method category=core -sig_in=s +sig_in=is sig_out=s -param_0_default="@DEFAULT@" +param_0_default=-1 +param_1_default="@DEFAULT@" doc=Return XML of parameters -doc_param_0=%(doc_profile_key)s +doc_param_0=security_limit: -1 means no security then the higher the most secure +doc_param_1=%(doc_profile_key)s [getParamsForCategory] async= type=method category=core -sig_in=ss +sig_in=sis sig_out=s -param_1_default="@DEFAULT@" +param_1_default=-1 +param_2_default="@DEFAULT@" doc=Return a xml of all params in a category doc_param_0=category: Category to get -doc_param_1=%(doc_profile_key)s +doc_param_1=security_limit: -1 means no security then the higher the most secure +doc_param_2=%(doc_profile_key)s [getParamsCategories] type=method diff -r 6a29a4d574bd -r ca2cae6b2c6d src/memory/memory.py --- a/src/memory/memory.py Sun Sep 08 18:05:19 2013 +0200 +++ b/src/memory/memory.py Thu Sep 05 20:28:44 2013 +0200 @@ -372,47 +372,90 @@ return None return cache[(category, name)] - def __constructProfileXml(self, profile): + def __constructProfileXml(self, security_limit, profile): """Construct xml for asked profile, filling values when needed /!\ as noticed in doc, don't forget to unlink the minidom.Document + @security_limit: -1 to return all the params. Otherwise sole the + params which have a security level defined *and* lower or equal to + the specified value are returned. @param profile: profile name (not key !) @return: a deferred that fire a minidom.Document of the profile xml (cf warning above) """ def constructProfile(ignore, profile_cache): + + def filterParam(node): + """Filter with security level. + @return: True is this param must be filtered""" + if security_limit < 0: + return False + if not node.hasAttribute('security'): + debug("filtered param: %s (no security set)" + % node.getAttribute("name")) + return True + if int(node.getAttribute('security')) > security_limit: + debug("filtered param: %s (security level > %i)" + % (node.getAttribute("name"), security_limit)) + return True + return False + + # init the result document prof_xml = minidom.parseString('') cache = {} for type_node in self.dom.documentElement.childNodes: - if type_node.nodeName == 'general' or type_node.nodeName == 'individual': # we use all params, general and individual - for cat_node in type_node.childNodes: - if cat_node.nodeName == 'category': - category = cat_node.getAttribute('name') - if category not in cache: - cache[category] = dest_cat = cat_node.cloneNode(True) # we make a copy for the new xml - new_node = True - else: - dest_cat = cache[category] - new_node = False # It's not a new node, we will merge information - params = cat_node.getElementsByTagName("param") - dest_params = {} - for node in dest_cat.childNodes: - if node.nodeName != "param": - continue - dest_params[node.getAttribute('name')] = node + if type_node.nodeName != 'general' and type_node.nodeName != 'individual': + continue + # we use all params, general and individual + for cat_node in type_node.childNodes: + if cat_node.nodeName != 'category': + continue + category = cat_node.getAttribute('name') + dest_params = {} # result (merged) params for category + if category not in cache: + # we make a copy for the new xml + cache[category] = dest_cat = cat_node.cloneNode(True) + for node in dest_cat.childNodes: + if node.nodeName != "param": + continue + if filterParam(node): + dest_cat.removeChild(node) + continue + dest_params[node.getAttribute('name')] = node + new_node = True + else: + # It's not a new node, we use the previously cloned one + dest_cat = cache[category] + new_node = False + params = cat_node.getElementsByTagName("param") - for param_node in params: - name = param_node.getAttribute('name') + for param_node in params: + # we have to merge new params (we are parsing individual parameters, we have to add them + # to the previously parsed general ones) + name = param_node.getAttribute('name') + if filterParam(param_node): + continue + if name not in dest_params: + # this is reached when a previous category exists + dest_params[name] = param_node.cloneNode(True) + dest_cat.appendChild(dest_params[name]) - if name not in dest_params: - dest_params[name] = param_node.cloneNode(True) - dest_cat.appendChild(dest_params[name]) + profile_value = self.__getParam(profile, category, + name, type_node.nodeName, + cache=profile_cache) + if profile_value is not None: + # there is a value for this profile, we must change the default + dest_params[name].setAttribute('value', profile_value) + if new_node: + prof_xml.documentElement.appendChild(dest_cat) - profile_value = self.__getParam(profile, category, name, type_node.nodeName, cache=profile_cache) - if profile_value is not None: # there is a value for this profile, we must change the default - dest_params[name].setAttribute('value', profile_value) - if new_node: - prof_xml.documentElement.appendChild(dest_cat) + to_remove = [] + for cat_node in prof_xml.documentElement.childNodes: + # we remove empty categories + if cat_node.getElementsByTagName("param").length == 0: + to_remove.append(cat_node) + for node in to_remove: + prof_xml.documentElement.removeChild(node) return prof_xml if profile in self.params: @@ -425,16 +468,16 @@ return d.addCallback(constructProfile, profile_cache) - def getParamsUI(self, profile_key): + def getParamsUI(self, security_limit, profile_key): """Return a SàT XMLUI for parameters, with given profile""" profile = self.getProfileName(profile_key) if not profile: error(_("Asking params for inexistant profile")) return "" - d = self.getParams(profile) + d = self.getParams(security_limit, profile) return d.addCallback(lambda param_xml: paramsXml2xmlUI(param_xml)) - def getParams(self, profile_key): + def getParams(self, security_limit, profile_key): """Construct xml for asked profile Take params xml as skeleton""" profile = self.getProfileName(profile_key) @@ -445,11 +488,11 @@ def returnXML(prof_xml): return_xml = prof_xml.toxml() prof_xml.unlink() - return return_xml + return '\n'.join([line for line in return_xml.split('\n')]) - return self.__constructProfileXml(profile).addCallback(returnXML) + return self.__constructProfileXml(security_limit, profile).addCallback(returnXML) - def getParamsForCategory(self, category, profile_key): + def getParamsForCategory(self, category, security_limit, profile_key): """Return node's xml for selected category""" #TODO: manage category of general type (without existant profile) profile = self.getProfileName(profile_key) @@ -467,7 +510,7 @@ prof_xml.unlink() return "" - d = self.__constructProfileXml(profile) + d = self.__constructProfileXml(security_limit, profile) return d.addCallback(returnCategoryXml) def __getParamNode(self, name, category, _type="@ALL@"): # FIXME: is _type useful ? @@ -851,14 +894,14 @@ def asyncGetStringParamA(self, name, category, attr="value", profile_key='@DEFAULT@'): return self.params.asyncGetStringParamA(name, category, attr, profile_key) - def getParamsUI(self, profile_key): - return self.params.getParamsUI(profile_key) + def getParamsUI(self, security_limit, profile_key): + return self.params.getParamsUI(security_limit, profile_key) - def getParams(self, profile_key): - return self.params.getParams(profile_key) + def getParams(self, security_limit, profile_key): + return self.params.getParams(security_limit, profile_key) - def getParamsForCategory(self, category, profile_key): - return self.params.getParamsForCategory(category, profile_key) + def getParamsForCategory(self, category, security_limit, profile_key): + return self.params.getParamsForCategory(category, security_limit, profile_key) def getParamsCategories(self): return self.params.getParamsCategories()