configurationengine/source/scripts/tests/unittest_generate.py
changeset 3 e7e0ae78773e
parent 0 2e8eeb919028
--- a/configurationengine/source/scripts/tests/unittest_generate.py	Fri Mar 12 08:30:17 2010 +0200
+++ b/configurationengine/source/scripts/tests/unittest_generate.py	Tue Aug 10 14:29:28 2010 +0300
@@ -17,8 +17,9 @@
 ## 
 # @author Teemu Rytkonen
 
-import sys, os, shutil, unittest
-import __init__
+import os, unittest
+import tempfile
+
 from testautomation.base_testcase import BaseTestCase
 from testautomation import zip_dir
 from scripttest_common import get_cmd
@@ -29,11 +30,10 @@
 rootconf = 'root3.confml'
 
 class TestGenerate(BaseTestCase):
-
     def test_get_help(self):
         cmd = '%s -h' % get_cmd('generate')
         out = self.run_command(cmd)
-        lines = out.split('\r\n')
+        lines = out.split(os.linesep)
         self.assertTrue('Options:' in lines)
         self.assertTrue('  Generate options:' in lines)
 
@@ -46,7 +46,39 @@
         self.assert_exists_and_contains_something(OUTPUT_DIR)
         
         self.assert_not_modified(testproject)
-    
+            
+    def test_generate_output_file_from_script(self):
+        testproject = os.path.join(ROOT_PATH, 'testdata/generate/impl_container/project')
+        self.set_modification_reference_time(testproject)
+        OUTPUT_DIR = os.path.join(ROOT_PATH, 'temp/output')
+        self.remove_if_exists(OUTPUT_DIR)
+        LOGFILE = os.path.join(OUTPUT_DIR, 'cone_temp.log')
+        cmd = '%s -p "%s" -c "%s" -o "%s" --log-file "%s"' % (get_cmd('generate'),
+                                                                          testproject,
+                                                                          'base_root.confml',
+                                                                          OUTPUT_DIR,
+                                                                          LOGFILE)
+        out = self.run_command(cmd)
+
+        self.assertEquals(True, os.path.isfile(os.path.join(OUTPUT_DIR, 'output_test.txt')))
+        self.assert_not_modified(testproject)
+
+    def test_generate_with_absolute_path(self):
+        self.set_modification_reference_time(testproject)
+        tempdir = os.path.join(tempfile.gettempdir(), 'cone_output')
+        (drive,OUTPUT_DIR) = os.path.splitdrive(os.path.abspath(tempdir))
+        LOGFILE = os.path.join(OUTPUT_DIR, 'cone_temp.log')
+        self.remove_if_exists(OUTPUT_DIR)
+        cmd = '%s -p "%s" -c "%s" -o "%s" --log-file "%s"' % (get_cmd('generate'),
+                                                            testproject,
+                                                            rootconf,
+                                                            OUTPUT_DIR,
+                                                            LOGFILE)
+        out = self.run_command(cmd)
+        self.assert_exists_and_contains_something(OUTPUT_DIR)
+        self.assertTrue(os.path.exists(LOGFILE))
+        self.assert_not_modified(testproject)
+
     def test_generate_with_report(self):
         self.set_modification_reference_time(testproject)
         OUTPUT_DIR  = os.path.join(ROOT_PATH, 'temp/gen2/output')
@@ -108,8 +140,43 @@
             report_file   = 'temp/gen7/report.csv',
             template_path = os.path.join(ROOT_PATH,'test_template/template2.csv'))
 
+    def test_generate_with_errors_in_project(self):
+        project = os.path.join(ROOT_PATH, 'testdata/generate/error_test_project')
+        
+        OUTPUT_DIR  = os.path.join(ROOT_PATH, 'temp/gen_err/output')
+        REPORT_FILE = os.path.join(ROOT_PATH, 'temp/gen_err/report.html')
+        LOG_FILE = os.path.join(ROOT_PATH, 'temp/gen_err/cone.log')
+        self.remove_if_exists([OUTPUT_DIR, REPORT_FILE, LOG_FILE])
+        cmd = '%s -p "%s" -c root.confml -o "%s" -r "%s" --log-file "%s"' % (get_cmd('generate'),project, OUTPUT_DIR, REPORT_FILE, LOG_FILE)
+        out = self.run_command(cmd)
+        
+        # Check that output and report are generated even though
+        # there are errors in the project
+        self.assert_exists_and_contains_something(OUTPUT_DIR)
+        self.assert_exists_and_contains_something(REPORT_FILE)
+        self.assert_exists_and_contains_something(LOG_FILE)
+        
+        # Check that the errors are shown in the log correctly
+        self.assert_file_contains(LOG_FILE,
+            ['''ERROR   : cone.rules Exception in get_refs() of relation ConfigureRelation(ref='layer1/implml/rules_with_errors.implml', lineno=11): Expression is None''',
+             '''ERROR   : cone Error executing rule ConfigureRelation(ref='layer1/implml/rules_with_errors.implml', lineno=11): ParseException: Syntax error: " configures ${TempFeature.Int} = 6000"''',
+             '''ERROR   : cone Error executing rule ConfigureRelation(ref='layer1/implml/rules_with_errors.implml', lineno=12): ParseException: Syntax error: "True configures "'''])
+        
+        # Check that the errors are shown in the report correctly
+        self.assert_file_contains(REPORT_FILE, data=[],
+            regexes=[r'Exception:\s*layer1/implml/rules_with_errors.implml:11',
+                     r'Exception:\s*layer1/implml/rules_with_errors.implml:12'])
+        
+        # Check from the output that the other rules were successfully
+        # executed
+        self.assert_file_contains(
+            os.path.join(OUTPUT_DIR, 'content/rules_with_errors_test.txt'),
+            ['TempFeature.String:  testing and more testing',
+            'TempFeature.Int:     501',
+            'TempFeature.Real:    1.75',
+            'TempFeature.Boolean: True'])
+
 class TestGenerateAllImplsOnLastLayer(BaseTestCase):
-    
     def _prepare_workdir(self, workdir):
         workdir = os.path.join(ROOT_PATH, workdir)
         self.recreate_dir(workdir)
@@ -176,13 +243,12 @@
             self.assert_dir_contents_equal('output', EXPECTED_DIR, ['.svn'])
             
             # Check that output has also been generated to the overridden output root directory
-            self.assert_exists_and_contains_something('overridden_output/output_rootdir_test.txt')
-            self.assert_exists_and_contains_something('overridden_output/test_subdir/output_rootdir_test.txt')
+            #self.assert_exists_and_contains_something('overridden_output/output_rootdir_test.txt')
+            #self.assert_exists_and_contains_something('overridden_output/test_subdir/output_rootdir_test.txt')
         finally:
             os.chdir(orig_workdir)
 
 class TestGenerationImplFilteringByTags(BaseTestCase):
-    
     def test_no_tag_filtering(self):
         self._run_tag_filtering_test(
             name     = 'no_filter',
@@ -264,6 +330,7 @@
         self.remove_if_exists(OUTPUT)
         
         cmd = '%s -p "%s" --output "%s" --log-file="%s" %s' % (get_cmd('generate'), PROJECT, OUTPUT, LOG, filter)
+        #print cmd
         self.run_command(cmd)
         
         self.assert_exists_and_contains_something(OUTPUT)
@@ -273,5 +340,198 @@
         
         self.assertEquals(expected_files, actual_files)
 
+class TestGenerationImplFilteringByLayers(BaseTestCase):
+    def test_filter_by_last_layer(self):
+        self._run_layer_filtering_test(
+            name     = 'll1',
+            filter   = '--layer -1',
+            expected = ['layer3'])
+    
+    def test_filter_by_two_last_layers(self):
+        self._run_layer_filtering_test(
+            name     = 'll2',
+            filter   = '--layer -1 --layer 2',
+            expected = ['layer2', 'layer3'])
+    
+    def test_filter_by_regex_1(self):
+        self._run_layer_filtering_test(
+            name     = 'r1',
+            filter   = '--layer-regex layer[13]',
+            expected = ['layer1', 'layer3'])
+    
+    def test_filter_by_regex_2(self):
+        self._run_layer_filtering_test(
+            name     = 'r2',
+            filter   = '--layer-regex [12]/root.confml',
+            expected = ['layer1', 'layer2'])
+    
+    def test_filter_by_regex_3(self):
+        self._run_layer_filtering_test(
+            name     = 'r3',
+            filter   = '--layer-regex layer1 --layer-regex layer3',
+            expected = ['layer1', 'layer3'])
+    
+    def test_filter_by_wildcard(self):
+        self._run_layer_filtering_test(
+            name     = 'w',
+            filter   = '--layer-wildcard *layer*',
+            expected = ['layer1', 'layer2', 'layer3'])
+    
+    def _run_layer_filtering_test(self, name, filter, expected):
+        PROJECT = os.path.join(ROOT_PATH, 'testdata/generate/layer_filtering_project')
+        
+        OUTPUT_ROOT = os.path.join(ROOT_PATH, 'temp/gen_lf/', name)
+        OUTPUT      = os.path.join(OUTPUT_ROOT, 'out')
+        LOG         = os.path.join(OUTPUT_ROOT, 'cone.log')
+        self.remove_if_exists(OUTPUT)
+        
+        cmd = '%s -p "%s" --output "%s" --log-file="%s" %s' % (get_cmd('generate'), PROJECT, OUTPUT, LOG, filter)
+        #print cmd
+        self.run_command(cmd)
+        
+        self.assert_exists_and_contains_something(OUTPUT)
+        
+        expected_files = sorted([x + '.txt' for x in expected])
+        actual_files = sorted(os.listdir(OUTPUT))
+        
+        # Ignore the rule output txt files
+        for f in ('rule_test_v2.txt', 'rule_test_v3.txt'):
+            if f in actual_files: del actual_files[actual_files.index(f)]
+        self.assertEquals(expected_files, actual_files)
+        
+        # Check that the correct rules have been executed
+        expected_str = ' ' + ' '.join(sorted(expected)) + ' x'
+        self.assert_file_content_equals(os.path.join(OUTPUT, 'rule_test_v2.txt'), expected_str)
+        self.assert_file_content_equals(os.path.join(OUTPUT, 'rule_test_v3.txt'), expected_str)
+
+class TestGenerateInvalidParameters(BaseTestCase):
+    PROJECT = os.path.join(ROOT_PATH, 'testdata/generate/layer_filtering_project')
+    
+    def _run_test(self, args, expected_msg):
+        if not isinstance(args, basestring):
+            args = ' '.join(args)
+        
+        cmd = get_cmd('generate') + ' ' + args
+        # Note: The following run_command() should really expect the
+        #       return code 2, but for some reason when running from the
+        #       standalone test set, the return value is 0 for some cases
+        #       (specifically, the ones that don't use parser.error() to
+        #       exit the program)
+        out = self.run_command(cmd, expected_return_code = None)
+        
+        self.assertTrue(expected_msg in out,
+                        "Expected message '%s' not in output ('%s')" % (expected_msg, out))
+    
+    def test_invalid_layer_index_1(self):
+        self._run_test(
+            '-p "%s" --layer -1 --layer foobar' % self.PROJECT,
+            "option --layer: invalid integer value: 'foobar'")
+    
+    def test_invalid_layer_index_2(self):
+        self._run_test(
+            '-p "%s" --layer -1 --layer 7' % self.PROJECT,
+            'Invalid layer index: 7')
+    
+    def test_no_matching_layer_for_regex(self):
+        self._run_test(
+            '-p "%s" --layer-regex foo' % self.PROJECT,
+            'No layers matched by layer patterns')
+    
+    def test_no_matching_layer_for_wildcard(self):
+        self._run_test(
+            '-p "%s" --layer-wildcard foo' % self.PROJECT,
+            'No layers matched by layer patterns')
+
+class TestGenerateImplContainer(BaseTestCase):
+    def _run_test(self, root, args):
+        PROJECT = os.path.join(ROOT_PATH, 'testdata/generate/impl_container/project')
+        EXPECTED = os.path.join(ROOT_PATH, 'testdata/generate/impl_container/expected', root)
+        
+        OUTPUT_ROOT = os.path.join(ROOT_PATH, 'temp/gen_ic/', root)
+        OUTPUT      = os.path.join(OUTPUT_ROOT, 'out')
+        LOG         = os.path.join(OUTPUT_ROOT, 'cone.log')
+        self.remove_if_exists(OUTPUT)
+        
+        cmd = '%s -p "%s" -c %s --output "%s" --log-file="%s" %s' % (get_cmd('generate'), PROJECT, root, OUTPUT, LOG, args)
+        #print cmd
+        self.run_command(cmd)
+        
+        self.assert_dir_contents_equal(EXPECTED, OUTPUT, ['.svn'])
+    
+    def test_implcontainer_with_triggering_rule_and_templateml(self):
+        self._run_test(
+            root = 'data_root.confml',
+            args = '--layer -1')
+
+class TestGenerateSetTempvarValue(BaseTestCase):
+    def test_set_tempvar_value_from_cmdline(self):
+        PROJECT = os.path.join(ROOT_PATH, 'generation_test_project')
+        
+        OUTPUT_ROOT = os.path.join(ROOT_PATH, 'temp/gen_tvs/')
+        OUTPUT      = os.path.join(OUTPUT_ROOT, 'out')
+        LOG         = os.path.join(OUTPUT_ROOT, 'cone.log')
+        self.remove_if_exists(OUTPUT)
+        
+        cmd = ['%(cone_cmd)s',
+               '-p "%(project)s"',
+               '-c root.confml',
+               '--output "%(output)s"',
+               '--log-file="%(log_file)s"',
+               '--impl simple_tempvar',
+               '--set "TempFeature.String=testing from cmdline"',
+               '--set "TempFeature.Int=8090"',
+               '--set "TempFeature.Real=-5.75"',]
+        cmd = ' '.join(cmd) % {'cone_cmd':  get_cmd('generate'),
+                               'project':   PROJECT,
+                               'output':    OUTPUT,
+                               'log_file':  LOG}
+        #print cmd
+        self.run_command(cmd)
+        
+        self.assert_file_contains(
+            os.path.join(OUTPUT, 'content', 'simple_tempvars_test.txt'),
+            ['TempFeature.String:  testing from cmdline and more testing',
+             'TempFeature.Int:     8091',
+             'TempFeature.Real:    -5.5'])
+
+class TestGenerateWhatOutput(BaseTestCase):
+    PROJECT = os.path.join(ROOT_PATH, 'generation_test_project')
+    OUTPUT_ROOT = os.path.join(ROOT_PATH, 'temp/gen_wop')
+    OUTPUT      = os.path.join(OUTPUT_ROOT, 'out')
+    LOG         = os.path.join(OUTPUT_ROOT, 'cone.log')
+    WHAT_FILE   = os.path.join(OUTPUT_ROOT, 'what_output.txt')
+    CMP_FILE    = os.path.join(PROJECT, 'what_output.txt')
+    
+    def test_write_what_out(self):        
+        self.remove_if_exists(self.OUTPUT)
+        
+        cmd = ['%(cone_cmd)s',
+               '-p "%(project)s"',
+               '-c root.confml',
+               '--what="%(what_file)s"',
+               '--output "%(output)s"',
+               '--log-file="%(log_file)s"',
+               '--all-layers',]
+        cmd = ' '.join(cmd) % {'cone_cmd':      get_cmd('generate'),
+                               'project':       self.PROJECT,
+                               'what_file':     self.WHAT_FILE,
+                               'output':        self.OUTPUT,
+                               'log_file':      self.LOG}
+        self.run_command(cmd)
+        
+        cmp_what_out_fh = open(self.CMP_FILE, 'r')
+        cmp_files = []
+        try: cmp_files = cmp_what_out_fh.readlines()
+        finally: cmp_what_out_fh.close()
+            
+        self.assert_exists_and_contains_something(self.WHAT_FILE)
+        self.assert_file_contains(self.WHAT_FILE, [self._flip(c.strip()) for c in cmp_files])
+        
+    def _flip(self, path):
+        newpath= path.replace('\\', os.sep)
+        newpath = newpath.replace('/', os.sep)
+        return newpath
+        
+
 if __name__ == '__main__':
-      unittest.main()
+    unittest.main()