From d4fa9d7b23336aba3a217311f931a6b3e5ade203 Mon Sep 17 00:00:00 2001 From: David Caro Date: Sun, 19 Apr 2015 21:49:40 +0200 Subject: [PATCH] Added possibility to exclude project combinations Change-Id: I40603f041d33a27d08bf6912b7d9d885a95278fd Signed-off-by: David Caro --- doc/source/definition.rst | 20 ++++ jenkins_jobs/parser.py | 28 ++++++ .../yamlparser/fixtures/template_exclude.xml | 99 +++++++++++++++++++ .../yamlparser/fixtures/template_exclude.yaml | 24 +++++ .../fixtures/template_without_exclude.xml | 99 +++++++++++++++++++ .../fixtures/template_without_exclude.yaml | 32 ++++++ 6 files changed, 302 insertions(+) create mode 100644 tests/yamlparser/fixtures/template_exclude.xml create mode 100644 tests/yamlparser/fixtures/template_exclude.yaml create mode 100644 tests/yamlparser/fixtures/template_without_exclude.xml create mode 100644 tests/yamlparser/fixtures/template_without_exclude.yaml diff --git a/doc/source/definition.rst b/doc/source/definition.rst index ad32496af..7a9f80ff9 100644 --- a/doc/source/definition.rst +++ b/doc/source/definition.rst @@ -121,6 +121,26 @@ additional variables can be specified for project variables. Example: .. literalinclude:: /../../tests/yamlparser/fixtures/templates002.yaml +You can also specify some variable combinations to exclude from the matrix with +the ``exclude`` keyword, to avoid generating jobs for those combinations. You +can specify all the variables of the combination or only a subset, if you +specify a subset, any value of the omited variable will match: + +.. literalinclude:: /../../tests/yamlparser/fixtures/template_exclude.yaml + +The above example will omit the jobs: + + * build-axe1val1-axe2val1-axe3val2 + * build-axe1val1-axe2val2-axe3val1 + * build-axe1val2-axe2val2-axe3val1 + +To achieve the same without the ``exclude`` tag one would have to do something +a bit more complicated, that gets more complicated for each dimension in the +combination, for the previous example, the counterpart would be: + +.. literalinclude:: + /../../tests/yamlparser/fixtures/template_without_exclude.yaml + Job Group ^^^^^^^^^ diff --git a/jenkins_jobs/parser.py b/jenkins_jobs/parser.py index 48b21b58d..5f4abb8b3 100644 --- a/jenkins_jobs/parser.py +++ b/jenkins_jobs/parser.py @@ -46,6 +46,29 @@ def matches(what, glob_patterns): for glob_pattern in glob_patterns) +def combination_matches(combination, match_combinations): + """ + Checks if the given combination is matches for any of the given combination + globs, being those a set of combinations where if a key is missing, it's + considered matching + + (key1=2, key2=3) + + would match the combination match: + (key2=3) + + but not: + (key1=2, key2=2) + """ + for cmatch in match_combinations: + for key, val in combination.items(): + if cmatch.get(key, val) != val: + break + else: + return True + return False + + class YamlParser(object): def __init__(self, config=None, plugins_info=None): self.data = {} @@ -255,6 +278,7 @@ class YamlParser(object): # reject keys that are not useful during yaml expansion for k in ['jobs']: project.pop(k) + excludes = project.pop('exclude', []) for (k, v) in project.items(): tmpk = '{{{0}}}'.format(k) if tmpk not in template_name: @@ -281,6 +305,10 @@ class YamlParser(object): params.update(expanded_values) params = deep_format(params, params) + if combination_matches(params, excludes): + logger.debug('Excluding combination %s', str(params)) + continue + allow_empty_variables = self.config \ and self.config.has_section('job_builder') \ and self.config.has_option( diff --git a/tests/yamlparser/fixtures/template_exclude.xml b/tests/yamlparser/fixtures/template_exclude.xml new file mode 100644 index 000000000..7755e126b --- /dev/null +++ b/tests/yamlparser/fixtures/template_exclude.xml @@ -0,0 +1,99 @@ + + + + <!-- Managed by Jenkins Job Builder --> + false + false + false + false + true + + + + + echo Combination axe1val1:axe2val1:axe3val1 + + + + + + + + + + <!-- Managed by Jenkins Job Builder --> + false + false + false + false + true + + + + + echo Combination axe1val1:axe2val2:axe3val2 + + + + + + + + + + <!-- Managed by Jenkins Job Builder --> + false + false + false + false + true + + + + + echo Combination axe1val2:axe2val1:axe3val1 + + + + + + + + + + <!-- Managed by Jenkins Job Builder --> + false + false + false + false + true + + + + + echo Combination axe1val2:axe2val1:axe3val2 + + + + + + + + + + <!-- Managed by Jenkins Job Builder --> + false + false + false + false + true + + + + + echo Combination axe1val2:axe2val2:axe3val2 + + + + + diff --git a/tests/yamlparser/fixtures/template_exclude.yaml b/tests/yamlparser/fixtures/template_exclude.yaml new file mode 100644 index 000000000..ab0307435 --- /dev/null +++ b/tests/yamlparser/fixtures/template_exclude.yaml @@ -0,0 +1,24 @@ +- project: + name: project-name + axe1: + - axe1val1 + - axe1val2 + axe2: + - axe2val1 + - axe2val2 + axe3: + - axe3val1 + - axe3val2 + exclude: + - axe1: axe1val1 + axe2: axe2val1 + axe3: axe3val2 + - axe2: axe2val2 + axe3: axe3val1 + jobs: + - build-{axe1}-{axe2}-{axe3} + +- job-template: + name: build-{axe1}-{axe2}-{axe3} + builders: + - shell: "echo Combination {axe1}:{axe2}:{axe3}" diff --git a/tests/yamlparser/fixtures/template_without_exclude.xml b/tests/yamlparser/fixtures/template_without_exclude.xml new file mode 100644 index 000000000..7755e126b --- /dev/null +++ b/tests/yamlparser/fixtures/template_without_exclude.xml @@ -0,0 +1,99 @@ + + + + <!-- Managed by Jenkins Job Builder --> + false + false + false + false + true + + + + + echo Combination axe1val1:axe2val1:axe3val1 + + + + + + + + + + <!-- Managed by Jenkins Job Builder --> + false + false + false + false + true + + + + + echo Combination axe1val1:axe2val2:axe3val2 + + + + + + + + + + <!-- Managed by Jenkins Job Builder --> + false + false + false + false + true + + + + + echo Combination axe1val2:axe2val1:axe3val1 + + + + + + + + + + <!-- Managed by Jenkins Job Builder --> + false + false + false + false + true + + + + + echo Combination axe1val2:axe2val1:axe3val2 + + + + + + + + + + <!-- Managed by Jenkins Job Builder --> + false + false + false + false + true + + + + + echo Combination axe1val2:axe2val2:axe3val2 + + + + + diff --git a/tests/yamlparser/fixtures/template_without_exclude.yaml b/tests/yamlparser/fixtures/template_without_exclude.yaml new file mode 100644 index 000000000..a5bcee18c --- /dev/null +++ b/tests/yamlparser/fixtures/template_without_exclude.yaml @@ -0,0 +1,32 @@ +- project: + name: project-name_comb1 + axe1: + - axe1val1 + - axe1val2 + axe2: axe2val1 + axe3: axe3val1 + jobs: + - build-{axe1}-{axe2}-{axe3} + +- project: + name: project-name_comb2 + axe1: + - axe1val1 + - axe1val2 + axe2: axe2val2 + axe3: axe3val2 + jobs: + - build-{axe1}-{axe2}-{axe3} + +- project: + name: project-name_comb3 + axe1: axe1val2 + axe2: axe2val1 + axe3: axe3val2 + jobs: + - build-{axe1}-{axe2}-{axe3} + +- job-template: + name: build-{axe1}-{axe2}-{axe3} + builders: + - shell: "echo Combination {axe1}:{axe2}:{axe3}"