configurationengine/source/scripts/conesub_merge.py
changeset 5 d2c80f5cab53
parent 3 e7e0ae78773e
equal deleted inserted replaced
4:0951727b8815 5:d2c80f5cab53
    14 # Description: 
    14 # Description: 
    15 #
    15 #
    16 
    16 
    17 import sys
    17 import sys
    18 import logging
    18 import logging
       
    19 import re
    19 from optparse import OptionParser, OptionGroup
    20 from optparse import OptionParser, OptionGroup
    20 import cone_common
    21 import cone_common
    21 
    22 
    22 from cone.public import api, utils, exceptions
    23 from cone.public import api, utils, exceptions
    23 
    24 
   182             return active_root
   183             return active_root
   183 
   184 
   184 def merge_config_root_to_config_root(source_project, target_project,
   185 def merge_config_root_to_config_root(source_project, target_project,
   185                                      source_config, target_config,
   186                                      source_config, target_config,
   186                                      layer_finder_func,
   187                                      layer_finder_func,
   187                                      merge_policy):
   188                                      merge_policy,
       
   189                                      find_pattern=None):
   188     """
   190     """
   189     Merge the source configuration root to the target configuration root.
   191     Merge the source configuration root to the target configuration root.
   190     
   192     
   191     @param source_config: Name of the source configuration.
   193     @param source_config: Name of the source configuration.
   192     @param target_config: Name of the target configuration.
   194     @param target_config: Name of the target configuration.
   195         arguments and return a list of tuples (layer_root, target_layer_root),
   197         arguments and return a list of tuples (layer_root, target_layer_root),
   196         where layer_root is the path to the layer root in the source
   198         where layer_root is the path to the layer root in the source
   197         configuration and target_layer_root the one in the target
   199         configuration and target_layer_root the one in the target
   198         configuration.
   200         configuration.
   199     @param merge_policy: The used merge policy.
   201     @param merge_policy: The used merge policy.
       
   202     @param find_pattern: Layers found with this pattern will be used from 
       
   203         the source configuration. If the configuration project has a root
       
   204         configuration which has the same ctr code as the source config,
       
   205         the other layers are taken from the found root config.
   200     """
   206     """
   201     target_root = get_active_root_if_necessary(target_project, target_config, 'target')
   207     target_root = get_active_root_if_necessary(target_project, target_config, 'target')
   202     source_root = get_active_root_if_necessary(source_project, source_config, 'source')
   208     source_root = get_active_root_if_necessary(source_project, source_config, 'source')
   203     
   209     
   204     print "Target config:  %s" % target_root
   210     print "Target config:  %s" % target_root
   207     try:
   213     try:
   208         source_config = source_project.get_configuration(source_root)
   214         source_config = source_project.get_configuration(source_root)
   209     except exceptions.NotFound:
   215     except exceptions.NotFound:
   210         raise MergeFailedException("Configuration root '%s' not found in source project" % source_root)
   216         raise MergeFailedException("Configuration root '%s' not found in source project" % source_root)
   211     
   217     
   212     
   218 
       
   219     def get_matching_config_in_target_project(target_prj, src_config):
       
   220         
       
   221         def get_based_on_ctr(meta):
       
   222             if meta:
       
   223                 for prop in meta.array:
       
   224                     if 'name' in prop.attrs and 'value' in prop.attrs:
       
   225                         name = prop.attrs['name']
       
   226                         if name == 'based_on_ctr':
       
   227                             ctr_codes = prop.attrs['value'].split(',')
       
   228                             return [ctr.strip() for ctr in ctr_codes]
       
   229             return []
       
   230         
       
   231         root_configs = target_prj.list_configurations()
       
   232         based_on_ctr_s = sorted(get_based_on_ctr(src_config.meta))
       
   233         for c in root_configs:
       
   234             based_on_ctr_c = sorted(get_based_on_ctr(target_prj.get_configuration(c).meta))
       
   235             if based_on_ctr_c and based_on_ctr_s:
       
   236                 # if only one ctr code specified in source config, try to find root config that has that code
       
   237                 # (and maybe some others)
       
   238                 if len(based_on_ctr_s) == 1:
       
   239                     if based_on_ctr_s[0] in based_on_ctr_c:
       
   240                         return c
       
   241                 # otherwise try to find a config that has all the same ctr codes
       
   242                 elif based_on_ctr_c == based_on_ctr_s:
       
   243                     return c
       
   244         return None
       
   245         
       
   246         
   213     # Create or get the target configuration root
   247     # Create or get the target configuration root
   214     try:
   248     try:
   215         target_config = target_project.get_configuration(target_root)
   249         target_config = target_project.get_configuration(target_root)
   216     except exceptions.NotFound:
   250     except exceptions.NotFound:
   217         logger.info('Creating new root configuration %s' % (target_config))
   251         logger.info('Creating new root configuration %s' % (target_config))
   218         target_config  = target_project.create_configuration(target_config)
   252         target_config  = target_project.create_configuration(target_config)
   219         for sourcelayer_path in source_config.list_configurations():
   253         # try to find a matching configuration in target project (based_on_ctr)
   220             sourcelayer = source_config.get_configuration(sourcelayer_path)
   254         cmp_config_in_target_prj = get_matching_config_in_target_project(target_project, source_config)
   221             sourcelayer_path = sourcelayer.path
   255         #cmp_config_in_target_prj = None
   222             if target_config.get_storage().is_resource(sourcelayer.path):
   256         if cmp_config_in_target_prj:
   223                 logger.info('Including layer %s to root %s' % (sourcelayer_path, target_config.path))
   257             logger.info('Found root %s with the same ctr code(s) from target project.' % cmp_config_in_target_prj)
   224                 target_config.include_configuration(sourcelayer_path)
   258             cmp_configurations = target_project.get_configuration(cmp_config_in_target_prj).list_configurations()
   225             else:
   259             p = re.compile(find_pattern)
   226                 logger.info('Creating new layer %s to root %s' % (sourcelayer_path, target_config.path))
   260             for cmp_layer_path in cmp_configurations:
   227                 target_config.create_configuration(sourcelayer_path)
   261                 if not p.search(cmp_layer_path):
       
   262                     if target_config.get_storage().is_resource(cmp_layer_path):
       
   263                         logger.info('Including layer %s to root %s' % (cmp_layer_path, target_config.path))
       
   264                         target_config.include_configuration(cmp_layer_path)
       
   265                     else:
       
   266                         logger.info('Creating new layer %s to root %s' % (cmp_layer_path, target_config.path))
       
   267                         target_config.create_configuration(cmp_layer_path)
       
   268         
       
   269             for sourcelayer_path in source_config.list_configurations():
       
   270                 sourcelayer = source_config.get_configuration(sourcelayer_path)
       
   271                 sourcelayer_path = sourcelayer.path
       
   272                 if p.search(sourcelayer_path):
       
   273                     if target_config.get_storage().is_resource(sourcelayer.path):
       
   274                         logger.info('Including layer %s to root %s' % (sourcelayer_path, target_config.path))
       
   275                         target_config.include_configuration(sourcelayer_path)
       
   276                     else:
       
   277                         logger.info('Creating new layer %s to root %s' % (sourcelayer_path, target_config.path))
       
   278                         target_config.create_configuration(sourcelayer_path)
       
   279         else:
       
   280             for sourcelayer_path in source_config.list_configurations():
       
   281                 sourcelayer = source_config.get_configuration(sourcelayer_path)
       
   282                 sourcelayer_path = sourcelayer.path
       
   283                 if target_config.get_storage().is_resource(sourcelayer.path):
       
   284                     logger.info('Including layer %s to root %s' % (sourcelayer_path, target_config.path))
       
   285                     target_config.include_configuration(sourcelayer_path)
       
   286                 else:
       
   287                     logger.info('Creating new layer %s to root %s' % (sourcelayer_path, target_config.path))
       
   288                     target_config.create_configuration(sourcelayer_path)
   228     
   289     
   229     # Collect a correctly sorted list of all layer paths to merge
   290     # Collect a correctly sorted list of all layer paths to merge
   230     layers_to_merge = layer_finder_func(source_config, target_config)
   291     layers_to_merge = layer_finder_func(source_config, target_config)
   231     
   292     
   232     print "Merging %d layer(s)..." % len(layers_to_merge)
   293     print "Merging %d layer(s)..." % len(layers_to_merge)