Salome HOME
sat job: be able to pass global options to a specific command (sat -o ... command)
[tools/sat.git] / commands / compile.py
index 532c88040f0f3272cde69333c760ccb90e721104..9a2d0956c73ebc5dc34f9ca2d9ab79c18c4a7936 100644 (file)
@@ -30,24 +30,27 @@ except NameError:
 # Define all possible option for the compile command :  sat compile <options>
 parser = src.options.Options()
 parser.add_option('p', 'products', 'list2', 'products',
-    _('products to configure. This option can be'
+    _('Optional: products to configure. This option can be'
     ' passed several time to configure several products.'))
 parser.add_option('', 'with_fathers', 'boolean', 'fathers',
-    _("build all necessary products to the given product (KERNEL is build before"
-      " building GUI)."), False)
+    _("Optional: build all necessary products to the given product (KERNEL is "
+      "build before building GUI)."), False)
 parser.add_option('', 'with_children', 'boolean', 'children',
-    _("build all products using the given product (all SMESH plugins are build "
-      "after SMESH)."), False)
+    _("Optional: build all products using the given product (all SMESH plugins"
+      " are build after SMESH)."), False)
 parser.add_option('', 'clean_all', 'boolean', 'clean_all',
-    _("clean BUILD dir and INSTALL dir before building product."), False)
+    _("Optional: clean BUILD dir and INSTALL dir before building product."),
+    False)
 parser.add_option('', 'clean_install', 'boolean', 'clean_install',
-    _("clean INSTALL dir before building product."), False)
+    _("Optional: clean INSTALL dir before building product."), False)
 parser.add_option('', 'make_flags', 'string', 'makeflags',
-    _("add extra options to the 'make' command."))
+    _("Optional: add extra options to the 'make' command."))
 parser.add_option('', 'show', 'boolean', 'no_compile',
-    _("DO NOT COMPILE just show if products are installed or not."), False)
-parser.add_option('', 'stop_first_fail', 'boolean', 'stop_first_fail', _("Stop"
-                    "s the command at first product compilation fail."), False)
+    _("Optional: DO NOT COMPILE just show if products are installed or not."),
+    False)
+parser.add_option('', 'stop_first_fail', 'boolean', 'stop_first_fail', _(
+                  "Optional: Stops the command at first product compilation"
+                  " fail."), False)
 
 def get_products_list(options, cfg, logger):
     '''method that gives the product list with their informations from 
@@ -80,7 +83,6 @@ def get_products_list(options, cfg, logger):
     products_infos = src.product.get_products_infos(products, cfg)
     
     products_infos = [pi for pi in products_infos if not(
-                                     src.product.product_is_native(pi[1]) or 
                                      src.product.product_is_fixed(pi[1]))]
     
     return products_infos
@@ -202,7 +204,7 @@ def sort_products(config, p_infos):
     :param config Config: The global configuration
     :param p_infos list: List of (str, Config) => (product_name, product_info)
     """
-    l_prod_sorted = deepcopy_list(p_infos)
+    l_prod_sorted = src.deepcopy_list(p_infos)
     for prod in p_infos:
         l_fathers = get_recursive_fathers(config,
                                           prod,
@@ -219,21 +221,9 @@ def sort_products(config, p_infos):
                 break
         
     return l_prod_sorted
-       
-def deepcopy_list(input_list):
-    """ Do a deep copy of a list
-    
-    :param input_list List: The list to copy
-    :return: The copy of the list
-    :rtype: List
-    """
-    res = []
-    for elem in input_list:
-        res.append(elem)
-    return res
 
 def extend_with_fathers(config, p_infos):
-    p_infos_res = deepcopy_list(p_infos)
+    p_infos_res = src.deepcopy_list(p_infos)
     for p_name_p_info in p_infos:
         fathers = get_recursive_fathers(config,
                                         p_name_p_info,
@@ -244,7 +234,7 @@ def extend_with_fathers(config, p_infos):
     return p_infos_res
 
 def extend_with_children(config, p_infos):
-    p_infos_res = deepcopy_list(p_infos)
+    p_infos_res = src.deepcopy_list(p_infos)
     for p_name_p_info in p_infos:
         children = get_recursive_children(config,
                                         p_name_p_info,
@@ -301,14 +291,30 @@ def compile_all_products(sat, config, options, products_infos, logger):
         logger.write(header, 3)
         logger.write("\n", 4, False)
         logger.flush()
-        
+
+        # Do nothing if the product is not compilable
+        if ("properties" in p_info and "compilation" in p_info.properties and 
+                                            p_info.properties.compilation == "no"):
+            log_step(logger, header, "ignored")
+            logger.write("\n", 3, False)
+            continue
+
+        # Do nothing if the product is native
+        if src.product.product_is_native(p_info):
+            log_step(logger, header, "native")
+            logger.write("\n", 3, False)
+            continue
+
         # Clean the build and the install directories 
         # if the corresponding options was called
         if options.clean_all:
             log_step(logger, header, "CLEAN BUILD AND INSTALL")
             sat.clean(config.VARS.application + 
                       " --products " + p_name + 
-                      " --build --install", batch=True, verbose=0)
+                      " --build --install",
+                      batch=True,
+                      verbose=0,
+                      logger_add_link = logger)
         
         # Clean the the install directory 
         # if the corresponding option was called
@@ -316,7 +322,10 @@ def compile_all_products(sat, config, options, products_infos, logger):
             log_step(logger, header, "CLEAN INSTALL")
             sat.clean(config.VARS.application + 
                       " --products " + p_name + 
-                      " --install", batch=True, verbose=0)
+                      " --install",
+                      batch=True,
+                      verbose=0,
+                      logger_add_link = logger)
         
         # Check if it was already successfully installed
         if src.product.check_installation(p_info):
@@ -331,6 +340,7 @@ def compile_all_products(sat, config, options, products_infos, logger):
         # Check if the dependencies are installed
         l_depends_not_installed = check_dependencies(config, p_name_info)
         if len(l_depends_not_installed) > 0:
+            log_step(logger, header, "")
             logger.write(src.printcolors.printcError(
                     _("ERROR : the following product(s) is(are) mandatory: ")))
             for prod_name in l_depends_not_installed:
@@ -349,13 +359,18 @@ def compile_all_products(sat, config, options, products_infos, logger):
         
         if res_prod != 0:
             # Clean the install directory if there is any
+            logger.write(_("Cleaning the install directory if there is any\n"),
+                         5)
             sat.clean(config.VARS.application + 
                       " --products " + p_name + 
-                      " --install", batch=True, verbose=0)
+                      " --install",
+                      batch=True,
+                      verbose=0,
+                      logger_add_link = logger)
             res += 1
             
         # Log the result
-        if res > 0:
+        if res_prod > 0:
             logger.write("\r%s%s" % (header, " " * len_end_line), 3)
             logger.write("\r" + header + src.printcolors.printcError("KO ") + error_step)
             logger.write("\n==== %(KO)s in compile of %(name)s \n" %
@@ -399,7 +414,7 @@ def compile_product(sat, p_name_info, config, options, logger, header, len_end):
     # Logging and sat command call for configure step
     len_end_line = len_end
     log_step(logger, header, "CONFIGURE")
-    res_c, __ = sat.configure(config.VARS.application + " --products " + p_name,
+    res_c = sat.configure(config.VARS.application + " --products " + p_name,
                           verbose = 0,
                           logger_add_link = logger)
     log_res_step(logger, res_c)
@@ -424,7 +439,7 @@ def compile_product(sat, p_name_info, config, options, logger, header, len_end):
         # Get the make_flags option if there is any
         if options.makeflags:
             make_arguments += " --option -j" + options.makeflags
-        res_m, __ = sat.make(make_arguments,
+        res_m = sat.make(make_arguments,
                          verbose = 0,
                          logger_add_link = logger)
         log_res_step(logger, res_m)
@@ -435,7 +450,7 @@ def compile_product(sat, p_name_info, config, options, logger, header, len_end):
         else: 
             # Logging and sat command call for make install step
             log_step(logger, header, "MAKE INSTALL")
-            res_mi, __ = sat.makeinstall(config.VARS.application + 
+            res_mi = sat.makeinstall(config.VARS.application + 
                                      " --products " + 
                                      p_name,
                                     verbose = 0,
@@ -444,18 +459,57 @@ def compile_product(sat, p_name_info, config, options, logger, header, len_end):
             log_res_step(logger, res_mi)
             res += res_mi
             
-            if res_m > 0:
+            if res_mi > 0:
                 error_step = "MAKE INSTALL"
 
+    # Check that the install directory exists
+    if res==0 and not(os.path.exists(p_info.install_dir)):
+        res = 1
+        error_step = "NO INSTALL DIR"
+        msg = _("Error: despite the fact that all the steps ended successfully,"
+                " no install directory was found !")
+        logger.write(src.printcolors.printcError(msg), 4)
+        logger.write("\n", 4)
+    
+    # Add the config file corresponding to the dependencies/versions of the 
+    # product that have been successfully compiled
+    if res==0:       
+        logger.write(_("Add the config file in installation directory\n"), 5)
+        add_compile_config_file(p_info, config)
+    
     return res, len_end_line, error_step
 
+def add_compile_config_file(p_info, config):
+    '''Execute the proper configuration command(s) 
+       in the product build directory.
+    
+    :param p_info Config: The specific config of the product
+    :param config Config: The global configuration
+    '''
+    # Create the compile config
+    compile_cfg = src.pyconf.Config()
+    for prod_name in p_info.depend:
+        if prod_name not in compile_cfg:
+            compile_cfg.addMapping(prod_name,
+                                   src.pyconf.Mapping(compile_cfg),
+                                   "")
+        prod_dep_info = src.product.get_product_config(config, prod_name, False)
+        compile_cfg[prod_name] = prod_dep_info.version
+    # Write it in the install directory of the product
+    compile_cfg_path = os.path.join(p_info.install_dir, src.CONFIG_FILENAME)
+    f = open(compile_cfg_path, 'w')
+    compile_cfg.__save__(f)
+    f.close()
+    
 def description():
     '''method that is called when salomeTools is called with --help option.
     
     :return: The text to display for the compile command description.
     :rtype: str
     '''
-    return _("The compile command constructs the products of the application")
+    return _("The compile command constructs the products of the application"
+             "\n\nexample:\nsat compile SALOME-master --products KERNEL,GUI,"
+             "MEDCOUPLING --clean_all")
   
 def run(args, runner, logger):
     '''method that is called when salomeTools is called with compile parameter.
@@ -477,6 +531,20 @@ def run(args, runner, logger):
     # check that the command has been called with an application
     src.check_config_has_application( runner.cfg )
 
+    # Print some informations
+    logger.write(_('Executing the compile commands in the build '
+                                'directories of the products of '
+                                'the application %s\n') % 
+                src.printcolors.printcLabel(runner.cfg.VARS.application), 1)
+    
+    info = [
+            (_("SOURCE directory"),
+             os.path.join(runner.cfg.APPLICATION.workdir, 'SOURCES')),
+            (_("BUILD directory"),
+             os.path.join(runner.cfg.APPLICATION.workdir, 'BUILD'))
+            ]
+    src.print_info(logger, info)
+
     # Get the list of products to treat
     products_infos = get_products_list(options, runner.cfg, logger)
 
@@ -491,19 +559,6 @@ def run(args, runner, logger):
     # Sort the list regarding the dependencies of the products
     products_infos = sort_products(runner.cfg, products_infos)
 
-    # Print some informations
-    logger.write(_('Executing the compile commands in the build '
-                                'directories of the products of '
-                                'the application %s\n') % 
-                src.printcolors.printcLabel(runner.cfg.VARS.application), 1)
-    
-    info = [
-            (_("SOURCE directory"),
-             os.path.join(runner.cfg.APPLICATION.workdir, 'SOURCES')),
-            (_("BUILD directory"),
-             os.path.join(runner.cfg.APPLICATION.workdir, 'BUILD'))
-            ]
-    src.print_info(logger, info)
     
     # Call the function that will loop over all the products and execute
     # the right command(s)
@@ -521,4 +576,7 @@ def run(args, runner, logger):
           'valid_result': nb_products - res,
           'nb_products': nb_products }, 1)    
     
-    return res
\ No newline at end of file
+    code = res
+    if code != 0:
+        code = 1
+    return code
\ No newline at end of file