The build runs no command this repository forbids
commands/forbidden-invocation@v1
No command the build executed matched the executable and the arguments this guardrail was given to look for.
| Id | commands/forbidden-invocation |
| Version | v1 |
| Category | commands |
| Default severity | error |
| Interpreter | python3 |
| Timeout | 30 seconds |
| Violations tolerated | 0 |
| Collects | commands |
Collectors
This guardrail gathers nothing itself. It depends on the collectors below, which the CLI runs once per build before any check, and reads what they found out of GUARDRAIL_FACTS. A collector that collects nothing skips this guardrail rather than failing it.
| Collector | Gathers | Inputs it is given |
|---|---|---|
commands | Every command the build executed, read from the session a running buildnote monitor records on the runner. Gathering is dynamic rather than static: this is what the job actually ran, not what a pipeline file says it would run. | none |
The inputs above are this guardrail's own, passed straight through. Configuring one in buildnote.json changes what is collected, and two guardrails configured the same way share the one collection.
Configuration
{
"guardrails": {
"failOn": "error",
"checks": [
{
"use": "commands/forbidden-invocation@v1",
"severity": "error",
"with": {
"command": "",
"arguments": "",
"match": "any",
"reason": ""
},
"exemptions": []
}
]
}
}Inputs
| Input | Description | Default | Environment variable |
|---|---|---|---|
command | Comma separated executable names, any one of which is the command to look for, matched on the file name of every token of the recorded line, so /usr/local/bin/terraform and npx terraform both count and so does a line that merely names it, such as grep terraform Makefile. | `` | GUARDRAIL_INPUT_COMMAND |
arguments | Comma separated arguments that make an invocation a violation, each matched against the tokens of the command line by equality, by the <argument>=<value> form of it, and as a glob, so -Dskip.tests=* reads a value the rule does not name. Naming none makes every invocation of the command a violation. | `` | GUARDRAIL_INPUT_ARGUMENTS |
match | any reports an invocation carrying one of the arguments, all reports one carrying every one of them. | any | GUARDRAIL_INPUT_MATCH |
reason | Why this repository forbids the invocation, reported as the violation's message in place of the default wording. | `` | GUARDRAIL_INPUT_REASON |
How to fix
Name the executable and the arguments that make an invocation a violation, and the build is held to it from the next run:
{
"guardrails": {
"checks": [
{
"use": "commands/forbidden-invocation@v1",
"with": {
"command": "terraform,tofu",
"arguments": "apply,-auto-approve",
"match": "all",
"reason": "Terraform is applied from the deploy pipeline rather than from a build"
}
}
]
}
}One entry is one rule. List the guardrail again with different inputs for the next rule, and each run reports its own verdict.
When the invocation reported is one the build is meant to make, take it out of the rule rather than out of the pipeline: narrow arguments to the form that is actually dangerous, or drop the entry. A rule nobody can satisfy is turned off within a week.
What is read is what the build ran, recorded by buildnote monitor, not what a pipeline file says it would run, so a command reached through a wrapper script or a package runner is reported the same as one written into the job. The command line is the process's argument vector joined by spaces and its original quoting is gone, and the name is looked for in every token of it: an argument written inside a quoted string reads exactly like an argument of the command, and a line naming the command as a word of its own, such as grep curl Dockerfile, reads like an invocation of it. Both are reported rather than guessed away, and the evidence is the recorded line, which says which of the two happened.