From 8e48af9373d40f61e0b41c2c1583158d87559be9 Mon Sep 17 00:00:00 2001 From: Jephte Clain Date: Fri, 16 Jun 2017 00:36:36 +0400 Subject: [PATCH] =?UTF-8?q?d=C3=A9but=20de=20travail=20sur=20les=20liens?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- lib/ulib/support/deploydb.py | 190 +++++++++++++++++++++++++++++++---- 1 file changed, 171 insertions(+), 19 deletions(-) diff --git a/lib/ulib/support/deploydb.py b/lib/ulib/support/deploydb.py index e411149..670bdd8 100755 --- a/lib/ulib/support/deploydb.py +++ b/lib/ulib/support/deploydb.py @@ -52,7 +52,7 @@ class GenericObject(object): elif method == 'reset': self.reset_attr(name, value) elif method == 'add': self.add_attr(name, value) elif method == 'del': self.del_attr(name, value) - def copy_attrs(self, other, method='set'): + def merge_attrs(self, other, method='set'): for name, values in other.attrs.items(): for value in values: self.modify_attr(name, value, method) @@ -130,29 +130,131 @@ class WebappObject(GenericObject): self._dump_values(indent, 'webapps') self._dump_attrs(indent) +class GenericLink(object): + _profile = None + _ftype = None + _froms = None + _ttype = None + _tos = None + _attrs = None + + def __init__(self, ftype, ttype): + self._ftype = ftype + self._froms = [] + self._ttype = ttype + self._tos = [] + self._attrs = {} + + def get_profile(self): return self._profile + def set_profile(self): self._profile = profile + profile = property(get_profile, set_profile) + + def get_ftype(self): return self._ftype + ftype = property(get_ftype) + def get_froms(self): return self._froms + froms = property(get_froms) + def add_from(self, fo): + if fo not in self._froms: self._froms.append(fo) + + def get_ttype(self): return self._ttype + ttype = property(get_ttype) + def get_tos(self): return self._tos + tos = property(get_tos) + def add_to(self, to): + if to not in self._tos: self._tos.append(to) + + def get_attrs(self): return self._attrs + attrs = property(get_attrs) + + def get_attr(self, name): return self._attrs.get(name, None) + def set_attr(self, name, value): + if name not in self._attrs: self._attrs[name] = [] + if value not in self._attrs[name]: self._attrs[name].append(value) + def reset_attr(self, name, value=None): + if name in self._attrs: del self._attrs[name] + if value is not None: self.set_attr(name, value) + def add_attr(self, name, value): + if name not in self._attrs: self._attrs[name] = [] + self._attrs[name].append(value) + def del_attr(self, name, value): + if name not in self._attrs: return + self._attrs[name].remove(value) + if not self._attrs[name]: del self._attrs[name] + def modify_attr(self, name, value, method='set'): + if method == 'set': self.set_attr(name, value) + elif method == 'reset': self.reset_attr(name, value) + elif method == 'add': self.add_attr(name, value) + elif method == 'del': self.del_attr(name, value) + def merge_attrs(self, other, method='set'): + for name, values in other.attrs.items(): + for value in values: + self.modify_attr(name, value, method) + + def _dump_profile(self, indent): + profile = self.profile or 'ALL' + print "%s profile: %s" % (indent, profile) + def _dump_froms(self, indent): + print "%s from: %s" % (indent, ' '.join(self.froms)) + def _dump_tos(self, indent): + print "%s to: %s" % (indent, ' '.join(self.tos)) + def _dump_attrs(self, indent): + if self.attrs: + print "%s attrs:" % indent + for name, values in self.attrs.items(): + if len(values) == 1: + print "%s %s=%s" % (indent, name, repr(values[0])) + else: + print "%s %s=(%s)" % (indent, name, ', '.join(map(repr, values))) + def dump(self, indent=''): + print "%slink" % indent + self._dump_profile(indent) + self._dump_froms(indent) + self._dump_tos(indent) + self._dump_attrs(indent) + +class UinstLink(GenericLink): + def __init__(self): + super(UinstLink, self).__init__('module', 'host') + + def dump(self, indent=''): + print "%suinst" % indent + self._dump_profile(indent) + self._dump_froms(indent) + self._dump_tos(indent) + self._dump_attrs(indent) + +class RuinstLink(GenericLink): + def __init__(self): + super(UinstLink, self).__init__('module', 'host') + + def dump(self, indent=''): + print "%suinst" % indent + self._dump_froms(indent) + self._dump_tos(indent) + self._dump_attrs(indent) + class Database(object): - _known_profiles = None _default_profile = None _default_domain = None _objects = None _objects_classes = None + _links = None + _links_classes = None + def __init__(self): self._known_profiles = {} self._objects = {} self._objects_classes = {} - - def get_known_profiles(self): - return self._known_profiles.keys() - known_profiles = property(get_known_profiles) + self._links = {} + self._links_classes = {} def has_default_profile(self): return self._default_profile is not None def get_default_profile(self): return self._default_profile def set_default_profile(self, profile): - if profile: self._known_profiles[profile] = True self._default_profile = profile or None default_profile = property(get_default_profile, set_default_profile) @@ -180,7 +282,6 @@ class Database(object): objects = self._objects.get(otype, None) if objects is None: return None return [objects[id] for id in objects if id is not None] - objects = property(get_objects) def has_object(self, otype, id): objects = self._objects.get(otype, None) if objects is None: return False @@ -196,6 +297,18 @@ class Database(object): self._objects[otype][id] = object return object + def register_link(self, ltype, lclass=None): + if not self._links.has_key(ltype): + self._links[ltype] = {} + if lclass is None: lclass = GenericLink + self._links_classes[ltype] = lclass + def get_known_profiles(self, ltype): + return self._links[ltype].keys() + def get_links(self, ltype, profile=None): + links = self._links.get(ltype, None) + if links is None: return None + return links.get(profile, None) + ################################################################################ # Analyse des fichiers de configuration @@ -538,27 +651,29 @@ class Parser(object): if name: o = self.db.get_object('host', name) if host: o.add_value(host) - o.copy_attrs(defaulto) + o.merge_attrs(defaulto) if dir is not None: o.set_attr('dir', dir) self.add_group('host', name) else: id = HostObject.genid(host) o = self.db.get_object('host', id) o.add_value(host) - o.copy_attrs(defaulto) + o.merge_attrs(defaulto) if dir is not None: o.set_attr('dir', dir) self.add_group('host', id) ib = HostObject.genib(id) o = self.db.get_object('host', ib) o.add_value(host) - o.copy_attrs(defaulto) + o.merge_attrs(defaulto) if dir is not None: o.set_attr('dir', dir) self.add_group('host', ib) ############################################################################ def __setup_uinst(self): self.db.register_object('module', ModuleObject) + self.db.register_link('uinst', UinstLink) + self.db.register_link('ruinst', RuinstLink) self.db.get_object('module', None) self.groups['module'] = {} self.handle_group(['module', 'defaults']) @@ -618,7 +733,7 @@ class Parser(object): if name: o = self.db.get_object('module', name) if module: o.add_value(module) - o.copy_attrs(defaulto) + o.merge_attrs(defaulto) if dir is not None: o.set_attr('dir', dir) if modulep is not None: o.set_attr('path', modulep) self.add_group('module', name) @@ -626,13 +741,50 @@ class Parser(object): id = ModuleObject.genid(module) o = self.db.get_object('module', id) if module: o.add_value(module) - o.copy_attrs(defaulto) + o.merge_attrs(defaulto) if dir is not None: o.set_attr('dir', dir) if modulep is not None: o.set_attr('path', modulep) self.add_group('module', id) - def handle_xuinst(self, cmd, *args): - pass + def handle_xuinst(self, ltype, *args): + """uinst -p profile attrs* + ruinst -p profile attrs* + """ + AP = ArgumentParser() + AP.add_argument('-p', '--profile', action='append', dest='profiles') + AP.add_argument('nvss', nargs=REMAINDER) + o = AP.parse_args(args) + profiles = o.profiles or [None] + for profile in profiles: + # préparer la mise à jour du groupe courant + currentls = self.db.get_link(ltype, profile, fo=self.groups['module']['current'], create=True) + if profile is not None: + globall = self.db.get_link(ltype, None, fo=None, create=True) + for currentl in currentls: + currentl.merge_attrs(globall) + defaultl = self.db.get_link(ltype, profile, fo=None, create=True) + for currentl in currentls: + currentl.merge_attrs(defaultl) + # traiter les liens + for nvs in nvss: + name, value = split_namev(nvs) + if name == defaultl.ttype: + # définir des destinations du lien + values = split_nlist(nvs)[1] + for host in values: + for currentl in currentls: + currentl.add_to(host) + else: + # définir un attribut du lien + name, value, type, method = split_namev(nv) + if value is None: + method = 'set' + value = '1' + elif type == 'path': + value = path.expanduser(value) + for id in self.groups[otype]['current']: + for currentl in currentls: + currentl.modify_attr(name, value, method) ############################################################################ def __setup_woinst(self): @@ -697,7 +849,7 @@ class Parser(object): if name: o = self.db.get_object('wobundle', name) if wobundle: o.add_value(wobundle) - o.copy_attrs(defaulto) + o.merge_attrs(defaulto) if dir is not None: o.set_attr('dir', dir) if wobundlep is not None: o.set_attr('path', wobundlep) self.add_group('wobundle', name) @@ -705,7 +857,7 @@ class Parser(object): id = WobundleObject.genid(wobundle) o = self.db.get_object('wobundle', id) if wobundle: o.add_value(wobundle) - o.copy_attrs(defaulto) + o.merge_attrs(defaulto) if dir is not None: o.set_attr('dir', dir) if wobundlep is not None: o.set_attr('path', wobundlep) self.add_group('wobundle', id) @@ -774,7 +926,7 @@ class Parser(object): if name: o = self.db.get_object('webapp', name) if webapp: o.add_value(webapp) - o.copy_attrs(defaulto) + o.merge_attrs(defaulto) if dir is not None: o.set_attr('dir', dir) if webappp is not None: o.set_attr('path', webappp) self.add_group('webapp', name) @@ -782,7 +934,7 @@ class Parser(object): id = WebappObject.genid(webapp) o = self.db.get_object('webapp', id) if webapp: o.add_value(webapp) - o.copy_attrs(defaulto) + o.merge_attrs(defaulto) if dir is not None: o.set_attr('dir', dir) if webappp is not None: o.set_attr('path', webappp) self.add_group('webapp', id)