From 3ace1dfae5ad70382e0d5062ba6930a76e9c6cbc Mon Sep 17 00:00:00 2001 From: Emmanuel Garette Date: Mon, 24 Feb 2020 20:16:49 +0100 Subject: [PATCH] add servermodel.updated --- README.md | 13 +- .../config.configuration.server.deploy.yml | 17 -- .../config.configuration.server.get.yml | 5 +- .../config.configuration.server.updated.yml | 21 -- messages/v1/messages/servermodel.create.yml | 1 + .../applicationservice/applicationservice.py | 7 +- src/risotto/services/config/config.py | 233 +++++++----------- .../services/servermodel/servermodel.py | 16 +- src/risotto/services/session/session.py | 4 +- src/risotto/services/session/storage.py | 2 +- 10 files changed, 106 insertions(+), 213 deletions(-) delete mode 100644 messages/v1/messages/config.configuration.server.deploy.yml delete mode 100644 messages/v1/messages/config.configuration.server.updated.yml diff --git a/README.md b/README.md index cf0077b..113d645 100644 --- a/README.md +++ b/README.md @@ -80,7 +80,7 @@ S=xxxxxxxxxxxxxxxxxxxxxx ./script/cucchiaiata session.servermodel.stop -s $S -a ## unbound -./script/cucchiaiata servermodel.create -n unbound -d "generic unbound configuration" -p eolebase -s eole -r last +./script/cucchiaiata servermodel.create -n unbound -d "generic unbound configuration" -s eole -r last ./script/cucchiaiata session.servermodel.start -s unbound S=xxxxxxxxxxxxxxxxxxxxxx ./script/cucchiaiata session.servermodel.configure -s $S --creole.serveur_dns.unbound_local_zones cadoles.com @@ -109,17 +109,8 @@ S=xxxxxxxxxxxxxxxxxxxxxx ./script/cucchiaiata session.server.stop -s $S -a # Generate configuration -./script/cucchiaiata config.configuration.server.deploy -s test ./script/cucchiaiata template.generate -s test - # OpenSSH -#add servermodel openssh link to eolebase -#add servermodel openssh2 lint to openssh -#link openssh applicationservice to this servermodel +./script/cucchiaiata applicationservice.dependency.add -n local_aca -a openssh -s eole -r last -./script/cucchiaiata servermodel.create -n openssh_1 -d description -p eolebase -s eole -r last -./script/cucchiaiata servermodel.create -n openssh_2 -d openssh_2 -p openssh_1 -s internal -r last -./script/cucchiaiata applicationservice.dependency.add -n local_openssh_1 -a openssh -s eole -r last - -#./script/cucchiaiata server.create -s test -d description -m eolebase -r last diff --git a/messages/v1/messages/config.configuration.server.deploy.yml b/messages/v1/messages/config.configuration.server.deploy.yml deleted file mode 100644 index 6bce28c..0000000 --- a/messages/v1/messages/config.configuration.server.deploy.yml +++ /dev/null @@ -1,17 +0,0 @@ ---- -uri: config.configuration.server.deploy - -description: Déployer la configuration d'un serveur. - -pattern: rpc - -parameters: - server_name: - type: String - ref: Server.ServerName - shortarg: s - description: Nom du serveur. - -response: - type: Deploy - description: La configuration du serveur est déployée. diff --git a/messages/v1/messages/config.configuration.server.get.yml b/messages/v1/messages/config.configuration.server.get.yml index 80b5a01..a2b35f7 100644 --- a/messages/v1/messages/config.configuration.server.get.yml +++ b/messages/v1/messages/config.configuration.server.get.yml @@ -10,11 +10,8 @@ parameters: server_name: type: String ref: Server.ServerName + shortarg: s description: Nom du serveur. - deployed: - type: Boolean - description: Configuration de type déployée. - default: true response: type: ConfigConfiguration diff --git a/messages/v1/messages/config.configuration.server.updated.yml b/messages/v1/messages/config.configuration.server.updated.yml deleted file mode 100644 index 4d90d81..0000000 --- a/messages/v1/messages/config.configuration.server.updated.yml +++ /dev/null @@ -1,21 +0,0 @@ ---- -uri: config.configuration.server.updated - -description: | - Une configuration de serveur a été mise à jour. - -pattern: event - -parameters: - server_id: - type: Number - description: | - Identifiant du serveur. - server_name: - type: String - ref: Server.ServerName - shortarg: s - description: Nom du serveur. - deployed: - type: Boolean - description: Configuration de type déployée. diff --git a/messages/v1/messages/servermodel.create.yml b/messages/v1/messages/servermodel.create.yml index f5738a6..f1f1a77 100644 --- a/messages/v1/messages/servermodel.create.yml +++ b/messages/v1/messages/servermodel.create.yml @@ -21,6 +21,7 @@ parameters: ref: Servermodel.ServermodelName shortarg: p description: Nom des modèles de serveur parents auquels rattacher le nouveau modèle. + default: null servermodel_parents_source_name: type: String shortarg: s diff --git a/src/risotto/services/applicationservice/applicationservice.py b/src/risotto/services/applicationservice/applicationservice.py index 467ee9b..71c66c5 100644 --- a/src/risotto/services/applicationservice/applicationservice.py +++ b/src/risotto/services/applicationservice/applicationservice.py @@ -89,10 +89,9 @@ class Risotto(Controller): as_descr['applicationservice_id'], dependency_descr['applicationservice_id']): raise Exception(_(f'{applicationservice_name} has already a dependency to {applicationservice_dependency}')) - else: - await self.insert_dependency(risotto_context, - as_descr['applicationservice_id'], - [dependency_descr['applicationservice_id']]) + await self.insert_dependency(risotto_context, + as_descr['applicationservice_id'], + [dependency_descr['applicationservice_id']]) await self.publish('v1.applicationservice.updated', risotto_context, **as_descr) diff --git a/src/risotto/services/config/config.py b/src/risotto/services/config/config.py index 5f0559f..9144555 100644 --- a/src/risotto/services/config/config.py +++ b/src/risotto/services/config/config.py @@ -5,7 +5,7 @@ from os.path import isdir, isfile, join from traceback import print_exc from typing import Dict, List -from tiramisu import Storage, delete_session, MetaConfig, MixConfig +from tiramisu import Storage, MixConfig from rougail import load as rougail_load from rougail.config import dtdfilename @@ -89,10 +89,10 @@ class Risotto(Controller): with open(cache_file) as fileio: xmlroot = parse(fileio).getroot() try: - self.servermodel[servermodel_id] = await self.build_metaconfig(servermodel_id, - servermodel_name, - xmlroot, - funcs_file) + self.servermodel[servermodel_id] = await self.build_mixconfig(servermodel_id, + servermodel_name, + xmlroot, + funcs_file) except Exception as err: if get_config().get('global').get('debug'): print_exc() @@ -101,12 +101,12 @@ class Risotto(Controller): None, msg) - async def build_metaconfig(self, - servermodel_id: int, - servermodel_name: str, - xmlroot: str, - funcs_file: str) -> MetaConfig: - """ Build metaconfig for a servermodel + async def build_mixconfig(self, + servermodel_id: int, + servermodel_name: str, + xmlroot: str, + funcs_file: str) -> MixConfig: + """ Build mixconfig for a servermodel """ # build tiramisu's session ID session_id = f'v_{servermodel_id}' @@ -114,37 +114,31 @@ class Risotto(Controller): dtdfilename, funcs_file) - # build servermodel metaconfig (v_xxx.m_v_xxx) - metaconfig = await MetaConfig([], - optiondescription=optiondescription, - session_id=session_id, - storage=self.save_storage) + # build servermodel mixconfig (v_xxx) mixconfig = await MixConfig(children=[], optiondescription=optiondescription, - session_id='m_' + session_id, + session_id=session_id, storage=self.save_storage) - await metaconfig.config.add(mixconfig) - # change default rights - ro_origin = await metaconfig.property.getdefault('read_only', 'append') + ro_origin = await mixconfig.property.getdefault('read_only', 'append') ro_append = frozenset(ro_origin - {'force_store_value'}) - rw_origin = await metaconfig.property.getdefault('read_write', 'append') + rw_origin = await mixconfig.property.getdefault('read_write', 'append') rw_append = frozenset(rw_origin - {'force_store_value'}) - await metaconfig.property.setdefault(ro_append, 'read_only', 'append') - await metaconfig.property.setdefault(rw_append, 'read_write', 'append') + await mixconfig.property.setdefault(ro_append, 'read_only', 'append') + await mixconfig.property.setdefault(rw_append, 'read_write', 'append') - await metaconfig.property.read_only() - await metaconfig.permissive.add('basic') - await metaconfig.permissive.add('normal') - await metaconfig.permissive.add('expert') + await mixconfig.property.read_only() + await mixconfig.permissive.add('basic') + await mixconfig.permissive.add('normal') + await mixconfig.permissive.add('expert') # set informtion and owner - await metaconfig.owner.set('v_{}'.format(servermodel_name)) - await metaconfig.information.set('servermodel_id', servermodel_id) - await metaconfig.information.set('servermodel_name', servermodel_name) + await mixconfig.owner.set('v_{}'.format(servermodel_name)) + await mixconfig.information.set('servermodel_id', servermodel_id) + await mixconfig.information.set('servermodel_name', servermodel_name) # return configuration - return metaconfig + return mixconfig async def servermodel_legacy(self, risotto_context: Context, @@ -169,9 +163,9 @@ class Risotto(Controller): msg) # do link - mix = await servermodel_parent.config.get('m_v_' + str(servermodel_parent_id)) + # mix = await servermodel_parent.config.get('m_v_' + str(servermodel_parent_id)) try: - await mix.config.add(self.servermodel[servermodel_id]) + await servermodel_parent.config.add(self.servermodel[servermodel_id]) except Exception as err: await log.error_msg(risotto_context, None, @@ -190,6 +184,8 @@ class Risotto(Controller): # loads servers for server in servers: try: + if server['server_id'] in self.server: + return await self.load_server(risotto_context, server['server_id'], server['server_name'], @@ -211,8 +207,6 @@ class Risotto(Controller): server_servermodel_id: int) -> None: """ Loads a server """ - if server_id in self.server: - return await log.info_msg(risotto_context, None, f'Load server {server_name} ({server_id})') @@ -226,29 +220,25 @@ class Risotto(Controller): # check if server was already created session_id = f's_{server_id}' - # get the servermodel's metaconfig - metaconfig = self.servermodel[server_servermodel_id] + # get the servermodel's mixconfig + mixconfig = self.servermodel[server_servermodel_id] - # create server configuration and server 'to deploy' configuration and store it + # create server configuration and store it self.server[server_id] = {'server': await self.build_config(session_id, server_id, server_name, - metaconfig), - 'server_to_deploy': await self.build_config(f'std_{server_id}', - server_id, - server_name, - metaconfig), + mixconfig), 'funcs_file': self.get_funcs_filename(server_servermodel_id)} async def build_config(self, session_id: str, server_id: int, server_name: str, - metaconfig: MetaConfig) -> None: + mixconfig: MixConfig) -> None: """ build server's config """ - config = await metaconfig.config.new(session_id, - storage=self.save_storage) + config = await mixconfig.config.new(session_id, + storage=self.save_storage) await config.information.set('server_id', server_id) await config.information.set('server_name', server_name) await config.owner.set(server_name) @@ -263,6 +253,8 @@ class Risotto(Controller): server_servermodel_id: int) -> None: """ Loads server's configuration when a new server is created """ + if server_id in self.server: + return await self.load_server(risotto_context, server_id, server_name, @@ -272,13 +264,11 @@ class Risotto(Controller): async def server_deleted(self, server_id: int) -> None: # delete config to it's parents - for server_type in ['server', 'server_to_deploy']: - config = self.server[server_id]['server'] - for parent in await config.config.parents(): - await parent.config.pop(await config.config.name()) - delete_session(storage=self.save_storage, - session_id=await config.config.name()) - # delete metaconfig + config = self.server[server_id]['server'] + for parent in await config.config.parents(): + await parent.config.pop(await config.session.id()) + await config.session.reset() + # delete mixconfig del self.server[server_id] @register('v1.servermodel.created') @@ -311,68 +301,53 @@ class Risotto(Controller): servermodelparentid) async def servermodel_delete(self, - servermodel_id: int) -> List[MetaConfig]: - metaconfig = self.servermodel.pop(servermodel_id) - mixconfig = await metaconfig.config.list()[0] + servermodel_id: int) -> List[MixConfig]: + mixconfig = self.servermodel.pop(servermodel_id) children = [] for child in await mixconfig.config.list(): children.append(child) - await mixconfig.config.pop(await child.config.name()) - await metaconfig.config.pop(await mixconfig.config.name()) - delete_session(storage=self.save_storage, - session_id=await mixconfig.config.name()) - del mixconfig - for parent in await metaconfig.config.parents(): - await parent.config.pop(await metaconfig.config.name()) - delete_session(storage=self.save_storage, - session_id=await metaconfig.config.name()) + await mixconfig.config.pop(await child.session.id()) + for parent in await mixconfig.config.parents(): + await parent.config.pop(await mixconfig.session.id()) + await mixconfig.session.reset() return children -# -# @register('v1.servermodel.updated') -# async def servermodel_updated(self, -# risotto_context: Context, -# servermodel_id: int, -# servermodel_name: str, -# servermodel_parents_id: List[int]) -> None: -# log.info_msg(risotto_context, -# None, -# f'Reload servermodel {servermodel_name} ({servermodel_id})') -# # unlink cache to force download new aggregated file -# cache_file = join(self.cache_root_path, str(servermodel_id)+".xml") -# if isfile(cache_file): -# unlink(cache_file) -# -# # store all informations -# if servermodel_id in self.servermodel: -# old_values = await self.servermodel[servermodel_id].value.exportation() -# old_permissives = await self.servermodel[servermodel_id].permissive.exportation() -# old_properties = await self.servermodel[servermodel_id].property.exportation() -# children = await self.servermodel_delete(servermodel_id) -# else: -# old_values = None -# -# # create new one -# await self.load_and_link_servermodel(risotto_context, -# servermodel_id, -# servermodel_name, -# servermodel_parents_id) -# -# # migrates informations -# if old_values is not None: -# await self.servermodel[servermodel_id].value.importation(old_values) -# await self.servermodel[servermodel_id].permissive.importation(old_permissives) -# await self.servermodel[servermodel_id].property.importation(old_properties) -# for child in children: -# await self.servermodel_legacy(risotto_context, -# await child.information.get('servermodel_name'), -# await child.information.get('servermodel_id'), -# servermodel_id) + + @register('v1.servermodel.updated') + async def servermodel_updated(self, + risotto_context: Context, + servermodel_id: int, + servermodel_name: str, + servermodel_parents_id: List[int]) -> None: + await log.info_msg(risotto_context, + None, + f'Reload servermodel {servermodel_name} ({servermodel_id})') + # store all informations + if servermodel_id in self.servermodel: + children = await self.servermodel_delete(servermodel_id) + else: + children = [] + + # create new one + await self.load_and_link_servermodel(risotto_context, + servermodel_id, + servermodel_name, + servermodel_parents_id) + # recreate link to children + for child in children: + if await child.config.type() == 'config': + server_id = await child.information.get('server_id') + server_name = await child.information.get('server_name') + await self.load_server(risotto_context, + server_id, + server_name, + servermodel_id) + else: + await self.servermodel[servermodel_id].config.add(child) @register('v1.config.configuration.server.get') async def get_configuration(self, risotto_context: Context, - server_name: str, - deployed: bool) -> bytes: + server_name: str) -> dict: server = await self.call('v1.server.describe', risotto_context, server_name=server_name) @@ -384,57 +359,17 @@ class Risotto(Controller): msg) raise CallError(msg) - if deployed: - server = self.server[server_id]['server'] - else: - server = self.server[server_id]['server_to_deploy'] + server = self.server[server_id]['server'] await server.property.read_only() try: configuration = await server.value.dict(fullpath=True, leader_to_list=True) except: - if deployed: - msg = _(f'No configuration available for server {server_id}') - else: - msg = _(f'No undeployed configuration available for server {server_id}') + msg = _(f'No configuration available for server {server_id}') await log.error_msg(risotto_context, None, msg) raise CallError(msg) return {'server_name': server_name, - 'deployed': deployed, 'configuration': configuration} - - @register('v1.config.configuration.server.deploy', 'v1.config.configuration.server.updated') - async def deploy_configuration(self, - risotto_context: Context, - server_name: str) -> Dict: - """Copy values, permissions, permissives from config 'to deploy' to active config - """ - server = await self.call('v1.server.describe', - risotto_context, - server_name=server_name) - server_id = server['server_id'] - # FIXME is server_to_deploy working? - config = self.server[server_id]['server'] - config_std = self.server[server_id]['server_to_deploy'] - - # when deploy, calculate force_store_value - ro = await config_std.property.getdefault('read_only', 'append') - if 'force_store_value' not in ro: - ro = frozenset(list(ro) + ['force_store_value']) - await config_std.property.setdefault(ro, 'read_only', 'append') - rw = await config_std.property.getdefault('read_write', 'append') - rw = frozenset(list(rw) + ['force_store_value']) - await config_std.property.setdefault(rw, 'read_write', 'append') - await config_std.property.add('force_store_value') - - # copy informations from server 'to deploy' configuration to server configuration - await config.value.importation(await config_std.value.exportation()) - await config.permissive.importation(await config_std.permissive.exportation()) - await config.property.importation(await config_std.property.exportation()) - - return {'server_id': server_id, - 'server_name': server_name, - 'deployed': True} diff --git a/src/risotto/services/servermodel/servermodel.py b/src/risotto/services/servermodel/servermodel.py index 412a556..0e8acb2 100644 --- a/src/risotto/services/servermodel/servermodel.py +++ b/src/risotto/services/servermodel/servermodel.py @@ -183,7 +183,9 @@ class Risotto(Generator): if not servermodel_parent and parent is not None: servermodel_parent = [await self._servermodel_describe(risotto_context, parent, - release_id)] + release_id, + source_name, + release_distribution)] # link application service with this servermodel dependencies = [] for depend in servermodels[new_servermodel]['applicationservices']: @@ -237,12 +239,16 @@ class Risotto(Generator): release_distribution=release_distribution) return await self._servermodel_describe(risotto_context, servermodel_name, - release['release_id']) + release['release_id'], + source_name, + release_distribution) async def _servermodel_describe(self, risotto_context, servermodel_name, - release_id): + release_id, + source_name, + release_distribution): sql = ''' SELECT ServermodelId as servermodel_id, ServermodelName as servermodel_name, ServermodelDescription as servermodel_description, ServermodelParentsId as servermodel_parents_id, ServermodelReleaseId as release_id, ServermodelApplicationServiceId as servermodel_applicationservice_id FROM Servermodel @@ -272,7 +278,9 @@ class Risotto(Generator): for servermodel_parent_name in servermodel_parents_name: servermodel_parents.append(await self._servermodel_describe(risotto_context, servermodel_parent_name, - release_id)) + release_id, + servermodel_parents_source_name, + servermodel_parents_release_distribution)) return await self._servermodel_create(risotto_context, servermodel_name, servermodel_description, diff --git a/src/risotto/services/session/session.py b/src/risotto/services/session/session.py index 2b27efe..db336fc 100644 --- a/src/risotto/services/session/session.py +++ b/src/risotto/services/session/session.py @@ -79,7 +79,7 @@ class Risotto(Controller): if not server or server['server_id'] not in config_module.server: raise Exception(_(f'cannot find server with name {server_name}')) id = server['server_id'] - config = config_module.server[id]['server_to_deploy'] + config = config_module.server[id]['server'] storage = self.get_storage('server') @@ -287,7 +287,7 @@ class Risotto(Controller): id_ = session['id'] config_module = dispatcher.get_service('config') if type == 'server': - config = config_module.server[id_]['server_to_deploy'] + config = config_module.server[id_]['server'] else: config = config_module.servermodel[id_] if save: diff --git a/src/risotto/services/session/storage.py b/src/risotto/services/session/storage.py index fe71432..0c2b8be 100644 --- a/src/risotto/services/session/storage.py +++ b/src/risotto/services/session/storage.py @@ -124,7 +124,7 @@ class Storage(object): class StorageServer(Storage): def get_config_name(self, server_id: int): - return f'std_{server_id}' + return f's_{server_id}' async def set_owner(self, config: Config,