diff --git a/doc/configuration.rst b/doc/configuration.rst index 717d1551..149bf6b1 100644 --- a/doc/configuration.rst +++ b/doc/configuration.rst @@ -187,32 +187,34 @@ aborted. Options ------- +There a couple common format specifiers available for both the options: + * compose_id + * release_short + * version + * date + * respin + * type + * type_suffix + * label + * label_major_version + * variant + * arch + * disc_type + **image_name_format** [optional] (*str*) -- Python's format string to serve as template for image names This format will be used for all phases generating images. Currently that means ``createiso``, ``live_images`` and ``buildinstall``. - Available keys are: - * compose_id - * variant - * arch - * disc_type + Available extra keys are: * disc_num * suffix - * release_short - * version **image_volid_formats** [optional] (*list*) -- A list of format strings for generating volume id. - The available keys are: - * compose_id - * variant - * arch - * disc_type - * release_short - * version + The extra available keys are: * base_product_short * base_product_version diff --git a/pungi/compose.py b/pungi/compose.py index 53375070..49adf27c 100644 --- a/pungi/compose.py +++ b/pungi/compose.py @@ -249,6 +249,25 @@ class Compose(kobo.log.LoggingBase): return return open(path, "r").read().strip() + def get_format_substs(self, **kwargs): + """Return a dict of basic format substitutions. + + Any kwargs will be added as well. + """ + substs = { + 'compose_id': self.compose_id, + 'release_short': self.ci_base.release.short, + 'version': self.ci_base.release.version, + 'date': self.compose_date, + 'respin': self.compose_respin, + 'type': self.compose_type, + 'type_suffix': self.compose_type_suffix, + 'label': self.compose_label, + 'label_major_version': self.compose_label_major_version, + } + substs.update(kwargs) + return substs + def get_image_name(self, arch, variant, disc_type='dvd', disc_num=1, suffix='.iso', format=None): """Create a filename for image with given parameters. @@ -268,22 +287,19 @@ class Compose(kobo.log.LoggingBase): else: disc_num = "" - compose_id = self.ci_base[variant.uid].compose_id if variant.type == "layered-product": variant_uid = variant.parent.uid else: variant_uid = variant.uid - args = { - 'compose_id': compose_id, - 'variant': variant_uid, - 'arch': arch, - 'disc_type': disc_type, - 'disc_num': disc_num, - 'suffix': suffix, - 'release_short': self.ci_base.release.short, - 'version': self.ci_base.release.version, - } - return format % args + args = self.get_format_substs(variant=variant_uid, + arch=arch, + disc_type=disc_type, + disc_num=disc_num, + suffix=suffix) + try: + return format % args + except KeyError as err: + raise RuntimeError('Failed to create image name: unknown format element: %s' % err.message) def can_fail(self, variant, arch, deliverable): """Figure out if deliverable can fail on variant.arch. diff --git a/pungi/util.py b/pungi/util.py index 6828ae71..9a849feb 100644 --- a/pungi/util.py +++ b/pungi/util.py @@ -350,16 +350,16 @@ def get_volid(compose, arch, variant=None, escape_spaces=False, disc_type=False) for i in all_products: if not variant_uid and "%(variant)s" in i: continue - volid = i % { - 'compose_id': compose.compose_id, - 'variant': variant_uid, - 'arch': arch, - 'disc_type': disc_type or '', - 'release_short': release_short, - 'version': release_version, - 'base_product_short': base_product_short, - 'base_product_version': base_product_version, - } + try: + volid = i % compose.get_format_substs(variant=variant_uid, + release_short=release_short, + version=release_version, + arch=arch, + disc_type=disc_type or '', + base_product_short=base_product_short, + base_product_version=base_product_version) + except KeyError as err: + raise RuntimeError('Failed to create volume id: unknown format element: %s' % err.message) volid = _apply_substitutions(compose, volid) if len(volid) <= 32: break diff --git a/tests/test_compose.py b/tests/test_compose.py index b3149c28..a23bf31f 100755 --- a/tests/test_compose.py +++ b/tests/test_compose.py @@ -40,6 +40,34 @@ class ComposeTestCase(unittest.TestCase): self.assertFalse(compose.can_fail(None, 'x86_64', 'live')) self.assertTrue(compose.can_fail(None, 'i386', 'live')) + @mock.patch('pungi.compose.ComposeInfo') + def test_get_image_name(self, ci): + conf = {} + variant = mock.Mock(uid='Server', type='variant') + ci.return_value.compose.respin = 2 + ci.return_value.compose.id = 'compose_id' + ci.return_value.compose.date = '20160107' + ci.return_value.compose.type = 'nightly' + ci.return_value.compose.type_suffix = '.n' + ci.return_value.compose.label = 'RC-1.0' + ci.return_value.compose.label_major_version = '1' + + ci.return_value.release.version = '3.0' + ci.return_value.release.short = 'rel_short' + + compose = Compose(conf, self.tmp_dir) + + keys = ['arch', 'compose_id', 'date', 'disc_num', 'disc_type', + 'label', 'label_major_version', 'release_short', 'respin', + 'suffix', 'type', 'type_suffix', 'variant', 'version'] + format = '-'.join(['%(' + k + ')s' for k in keys]) + name = compose.get_image_name('x86_64', variant, format=format, + disc_num=7, disc_type='live', suffix='.iso') + + self.assertEqual(name, '-'.join(['x86_64', 'compose_id', '20160107', '7', 'live', + 'RC-1.0', '1', 'rel_short', '2', '.iso', 'nightly', + '.n', 'Server', '3.0'])) + if __name__ == "__main__": unittest.main() diff --git a/tests/test_util.py b/tests/test_util.py index c15013d7..e2cc0871 100755 --- a/tests/test_util.py +++ b/tests/test_util.py @@ -5,9 +5,12 @@ import mock import os import sys import unittest +import tempfile +import shutil sys.path.insert(0, os.path.join(os.path.dirname(__file__), "..")) +from pungi import compose from pungi import util @@ -80,5 +83,46 @@ class TestGetVariantData(unittest.TestCase): self.assertItemsEqual(result, []) +class TestVolumeIdGenerator(unittest.TestCase): + def setUp(self): + self.tmp_dir = tempfile.mkdtemp() + + def tearDown(self): + shutil.rmtree(self.tmp_dir) + + @mock.patch('pungi.compose.ComposeInfo') + def test_get_volid(self, ci): + all_keys = [ + (['arch', 'compose_id', 'date', 'disc_type'], 'x86_64-compose_id-20160107-'), + (['label', 'label_major_version', 'release_short', 'respin'], 'RC-1.0-1-rel_short2-2'), + (['type', 'type_suffix', 'variant', 'version'], 'nightly-.n-Server-6.0') + ] + for keys, expected in all_keys: + format = '-'.join(['%(' + k + ')s' for k in keys]) + conf = { + 'release_short': 'rel_short2', + 'release_version': '6.0', + 'release_is_layered': False, + 'image_volid_formats': [format] + } + variant = mock.Mock(uid='Server', type='variant') + ci.return_value.compose.respin = 2 + ci.return_value.compose.id = 'compose_id' + ci.return_value.compose.date = '20160107' + ci.return_value.compose.type = 'nightly' + ci.return_value.compose.type_suffix = '.n' + ci.return_value.compose.label = 'RC-1.0' + ci.return_value.compose.label_major_version = '1' + + ci.return_value.release.version = '3.0' + ci.return_value.release.short = 'rel_short' + + c = compose.Compose(conf, self.tmp_dir) + + volid = util.get_volid(c, 'x86_64', variant, escape_spaces=False, disc_type=False) + + self.assertEqual(volid, expected) + + if __name__ == "__main__": unittest.main()