# copyright 2010-2011 LOGILAB S.A. (Paris, FRANCE), all rights reserved.# contact http://www.logilab.fr/ -- mailto:contact@logilab.fr## This file is part of CubicWeb.## CubicWeb is free software: you can redistribute it and/or modify it under the# terms of the GNU Lesser General Public License as published by the Free# Software Foundation, either version 2.1 of the License, or (at your option)# any later version.## CubicWeb is distributed in the hope that it will be useful, but WITHOUT# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS# FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more# details.## You should have received a copy of the GNU Lesser General Public License along# with CubicWeb. If not, see <http://www.gnu.org/licenses/>."""hooks for repository sources synchronization"""fromsocketimportgethostnamefromyams.schemaimportrole_namefromcubicwebimportValidationErrorfromcubicweb.selectorsimportis_instancefromcubicweb.serverimportSOURCE_TYPES,hookclassSourceHook(hook.Hook):__abstract__=Truecategory='cw.sources'classSourceAddedOp(hook.Operation):defpostcommit_event(self):self.session.repo.add_source(self.entity)classSourceAddedHook(SourceHook):__regid__='cw.sources.added'__select__=SourceHook.__select__&is_instance('CWSource')events=('after_add_entity',)def__call__(self):try:sourcecls=SOURCE_TYPES[self.entity.type]exceptKeyError:msg=self._cw._('unknown source type')raiseValidationError(self.entity.eid,{role_name('type','subject'):msg})sourcecls.check_conf_dict(self.entity.eid,self.entity.host_config,fail_if_unknown=notself._cw.vreg.config.repairing)SourceAddedOp(self._cw,entity=self.entity)classSourceRemovedOp(hook.Operation):defprecommit_event(self):self.session.repo.remove_source(self.uri)classSourceRemovedHook(SourceHook):__regid__='cw.sources.removed'__select__=SourceHook.__select__&is_instance('CWSource')events=('before_delete_entity',)def__call__(self):ifself.entity.name=='system':raiseValidationError(self.entity.eid,{None:'cant remove system source'})SourceRemovedOp(self._cw,uri=self.entity.name)classSourceUpdatedOp(hook.DataOperationMixIn,hook.Operation):defprecommit_event(self):self.__processed=[]forsourceinself.get_data():conf=source.repo_source.check_config(source)self.__processed.append((source,conf))defpostcommit_event(self):forsource,confinself.__processed:source.repo_source.update_config(source,conf)classSourceUpdatedHook(SourceHook):__regid__='cw.sources.configupdate'__select__=SourceHook.__select__&is_instance('CWSource')events=('after_update_entity',)def__call__(self):if'config'inself.entity.cw_edited:SourceUpdatedOp.get_instance(self._cw).add_data(self.entity)classSourceHostConfigUpdatedHook(SourceHook):__regid__='cw.sources.hostconfigupdate'__select__=SourceHook.__select__&is_instance('CWSourceHostConfig')events=('after_add_entity','after_update_entity','before_delete_entity',)def__call__(self):ifself.entity.match(gethostname()):ifself.event=='after_update_entity'and \not'config'inself.entity.cw_edited:returntry:SourceUpdatedOp.get_instance(self._cw).add_data(self.entity.cwsource)exceptIndexError:# XXX no source linked to the host config yetpass# source mapping synchronization. Expect cw_for_source/cw_schema are immutable# relations (i.e. can't change from a source or schema to another).classSourceMappingDeleteHook(SourceHook):"""check cw_for_source and cw_schema are immutable relations XXX empty delete perms would be enough? """__regid__='cw.sources.delschemaconfig'__select__=SourceHook.__select__&hook.match_rtype('cw_for_source','cw_schema')events=('before_add_relation',)def__call__(self):ifnotself._cw.added_in_transaction(self.eidfrom):msg=self._cw._("can't change this relation")raiseValidationError(self.eidfrom,{self.rtype:msg})classSourceMappingChangedOp(hook.DataOperationMixIn,hook.Operation):defcheck_or_update(self,checkonly):session=self.session# take care, can't call get_data() twicetry:data=self.__dataexceptAttributeError:data=self.__data=self.get_data()forschemacfg,sourceindata:ifsourceisNone:source=schemacfg.cwsource.repo_sourceifsession.added_in_transaction(schemacfg.eid):ifnotsession.deleted_in_transaction(schemacfg.eid):source.add_schema_config(schemacfg,checkonly=checkonly)elifsession.deleted_in_transaction(schemacfg.eid):source.delete_schema_config(schemacfg,checkonly=checkonly)else:source.update_schema_config(schemacfg,checkonly=checkonly)defprecommit_event(self):self.check_or_update(True)defpostcommit_event(self):self.check_or_update(False)classSourceMappingChangedHook(SourceHook):__regid__='cw.sources.schemaconfig'__select__=SourceHook.__select__&is_instance('CWSourceSchemaConfig')events=('after_add_entity','after_update_entity')def__call__(self):ifself.event=='after_add_entity'or(self.event=='after_update_entity'and'options'inself.entity.cw_edited):SourceMappingChangedOp.get_instance(self._cw).add_data((self.entity,None))classSourceMappingDeleteHook(SourceHook):__regid__='cw.sources.delschemaconfig'__select__=SourceHook.__select__&hook.match_rtype('cw_for_source')events=('before_delete_relation',)def__call__(self):SourceMappingChangedOp.get_instance(self._cw).add_data((self._cw.entity_from_eid(self.eidfrom),self._cw.entity_from_eid(self.eidto)))