Skip to content

Commit f058a58

Browse files
committed
Add switch for running Sonobuoy tests in parallel
Signed-off-by: Matthias Büchse <matthias.buechse@alasca.cloud>
1 parent faee80f commit f058a58

File tree

5 files changed

+29
-5
lines changed

5 files changed

+29
-5
lines changed

Tests/README.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -49,6 +49,8 @@ Install KaaS-specific requirements:
4949
pip install -r kaas/requirements.txt
5050
```
5151

52+
Additionally, Sonobuoy must be installed and in your PATH environment variable.
53+
5254
Given a kubeconfig file `path/to/kubeconfig.yaml`, run
5355

5456
```shell
@@ -58,6 +60,10 @@ Given a kubeconfig file `path/to/kubeconfig.yaml`, run
5860
Replace `SUBJECT` with an arbitrary, but meaningful subject name. Also, please note that the check
5961
will always use the `current-context` of the kubeconfig and will fail if it isn't set.
6062

63+
Note: Sonobuoy checks (such as CNCF k8s conformance) are known to run for multiple hours (during which
64+
you won't see feedback). If you want to save wall-time by running the sonobuoy checks in parallel,
65+
simply add `-a execution_mode=parallel` to the command-line.
66+
6167
A report in YAML format will be created.
6268

6369
Additionally, the directory `sono-results` will be generated. It contains a JUnit XML file:

Tests/kaas/sonobuoy_handler/run_sonobuoy.py

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,8 +21,13 @@ def cli():
2121
@click.option("-r", "--result_dir_name", "result_dir_name", type=str, default="sonobuoy_results", help="directory name to store results at",)
2222
@click.option("-c", "--check", "check_name", type=str, default="sonobuoy_executor", help="this MUST be the same name as the id in 'scs-compatible-kaas.yaml'",)
2323
@click.option("--scs-sonobuoy-config", "scs_sonobuoy_config_yaml", type=click.Path(exists=True), default="kaas/sonobuoy-config.yaml", help="Configuration for Sonobuoy (yaml format)")
24+
@click.option('--execution-mode', 'mode', type=click.Choice(('serial', 'parallel')), default='serial')
2425
@click.option("-a", "--arg", "args", multiple=True)
25-
def sonobuoy_run(kubeconfig, result_dir_name, check_name, scs_sonobuoy_config_yaml, args):
26+
def sonobuoy_run(kubeconfig, result_dir_name, check_name, scs_sonobuoy_config_yaml, mode, args):
27+
if mode == 'parallel':
28+
# This is merely a shortcut to simplify commandline in scs-compatible-kaas.yaml
29+
# For more on parallel execution, see https://github.com/vmware-tanzu/sonobuoy/issues/1435
30+
args.append('--e2e-parallel=true')
2631
sonobuoy_handler = SonobuoyHandler(check_name, kubeconfig, result_dir_name, scs_sonobuoy_config_yaml, args)
2732
sys.exit(sonobuoy_handler.run())
2833

Tests/scs-compatible-kaas.yaml

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,9 +9,10 @@ variables:
99
# working directory for the subject under test
1010
# (note that we consider each kubernetes branch a test subject of its own)
1111
- kubeconfig
12+
- execution_mode: serial # alternatively: parallel
1213
scripts:
1314
- executable: ./kaas/sonobuoy_handler/run_sonobuoy.py
14-
args: run -k {kubeconfig} --scs-sonobuoy-config kaas/scs-sonobuoy-config.yaml -r {subject_root}/sono-results-e2e -c 'cncf-k8s-conformance' -a '--mode=certified-conformance'
15+
args: run -k {kubeconfig} --scs-sonobuoy-config kaas/scs-sonobuoy-config.yaml -r {subject_root}/sono-results-e2e -c 'cncf-k8s-conformance' -a '--mode=certified-conformance' --execution-mode {execution_mode}
1516
#~ args: -k {kubeconfig} -r {subject_root}/sono-results -c 'cncf-k8s-conformance' -a '--plugin-env e2e.E2E_DRYRUN=true'
1617
testcases:
1718
- id: cncf-k8s-conformance
@@ -31,7 +32,7 @@ scripts:
3132
description: Must fulfill all requirements of scs-0214-v2.
3233
url: https://docs.scs.community/standards/scs-0214-v2-k8s-node-distribution#decision
3334
- executable: ./kaas/sonobuoy_handler/run_sonobuoy.py
34-
args: run -k {kubeconfig} --scs-sonobuoy-config kaas/scs-sonobuoy-config.yaml -r {subject_root}/sono-results-0219 -c 'kaas-networking-check' -a '--e2e-focus "NetworkPolicy"'
35+
args: run -k {kubeconfig} --scs-sonobuoy-config kaas/scs-sonobuoy-config.yaml -r {subject_root}/sono-results-0219 -c 'kaas-networking-check' -a '--e2e-focus "NetworkPolicy"' --execution-mode {execution_mode}
3536
testcases:
3637
- id: kaas-networking-check
3738
description: Must fulfill all requirements of scs-0219-v1.

Tests/scs-compliance-check.py

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -302,7 +302,8 @@ def main(argv):
302302
raise RuntimeError("You need pass --subject=SUBJECT.")
303303
with open(config.arg0, "r", encoding="UTF-8") as specfile:
304304
spec = load_spec(yaml.load(specfile, Loader=yaml.SafeLoader))
305-
missing_vars = [v for v in spec.get("variables", ()) if v not in config.assignment]
305+
assignment = {**spec['var_defaults'], **config.assignment}
306+
missing_vars = [v for v in spec.get("variables", ()) if v not in assignment]
306307
if missing_vars:
307308
raise RuntimeError(f"Missing variable assignments (via -a) for: {', '.join(missing_vars)}")
308309
if "prerequisite" in spec:
@@ -317,7 +318,7 @@ def main(argv):
317318
if not versions:
318319
raise RuntimeError(f"No valid version found for {config.checkdate}")
319320
check_cwd = os.path.dirname(config.arg0) or os.getcwd()
320-
runner = CheckRunner(check_cwd, config.assignment, verbosity=config.verbose and 2 or not config.quiet)
321+
runner = CheckRunner(check_cwd, assignment, verbosity=config.verbose and 2 or not config.quiet)
321322
title, partial = spec['name'], False
322323
if config.sections:
323324
title += f" [sections: {', '.join(config.sections)}]"

Tests/scs_cert_lib.py

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -108,6 +108,17 @@ def _resolve_spec(spec: dict):
108108
for vname in entry['versions']:
109109
# trigger KeyError
110110
_ = version_lookup[vname]
111+
# step 5. unify variables declaration (the list may contain strings as well as singleton dicts)
112+
variables = []
113+
defaults = {}
114+
for var_decl in spec.get('variables', ()):
115+
if isinstance(var_decl, dict):
116+
defaults.update(var_decl)
117+
if isinstance(var_decl, str):
118+
variables.append(var_decl)
119+
variables.extend(defaults)
120+
spec['variables'] = variables
121+
spec['var_defaults'] = defaults
111122

112123

113124
def load_spec(document: dict) -> dict:

0 commit comments

Comments
 (0)