Rules / GL086
GL086 Script line that YAML parses as a mapping
Severity: error
OWASP: CICD-SEC-7 – Insecure System Configuration
CWE: CWE-710 – Improper Adherence to Coding Standards
Risk
In YAML, a plain (unquoted) scalar that contains : (colon and space) is a key–value pair. A script line such as
- curl -H "Authorization: Bearer $DEPLOY_TOKEN" https://hooks.example.com/deploy
is read as the mapping {'curl -H "Authorization': 'Bearer $DEPLOY_TOKEN" https://hooks.example.com/deploy'}, not as a command. Double quotes around an argument don't help, because the line itself starts unquoted.
GitLab accepts the file on push and rejects it only when it creates the pipeline, with script config should be a string or a nested array of strings, which doesn't point at the colon. Until then, the line is no command at all, and static checks that read script lines, glsec's own included, don't see what it would do.
What glsec checks
Every item of script:, before_script:, after_script: and hooks:pre_get_sources_script:, in jobs, under default: and at the top level, including items of nested lists. An item that is a mapping is reported at its line.
Trigger example
deploy:
script:
- curl -H "Authorization: Bearer $DEPLOY_TOKEN" "https://hooks.example.com/deploy"
Safe alternatives
Quote the whole line:
deploy:
script:
- 'curl -H "Authorization: Bearer $DEPLOY_TOKEN" "https://hooks.example.com/deploy"'
Use a block scalar:
deploy:
script:
- |
curl -H "Authorization: Bearer $DEPLOY_TOKEN" "https://hooks.example.com/deploy"
Not flagged
- A colon without a following space, as in
echo key:valueorhttps://example.com:8443/. - Lines quoted as a whole, and block scalars (
|,>). run:steps, whosescript:is a single string.
See also
- GL025: user-controlled variables in URLs, which a line read as a mapping hides from glsec
Documentation for glsec 1.24.0. Source of this page · Rule implementation