Provider configuration¶
Information
This configuration documentation applies to all provider plugins part of OpenTestFactory. Externally provided provider plugins may or may not support this configuration.
If, as a provider plugin writer you are using the opentf-toolkit, your provider plugin supports this configuration.
A provider plugin configuration file may have a hooks
section. This section, if
defined, specifies steps that will run before and/or after a function is executed.
Those steps are regular steps. For more information about step syntax, see “Workflow syntax for OpenTestFactory orchestrator.”
Hooks defined in a provider plugin configuration file only applies to functions offered by the plugin.
The hooks
section¶
The hooks
section contains an ordered list of hooks. Whenever a function provided
by the plugin is called, those hooks are tested in order. All hooks that match are
applied.
If two or more hooks match, the before
blocks are added in order and the after
blocks are added in reverse order:
before_steps from workflow-defined hooks
before_steps from provider-defined hook 1
before_steps from provider-defined hook 2
steps from function
after_steps from provider-defined hook 2
after_steps from provider-defined hook 1
after_steps from workflow-defined hooks
By default, hooks apply to all functions defined that match the specified events.
It is possible to further limit their scopes by using the if
conditional.
The events
keyword allows to limit the scope of a hook by specifying the function
it applies to. The value is used as follows:
categoryPrefix
: only applies to functions having this prefix.category
: only applies to functions having this category.categoryVersion
: only applies to functions having this version.
If categoryPrefix
is not specified, category
is required.
categoryVersion
can only be specified if at least category
or
categoryPrefix
is specified.
If a hook applies to all categories, use _
as a placeholder, as in:
events:
- category: _
You can use the if
conditional to prevent a hook from applying unless a condition
is met. You can use any supported context and expression to create a conditional.
When you use expressions in an if
conditional, you may omit the expression syntax
(${{ }}
) because the orchestrator automatically evaluates the if
conditional as
an expression. For more information, see “Context and expression syntax for
OpenTestFactory workflows.”
If the expression evaluates to true, the before
and/or after
changes occur
and the following entry, if present, is tested.
If the expression does not evaluate to true, the hook entry is skipped and the following entry, if present, is tested.
There must be a before
block or an after
block, or both. If present, they
specify a non-empty list of steps.
You can define this hooks
section in your configuration file, typically /app/conf/{provider_name}.yaml
(in lower-case) or you can define a {provider_name}_PROVIDER_HOOKS
environment variable (in upper-case)
that refers to a file containing the hooks definition.
Hooks defined via the {provider_name}_PROVIDER_HOOKS
environment variable replace
the ones possibly defined in the provider’s configuration file.
You can find the list of providers part of the reference implementation in the
Providers section. If no specific instructions is provided
in your provider’s documentation, the provider name to use is the ‘short’ name
used as the documentation title (for example, cucumber
for the Cucumber provider
plugin).
Examples¶
In the following examples you will define hooks for the Cucumber plugin.
Defining hooks in the provider configuration file¶
Add a hooks
section in your provider configuration file for the Cucumber plugin
(typically /app/conf/cucumber.yaml
):
apiVersion: opentestfactory.org/v1beta1
kind: ProviderConfig
current-context: ...
contexts:
...
hooks:
- name: my hook
events:
- categoryPrefix: cucumber
category: cucumber
if: ('junit' in inputs.reporters) && (runner.os == 'windows')
before:
- run: echo hello windows
- run: del foobar.html
after:
- run: echo ::attach::foobar.html
- run: cleanup
if: always()
- name: my other hook
events:
- category: _
before:
- uses: actions/delete-file
with:
path: foo/${{ inputs.yada }}/bar
Defining hooks using a separate definition file¶
Alternatively, you can provide a separate file for the hooks definition. This
file can have any name, as long as it is accessible from your plugin and the
CUCUMBER_PROVIDER_HOOKS
environment variable is set to its path:
CUCUMBER_PROVIDER_HOOKS=/app/hooks/cucumber_hooks.yaml
The hooks definition is exactly as above:
hooks:
- name: my hook
events:
- categoryPrefix: cucumber
category: cucumber
if: ('junit' in inputs.reporters) && (runner.os == 'windows')
before:
- run: echo hello windows
- run: del foobar.html
after:
- run: echo ::attach::foobar.html
- run: cleanup
if: always()
- name: my other hook
events:
- category: _
before:
- uses: actions/delete-file
with:
path: foo/${{ inputs.yada }}/bar
Observable effects¶
Assuming the following workflow:
metadata:
name: hooks demo
jobs:
my_job:
runs-on: windows
steps:
- run: echo Hi there
- uses: cucumber/cucumber@v1
with:
reporters: [foo, junit]
- run: echo Bye
my_second_job:
runs-on: windows
steps:
- uses: cucumber/params@v1
The my_job
job will execute the following steps, in order:
- run: echo Hi there
- run: hello windows
- run: del foobar.html
- run: <what cucumber/cucumber does>
- run: echo ::attach::foobar.html
- run: cleanup
If Cucumber returns a non-zero status code, the echo ::attach::
step will
be skipped, but the cleanup
one will run nonetheless, as it includes an
if: always()
clause.
The my_second_job
job will execute the following steps, in order:
- run: <what actions/delete-file does>
- run: <what cucumber/params does>