package-installs: allow when filter to be a list

Allow the "when:" statements to be a list of values, which are
effectively anded together to filter the package install.

Change-Id: Ia6f10741fa6be24b11d6991c8a6b6e07951ff68d
This commit is contained in:
Ian Wienand 2020-05-12 13:00:27 +10:00
parent 9080d04923
commit 138d3f9b81
4 changed files with 81 additions and 27 deletions

View File

@ -93,6 +93,9 @@ packages), you can use something like::
other_package: other_package:
when: DIB_FEATURE_FLAG!=0 when: DIB_FEATURE_FLAG!=0
You can also use a list of items in the ``when`` statement, which will
be effectively combined with *and*.
DEPRECATED: Adding a file under your elements pre-install.d, install.d, or DEPRECATED: Adding a file under your elements pre-install.d, install.d, or
post-install.d directories called package-installs-<element-name> will cause post-install.d directories called package-installs-<element-name> will cause
the list of packages in that file to be installed at the beginning of the the list of packages in that file to be installed at the beginning of the

View File

@ -61,7 +61,7 @@ def _valid_for_arch(pkg_name, arch, not_arch):
return not _is_arch_in_list(not_arch) return not _is_arch_in_list(not_arch)
def _when(statement): def _when(statements):
'''evaulate a when: statement '''evaulate a when: statement
Evaluate statements of the form Evaluate statements of the form
@ -74,38 +74,48 @@ def _when(statement):
''' '''
# No statement means install # No statement means install
if statement is None: if statements is None:
return True return True
# FOO = BAR if not isinstance(statements, list):
# var op val statements = [statements]
match = re.match(
r"(?P<var>[\w]+)(\s*)(?P<op>=|!=)(\s*)(?P<val>.*)", statement)
if not match:
print("Malformed when line: <%s>" % statement)
sys.exit(1)
match = match.groupdict()
var = match['var']
op = match['op']
val = match['val']
if var not in os.environ: result = []
raise RuntimeError("The variable <%s> is not set" % var)
logger.debug("when eval %s%s%s against <%s>" % for s in statements:
(var, op, val, os.environ[var])) # FOO = BAR
# var op val
match = re.match(
r"(?P<var>[\w]+)(\s*)(?P<op>=|!=)(\s*)(?P<val>.*)", s)
if not match:
print("Malformed when line: <%s>" % s)
sys.exit(1)
match = match.groupdict()
var = match['var']
op = match['op']
val = match['val']
if op == '=': if var not in os.environ:
if val == os.environ[var]: raise RuntimeError("The variable <%s> is not set" % var)
return True
elif op == '!=':
if val != os.environ[var]:
return True
else:
print("Malformed when op: %s" % op)
sys.exit(1)
return False logger.debug("when eval %s%s%s against <%s>" %
(var, op, val, os.environ[var]))
if op == '=':
if val == os.environ[var]:
result.append(True)
continue
elif op == '!=':
if val != os.environ[var]:
result.append(True)
continue
else:
print("Malformed when op: %s" % op)
sys.exit(1)
result.append(False)
return all(result)
def collect_data(data, objs, element_name): def collect_data(data, objs, element_name):

View File

@ -138,3 +138,39 @@ class TestPackageInstall(base.BaseTestCase):
self.assertRaises(RuntimeError, installs_squash.collect_data, self.assertRaises(RuntimeError, installs_squash.collect_data,
self.final_dict, objs, 'test_element') self.final_dict, objs, 'test_element')
@mock.patch.object(os, 'environ',
dict(
DIB_A_FEATURE='1',
DIB_B_FEATURE='1',
DIB_C_FEATURE='1',
**os.environ))
def test_skip_when_list(self):
'''Exercise the when flag with lists'''
objs = {
'not_skipped_package': {
'when': [
'DIB_A_FEATURE=1',
'DIB_B_FEATURE=1',
'DIB_C_FEATURE=1'
]
},
'skipped_package': {
'when': [
'DIB_A_FEATURE=1',
'DIB_B_FEATURE=0',
'DIB_C_FEATURE=1',
]
},
}
result = installs_squash.collect_data(
self.final_dict, objs, 'test_element')
expected = {
'install.d': {
'install': [('not_skipped_package', 'test_element')]
}
}
self.assertThat(result, IsMatchingInstallList(expected))

View File

@ -0,0 +1,5 @@
---
features:
- |
The ``package-installs`` element can now take a list value for the
``when`` environment filter.