diff --git a/easybuild/framework/easyconfig/templates.py b/easybuild/framework/easyconfig/templates.py index fccdd58817..36be6a56ea 100644 --- a/easybuild/framework/easyconfig/templates.py +++ b/easybuild/framework/easyconfig/templates.py @@ -50,9 +50,12 @@ 'nameletter': 'First letter of software name', 'toolchain_name': 'Toolchain name', 'toolchain_version': 'Toolchain version', + 'version_major_minor_patch': "Major.Minor.Patch version", 'version_major_minor': "Major.Minor version", 'version_major': 'Major version', + 'version_minor_patch': 'Minor.Patch version', 'version_minor': 'Minor version', + 'version_patch': 'Patch version', } # derived from EasyConfig._config TEMPLATE_NAMES_CONFIG = [ @@ -204,9 +207,12 @@ 'r_short_ver': 'rshortver', 'r_ver': 'rver', 'toolchain_ver': 'toolchain_version', + 'ver_maj_min_patch': 'version_major_minor_patch', 'ver_maj_min': 'version_major_minor', 'ver_maj': 'version_major', + 'ver_min_patch': 'version_minor_patch', 'ver_min': 'version_minor', + 'ver_patch': 'version_patch', 'version_prefix': 'versionprefix', 'version_suffix': 'versionsuffix', } @@ -343,11 +349,16 @@ def template_constant_dict(config, ignore=None, toolchain=None): minor = version[1] template_values['version_minor'] = minor template_values['version_major_minor'] = '.'.join([major, minor]) + if len(version) > 2: + patch = version[2] + template_values['version_patch'] = patch + template_values['version_minor_patch'] = '.'.join([minor, patch]) + template_values['version_major_minor_patch'] = '.'.join([major, minor, patch]) except IndexError: # if there is no minor version, skip it pass # only go through this once - ignore.extend(['version_major', 'version_minor', 'version_major_minor']) + ignore.extend(name for name in TEMPLATE_NAMES_EASYCONFIG if name.startswith('version_')) elif name.endswith('letter'): # parse first letters diff --git a/test/framework/easyconfig.py b/test/framework/easyconfig.py index 7a07eab449..627741469b 100644 --- a/test/framework/easyconfig.py +++ b/test/framework/easyconfig.py @@ -566,15 +566,16 @@ def test_extensions_templates(self): # bogus, but useful to check whether this get resolved 'exts_default_options = {"source_urls": [PYPI_SOURCE]}', 'exts_list = [', - ' ("toy", "0.0", {', + ' ("toy", "0.0.1", {', # %(name)s and %(version_major_minor)s should be resolved using name/version of extension (not parent) # %(pymajver)s should get resolved because Python is listed as a (runtime) dep # %(versionsuffix)s should get resolved with value of parent ' "source_tmpl": "%(name)s-%(version_major_minor)s-py%(pymajver)s%(versionsuffix)s.tar.gz",', - ' "patches": ["%(name)s-%(version)s_fix-silly-typo-in-printf-statement.patch"],', + ' "patches": ["%(name)s-%(version_major_minor)s_fix-silly-typo-in-printf-statement.patch"],', # use hacky prebuildopts that is picked up by 'EB_Toy' easyblock, to check whether templates are resolved - ' "prebuildopts": "gcc -O2 %(name)s.c -o toy-%(version)s &&' + - ' mv toy-%(version)s toy # echo installdir is %(installdir)s #",', + ' "prebuildopts": "gcc -O2 %(name)s.c -o toy-%(version_minor_patch)s &&' + + ' mv toy-%(version_minor_patch)s toy # echo installdir is %(installdir)s #",', + ' "postbuildopts": "echo postbuild step for %(name)s-%(version)s",', ' }),', ']', ]) @@ -597,16 +598,15 @@ def test_extensions_templates(self): # check whether template values were resolved correctly in Extension instances that were created/used toy_ext = eb.ext_instances[0] self.assertEqual(os.path.basename(toy_ext.src), 'toy-0.0-py3-test.tar.gz') - patches = [] - for patch in toy_ext.patches: - patches.append(patch['path']) + patches = [patch['path'] for patch in toy_ext.patches] self.assertEqual(patches, [os.path.join(self.test_prefix, toy_patch_fn)]) # define actual installation dir pi_installdir = os.path.join(self.test_installpath, 'software', 'pi', '3.14-test') - expected_prebuildopts = 'gcc -O2 toy.c -o toy-0.0 && mv toy-0.0 toy # echo installdir is %s #' % pi_installdir + expected_prebuildopts = 'gcc -O2 toy.c -o toy-0.1 && mv toy-0.1 toy # echo installdir is %s #' % pi_installdir expected = { 'patches': ['toy-0.0_fix-silly-typo-in-printf-statement.patch'], 'prebuildopts': expected_prebuildopts, + 'postbuildopts': "echo postbuild step for toy-0.0.1", 'source_tmpl': 'toy-0.0-py3-test.tar.gz', 'source_urls': ['https://pypi.python.org/packages/source/t/toy'], } @@ -3723,7 +3723,7 @@ def test_template_constant_dict(self): # also check result of template_constant_dict when dict representing extension is passed ext_dict = { 'name': 'foo', - 'version': '1.2.3', + 'version': '1.2.3.42', 'options': { 'source_urls': ['https://example.com'], 'source_tmpl': '%(name)s-%(version)s.tar.gz', @@ -3744,13 +3744,27 @@ def test_template_constant_dict(self): 'rpath_enabled': rpath, 'software_commit': '', 'sysroot': '', - 'version': '1.2.3', + 'version': '1.2.3.42', 'version_major': '1', 'version_major_minor': '1.2', - 'version_minor': '2' + 'version_major_minor_patch': '1.2.3', + 'version_minor': '2', + 'version_minor_patch': '2.3', + 'version_patch': '3', } self.assertEqual(res, expected) + # No patch version makes the templates undefined + ext_dict['version'] = '1.2' + res = template_constant_dict(ext_dict) + res.pop('arch') + + del expected['version_major_minor_patch'] + del expected['version_minor_patch'] + del expected['version_patch'] + expected['version'] = '1.2' + self.assertEqual(res, expected) + def test_parse_deps_templates(self): """Test whether handling of templates defined by dependencies is done correctly.""" test_ecs = os.path.join(os.path.dirname(os.path.abspath(__file__)), 'easyconfigs', 'test_ecs')