Lambda Configuration Parameters
The tutorial suite's Advanced Configuration Parameters group contains the Lambda Selector and Lambda Multi-Selector tests covered in this chapter. Their Lambda Configuration Parameters obtain selectable values from callbacks at run-configuration time. Unlike the fixed choices introduced in the Basic Configuration Parameters group, these fields can retrieve current options from external or changing sources. This chapter covers single-value and multi-value Lambda selectors.
Lambda Selector Parameter
Earlier Maze tests require a manually downloaded application and the folder containing its executable. This test replaces that setup with a version selector. Selecting a Maze app release from GitHub downloads the matching binary in the background or reuses its cached copy.
Selecting a value
Select the button at the right of Maze App Version to open its dialog. Leave the filter empty
to request every available release, or enter part of a tag such as v3, then select
Fetch. The returned release tags populate the drop-down:
Choose one version and select OK to assign its tag to the test configuration:
Fetching again replaces the available choices with the callback's latest result while preserving the current selection when that value is still available.
Defining a dynamic selector
Source directory:
orcraft-test-suite-tutorial/test_group_advanced_configuration_parameters/test_lambda_selector_parameter/
A regular OrcraftConfigField.Select
receives its choices through options when the configuration class is defined.
OrcraftConfigField.SelectLambda
instead receives an options_lambda callback that the controller invokes when options are requested. This mechanism
supports values obtained from external or changing sources.
The test developer declares a SelectLambda field in the test's configuration class and assigns
its provider callback through options_lambda:
maze_app_version = OrcraftConfigField.SelectLambda(
default="",
label="Maze App Version",
input_placeholder="Filter versions (e.g. v3)",
button_text="Fetch",
options_lambda=lambda text: fetch_maze_app_release_versions(text),
layout=OrcraftConfigField.Layout.NewRow,
)
The field starts empty. input_placeholder describes the optional filter accepted by the callback,
while button_text labels the action that invokes it - both are listed with the other
common config field options. The lambda receives the text entered in the
dialog and returns the values supplied by fetch_maze_app_release_versions.
Supplying dynamic options
The test developer implements the option-provider function separately from the configuration field. The function may read from any source appropriate to the test. In this tutorial, the provider calls a shared GitHub helper that requests the Maze app releases, excludes drafts, and returns the release tags as a tuple. When filter text is present, the provider returns only tags containing that text:
def fetch_github_release_versions(owner: str, repo: str, filter_text: str = "") -> tuple[str, ...]:
url = f"https://api.github.com/repos/{owner}/{repo}/releases"
request = Request(url, headers=_gh_headers())
try:
with urlopen(request, timeout=8) as response:
releases = json.loads(response.read().decode("utf-8"))
except Exception:
return tuple()
versions = [release["tag_name"] for release in releases if not release.get("draft")]
query = filter_text.strip().lower()
if query:
versions = [version for version in versions if query in version.lower()]
return tuple(versions)
def fetch_maze_app_release_versions(filter_text: str = "") -> tuple[str, ...]:
return fetch_github_release_versions(MAZE_APP_OWNER, MAZE_APP_REPO, filter_text)
The constants passed by the wrapper identify the GMCoreAI/orcraft-maze-app repository. Keeping
the repository-specific wrapper separate allows the generic helper to serve other GitHub-backed selectors.
orcraft-test-suite-tutorial/common/github_repo_access.py
Reading the selected value
def _run_case(self, case: OrcraftTestCase):
maze_app = MazeApp.from_release(
self.config.maze_app_version,
self.config.command,
force=self.config.force_redownload,
)
maze_app.run()
return case.result
At run time, the selected release tag is passed to MazeApp.from_release. The helper downloads the
matching binary for the current platform, or reuses its cached copy unless
Re-download (ignore cached binary) is enabled, then runs the selected command.
Lambda Multi-Selector Parameter
Lambda Multi-Selector Parameter follows the same principle but supports several values from the callback. This test selects multiple Maze app releases and runs the same command against every selected version.
Selecting multiple values
Open Maze App Versions and select Fetch, as in the single-value selector. The same callback returns the available release tags, while this dialog displays a checkbox beside each option. Select each version to include, then select OK:
The selected tags are stored together in the Maze App Versions field:
When the test runs, each selected release is downloaded in the background or loaded from the cache. This workflow eliminates manual binary downloads and folder-list configuration.
Defining a dynamic multi-selector
The implementation differs from the single-value selector in two respects: the configuration uses
MultiSelectLambda with a tuple
default, and the test iterates over the selected values.
Source directory:
orcraft-test-suite-tutorial/test_group_advanced_configuration_parameters/test_lambda_multi_selector_parameter/
maze_app_versions = OrcraftConfigField.MultiSelectLambda(
default=(),
label="Maze App Versions",
input_placeholder="Filter versions (e.g. v3)",
button_text="Fetch",
options_lambda=lambda text: fetch_maze_app_release_versions(text),
required=True,
layout=OrcraftConfigField.Layout.NewRow,
)
required=True prevents the test from running until at least one version is selected. The field
reuses the same fetch_maze_app_release_versions provider shown in
Supplying dynamic options. The callback only supplies
the available choices; the field type determines whether the user can select one value or several.
Reading multiple selected values
def _run_case(self, case: OrcraftTestCase):
for tag in self.config.maze_app_versions:
maze_app = MazeApp.from_release(
tag,
self.config.command,
force=self.config.force_redownload,
)
maze_app.run()
return case.result
The configuration value is a tuple of selected tags. _run_case loops over it, resolves each
release through MazeApp.from_release, and runs the configured command once per version.
After defining callback-driven configuration choices, continue to Matrix and Cases to generate test cases from combinations of configuration values and access their dimension values at run time.