@htekdev/actions-debugger 1.0.58 → 1.0.60
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/errors/permissions-auth/github-token-cross-repo-dispatch-limitation.yml +115 -0
- package/errors/runner-environment/runner-environment-119.yml +98 -0
- package/errors/runner-environment/runner-environment-120.yml +118 -0
- package/errors/runner-environment/runner-environment-121.yml +113 -0
- package/errors/runner-environment/runner-environment-122.yml +134 -0
- package/errors/silent-failures/reusable-workflow-outputs-undeclared-workflow-level.yml +95 -0
- package/errors/triggers/pull-request-target-checkout-base-branch.yml +101 -0
- package/errors/yaml-syntax/composite-action-run-step-missing-shell.yml +93 -0
- package/package.json +1 -1
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
id: permissions-auth-043
|
|
2
|
+
title: 'GITHUB_TOKEN cannot dispatch workflows or events in other repositories'
|
|
3
|
+
category: permissions-auth
|
|
4
|
+
severity: error
|
|
5
|
+
tags:
|
|
6
|
+
- GITHUB_TOKEN
|
|
7
|
+
- repository_dispatch
|
|
8
|
+
- workflow_dispatch
|
|
9
|
+
- cross-repo
|
|
10
|
+
- 404
|
|
11
|
+
- permissions
|
|
12
|
+
patterns:
|
|
13
|
+
- regex: 'Resource not accessible by integration'
|
|
14
|
+
flags: 'i'
|
|
15
|
+
- regex: '404.*dispatches|dispatches.*404'
|
|
16
|
+
flags: 'i'
|
|
17
|
+
- regex: 'HttpError: Not Found'
|
|
18
|
+
flags: 'i'
|
|
19
|
+
error_messages:
|
|
20
|
+
- 'Resource not accessible by integration'
|
|
21
|
+
- 'HttpError: Not Found'
|
|
22
|
+
- '{"message":"Not Found","documentation_url":"https://docs.github.com/rest/repos/repos#create-a-repository-dispatch-event"}'
|
|
23
|
+
- 'RequestError [HttpError]: Not Found'
|
|
24
|
+
root_cause: |
|
|
25
|
+
GITHUB_TOKEN is automatically scoped to the repository where the workflow
|
|
26
|
+
runs. It cannot authenticate to any other repository, regardless of what is
|
|
27
|
+
declared in the workflow's permissions block. The permissions block controls
|
|
28
|
+
only the scopes of the automatically-generated token for the CURRENT repo —
|
|
29
|
+
it has no effect on access to other repositories.
|
|
30
|
+
|
|
31
|
+
Attempts to call the GitHub REST API against a different repository —
|
|
32
|
+
including POST /repos/{owner}/{other-repo}/dispatches (repository_dispatch)
|
|
33
|
+
or POST /repos/{owner}/{other-repo}/actions/workflows/{id}/dispatches
|
|
34
|
+
(workflow_dispatch) — return 404 Not Found. GitHub returns 404 rather than
|
|
35
|
+
403 to avoid leaking information about whether the target repository exists
|
|
36
|
+
or is private.
|
|
37
|
+
|
|
38
|
+
This is a hard authentication boundary enforced by GitHub's token system,
|
|
39
|
+
not a configuration issue. No amount of permissions: adjustments in the
|
|
40
|
+
workflow file can grant the automatic GITHUB_TOKEN cross-repository access.
|
|
41
|
+
|
|
42
|
+
Note: this is distinct from the GITHUB_TOKEN loopback limitation (where
|
|
43
|
+
GITHUB_TOKEN cannot trigger new workflow runs in the SAME repository). This
|
|
44
|
+
error applies to any cross-repository API call.
|
|
45
|
+
fix: |
|
|
46
|
+
Replace GITHUB_TOKEN with a credential that has access to the target
|
|
47
|
+
repository: a Personal Access Token (PAT) with repo scope, or a GitHub App
|
|
48
|
+
installation token scoped to both repositories. Store the credential as an
|
|
49
|
+
encrypted repository or organization secret.
|
|
50
|
+
|
|
51
|
+
GitHub Apps with installation tokens are the recommended approach for
|
|
52
|
+
production cross-repo automation — they provide fine-grained permissions,
|
|
53
|
+
do not depend on a specific user account, and tokens are automatically
|
|
54
|
+
rotated.
|
|
55
|
+
fix_code:
|
|
56
|
+
- language: yaml
|
|
57
|
+
label: 'Use a PAT secret for cross-repo repository_dispatch'
|
|
58
|
+
code: |
|
|
59
|
+
jobs:
|
|
60
|
+
trigger-downstream:
|
|
61
|
+
runs-on: ubuntu-latest
|
|
62
|
+
steps:
|
|
63
|
+
- name: Dispatch event to other repository
|
|
64
|
+
uses: actions/github-script@v7
|
|
65
|
+
with:
|
|
66
|
+
github-token: ${{ secrets.CROSS_REPO_PAT }}
|
|
67
|
+
script: |
|
|
68
|
+
await github.rest.repos.createDispatchEvent({
|
|
69
|
+
owner: 'my-org',
|
|
70
|
+
repo: 'other-repo',
|
|
71
|
+
event_type: 'build-triggered',
|
|
72
|
+
client_payload: {
|
|
73
|
+
ref: context.ref,
|
|
74
|
+
sha: context.sha
|
|
75
|
+
}
|
|
76
|
+
});
|
|
77
|
+
- language: yaml
|
|
78
|
+
label: 'Use a GitHub App installation token for cross-repo workflow dispatch (recommended)'
|
|
79
|
+
code: |
|
|
80
|
+
jobs:
|
|
81
|
+
trigger-downstream:
|
|
82
|
+
runs-on: ubuntu-latest
|
|
83
|
+
steps:
|
|
84
|
+
- name: Generate GitHub App installation token
|
|
85
|
+
id: app-token
|
|
86
|
+
uses: actions/create-github-app-token@v1
|
|
87
|
+
with:
|
|
88
|
+
app-id: ${{ vars.APP_ID }}
|
|
89
|
+
private-key: ${{ secrets.APP_PRIVATE_KEY }}
|
|
90
|
+
owner: my-org
|
|
91
|
+
repositories: other-repo
|
|
92
|
+
|
|
93
|
+
- name: Dispatch workflow in other repository
|
|
94
|
+
uses: actions/github-script@v7
|
|
95
|
+
with:
|
|
96
|
+
github-token: ${{ steps.app-token.outputs.token }}
|
|
97
|
+
script: |
|
|
98
|
+
await github.rest.actions.createWorkflowDispatch({
|
|
99
|
+
owner: 'my-org',
|
|
100
|
+
repo: 'other-repo',
|
|
101
|
+
workflow_id: 'deploy.yml',
|
|
102
|
+
ref: 'main'
|
|
103
|
+
});
|
|
104
|
+
prevention:
|
|
105
|
+
- 'Never use ${{ secrets.GITHUB_TOKEN }} in API calls targeting other repositories — it will always 404'
|
|
106
|
+
- 'Prefer GitHub Apps with installation tokens over PATs for cross-repo automation — scoped, auto-rotating, and not tied to a user account'
|
|
107
|
+
- 'Store cross-repo PATs as organization secrets so they are reusable across multiple source repositories without per-repo duplication'
|
|
108
|
+
- 'When debugging 404 on dispatch endpoints, first check whether the token is GITHUB_TOKEN vs a PAT — this is the most common cause'
|
|
109
|
+
docs:
|
|
110
|
+
- url: 'https://docs.github.com/en/actions/security-for-github-actions/security-guides/automatic-token-authentication#permissions-for-the-github_token'
|
|
111
|
+
label: 'GitHub Docs: Permissions for the GITHUB_TOKEN'
|
|
112
|
+
- url: 'https://docs.github.com/en/apps/creating-github-apps/authenticating-with-a-github-app/making-authenticated-api-requests-with-a-github-app-in-a-github-actions-workflow'
|
|
113
|
+
label: 'GitHub Docs: Authenticating with a GitHub App in GitHub Actions'
|
|
114
|
+
- url: 'https://github.com/orgs/community/discussions/26724'
|
|
115
|
+
label: 'GitHub Community: GITHUB_TOKEN cannot dispatch to another repository'
|
|
@@ -0,0 +1,98 @@
|
|
|
1
|
+
id: runner-environment-119
|
|
2
|
+
title: "ubuntu-24.04 GCC 13 treats implicit function declarations as hard errors in C"
|
|
3
|
+
category: runner-environment
|
|
4
|
+
severity: error
|
|
5
|
+
tags:
|
|
6
|
+
- ubuntu-24
|
|
7
|
+
- gcc-13
|
|
8
|
+
- c-compilation
|
|
9
|
+
- implicit-declaration
|
|
10
|
+
- breaking-change
|
|
11
|
+
- ubuntu-latest
|
|
12
|
+
patterns:
|
|
13
|
+
- regex: 'error: implicit declaration of function'
|
|
14
|
+
flags: 'i'
|
|
15
|
+
- regex: '\[-Wimplicit-function-declaration\]'
|
|
16
|
+
flags: 'i'
|
|
17
|
+
- regex: 'implicit declaration of function .* is invalid in C99'
|
|
18
|
+
flags: 'i'
|
|
19
|
+
- regex: 'cc1: some warnings being treated as errors'
|
|
20
|
+
flags: 'i'
|
|
21
|
+
error_messages:
|
|
22
|
+
- "error: implicit declaration of function 'foo' [-Wimplicit-function-declaration]"
|
|
23
|
+
- "implicit declaration of function 'getline' is invalid in C99 [-Wimplicit-function-declaration]"
|
|
24
|
+
- "cc1: some warnings being treated as errors"
|
|
25
|
+
- "error: 'strdup' undeclared (first use in this function)"
|
|
26
|
+
root_cause: |
|
|
27
|
+
ubuntu-24.04 runners ship with GCC 13.2.0, replacing GCC 11.4.0 on ubuntu-22.04.
|
|
28
|
+
GCC 13 promotes several previously-warning-level diagnostics to hard errors in C
|
|
29
|
+
compilation. The most commonly triggered change is -Wimplicit-function-declaration:
|
|
30
|
+
calling a function without a prior declaration or prototype is now an error, not
|
|
31
|
+
a warning. This matches the requirement in the C99, C11, and C23 standards, but
|
|
32
|
+
was only enforced as a warning in earlier GCC versions.
|
|
33
|
+
|
|
34
|
+
Workflows that compiled successfully on ubuntu-22.04 (GCC 11) now fail on
|
|
35
|
+
ubuntu-24.04 (GCC 13) with "error: implicit declaration of function" even when
|
|
36
|
+
the source code has not changed. Common triggers:
|
|
37
|
+
- Missing #include directives for standard library functions (getline, strtok_r,
|
|
38
|
+
strdup, getaddrinfo, etc.)
|
|
39
|
+
- Using POSIX-only functions without _GNU_SOURCE or _POSIX_C_SOURCE feature macros
|
|
40
|
+
- Legacy C code or vendored dependencies not maintained for C99 compliance
|
|
41
|
+
|
|
42
|
+
Additional GCC 13 diagnostics upgraded from warnings to errors:
|
|
43
|
+
- -Wint-conversion: assigning int where pointer is expected (and vice versa)
|
|
44
|
+
- -Wincompatible-pointer-types: passing incompatible pointer type to a function
|
|
45
|
+
|
|
46
|
+
The ubuntu-latest label resolves to ubuntu-24.04 as of 2025. Workflows that
|
|
47
|
+
previously used ubuntu-latest and relied on GCC 11 behavior are now affected
|
|
48
|
+
even without changing their runner label.
|
|
49
|
+
fix: |
|
|
50
|
+
Preferred fix: correct the source code by adding missing #include directives
|
|
51
|
+
or explicit function prototypes. This is the standards-compliant approach and
|
|
52
|
+
permanently resolves the issue.
|
|
53
|
+
|
|
54
|
+
Temporary suppression: add -Wno-implicit-function-declaration (and optionally
|
|
55
|
+
-Wno-int-conversion, -Wno-incompatible-pointer-types) to CFLAGS in the build
|
|
56
|
+
step. This restores GCC 11 behavior for vendored or unmaintained C code but
|
|
57
|
+
should be treated as a short-term workaround only.
|
|
58
|
+
|
|
59
|
+
Short-term runner pin: use runs-on: ubuntu-22.04 while fixing the source.
|
|
60
|
+
ubuntu-22.04 will eventually be retired from GitHub-hosted runners.
|
|
61
|
+
fix_code:
|
|
62
|
+
- language: yaml
|
|
63
|
+
label: "Add suppression flags to CFLAGS for legacy C code"
|
|
64
|
+
code: |
|
|
65
|
+
jobs:
|
|
66
|
+
build:
|
|
67
|
+
runs-on: ubuntu-24.04
|
|
68
|
+
steps:
|
|
69
|
+
- uses: actions/checkout@v4
|
|
70
|
+
|
|
71
|
+
- name: Build with legacy C compatibility flags
|
|
72
|
+
run: |
|
|
73
|
+
make CFLAGS="-O2 -Wno-implicit-function-declaration \
|
|
74
|
+
-Wno-int-conversion \
|
|
75
|
+
-Wno-incompatible-pointer-types"
|
|
76
|
+
- language: yaml
|
|
77
|
+
label: "Pin to ubuntu-22.04 temporarily while fixing source"
|
|
78
|
+
code: |
|
|
79
|
+
jobs:
|
|
80
|
+
build:
|
|
81
|
+
# TODO: fix implicit declarations then migrate back to ubuntu-24.04
|
|
82
|
+
runs-on: ubuntu-22.04
|
|
83
|
+
steps:
|
|
84
|
+
- uses: actions/checkout@v4
|
|
85
|
+
- run: make
|
|
86
|
+
prevention:
|
|
87
|
+
- "Run builds on ubuntu-24.04 in a matrix alongside ubuntu-22.04 to detect GCC 13 errors before fully migrating"
|
|
88
|
+
- "Add all required #include headers — GCC 13 enforces what the C standard has required since C99"
|
|
89
|
+
- "Use -Wno-error=implicit-function-declaration as a transitional flag rather than disabling the warning entirely"
|
|
90
|
+
- "Audit vendored C libraries for GCC 13 compatibility before upgrading runner images"
|
|
91
|
+
- "Enable -Wall in CI early to surface implicit declaration warnings before they become hard errors"
|
|
92
|
+
docs:
|
|
93
|
+
- url: "https://gcc.gnu.org/gcc-13/porting_to.html"
|
|
94
|
+
label: "GCC 13 porting guide — new errors and behavioral changes"
|
|
95
|
+
- url: "https://github.com/actions/runner-images/blob/main/images/ubuntu/Ubuntu2404-Readme.md"
|
|
96
|
+
label: "ubuntu-24.04 runner image — installed software (GCC 13.2.0)"
|
|
97
|
+
- url: "https://gcc.gnu.org/onlinedocs/gcc/Warning-Options.html"
|
|
98
|
+
label: "GCC warning options — -Wimplicit-function-declaration"
|
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
id: runner-environment-120
|
|
2
|
+
title: "snap install fails on GitHub-hosted runners — snapd daemon not available"
|
|
3
|
+
category: runner-environment
|
|
4
|
+
severity: error
|
|
5
|
+
tags:
|
|
6
|
+
- snap
|
|
7
|
+
- snapd
|
|
8
|
+
- ubuntu
|
|
9
|
+
- package-manager
|
|
10
|
+
- runner-limitation
|
|
11
|
+
- apt-alternative
|
|
12
|
+
patterns:
|
|
13
|
+
- regex: 'snap.*command not found|command not found.*snap'
|
|
14
|
+
flags: 'i'
|
|
15
|
+
- regex: 'cannot communicate with server.*snapd\.sock'
|
|
16
|
+
flags: 'i'
|
|
17
|
+
- regex: 'dial unix /run/snapd\.sock.*no such file or directory'
|
|
18
|
+
flags: 'i'
|
|
19
|
+
- regex: 'error: cannot connect to the snap daemon'
|
|
20
|
+
flags: 'i'
|
|
21
|
+
error_messages:
|
|
22
|
+
- "sudo: snap: command not found"
|
|
23
|
+
- "error: cannot communicate with server: Post \"http://localhost/v2/snaps/...\": dial unix /run/snapd.sock: connect: no such file or directory"
|
|
24
|
+
- "error: cannot connect to the snap daemon"
|
|
25
|
+
- "/bin/sh: 1: snap: not found"
|
|
26
|
+
root_cause: |
|
|
27
|
+
GitHub-hosted runner images (ubuntu-22.04, ubuntu-24.04, and ubuntu-latest) do
|
|
28
|
+
not include the snapd daemon and do not support the snap package manager.
|
|
29
|
+
|
|
30
|
+
Snapd requires a persistent background daemon (snapd.service) and specific kernel
|
|
31
|
+
configuration for confinement (AppArmor profiles, seccomp filters) that is not
|
|
32
|
+
available or not configured in the ephemeral VM environment GitHub uses for
|
|
33
|
+
hosted runners. Even if the snap binary were present, the daemon is not running,
|
|
34
|
+
causing all snap commands to fail at the IPC socket connection step.
|
|
35
|
+
|
|
36
|
+
This limitation surprises developers who routinely use snap packages on local
|
|
37
|
+
Ubuntu workstations and attempt to replicate those install commands in CI.
|
|
38
|
+
Common affected workflows:
|
|
39
|
+
- Installing tools distributed primarily or exclusively via snap (certain IoT,
|
|
40
|
+
embedded, or cross-compile toolchains; some cloud CLI tools)
|
|
41
|
+
- Reproducing local Ubuntu developer setup scripts in CI verbatim
|
|
42
|
+
- CI pipelines for snap packages themselves (snap build requires LXD or snapcraft)
|
|
43
|
+
|
|
44
|
+
The error "cannot communicate with server: dial unix /run/snapd.sock: no such
|
|
45
|
+
file or directory" is deterministic — it fails on every run, not intermittently.
|
|
46
|
+
fix: |
|
|
47
|
+
Replace snap install commands with an equivalent alternative:
|
|
48
|
+
|
|
49
|
+
1. APT: Most tools available as snaps also have apt packages. Check
|
|
50
|
+
packages.ubuntu.com for the apt equivalent (the version may be older).
|
|
51
|
+
|
|
52
|
+
2. Direct binary / official releases: Many developer tools (kubectl, helm,
|
|
53
|
+
terraform, go, etc.) publish standalone binaries on GitHub Releases or
|
|
54
|
+
their official download pages.
|
|
55
|
+
|
|
56
|
+
3. Official setup-* actions: GitHub and tool vendors maintain actions/setup-go,
|
|
57
|
+
azure/setup-kubectl, hashicorp/setup-terraform, etc. that install tools
|
|
58
|
+
cleanly without snap.
|
|
59
|
+
|
|
60
|
+
4. Docker: Run the snap-packaged tool inside a Docker container if no other
|
|
61
|
+
distribution method exists (the snap itself cannot run inside Docker, but
|
|
62
|
+
the underlying tool usually has a Docker image).
|
|
63
|
+
|
|
64
|
+
For snap package development and testing (e.g., snapcraft builds), use a
|
|
65
|
+
self-hosted runner with LXD configured, or the snapcore/action-build action
|
|
66
|
+
which handles the LXD setup automatically.
|
|
67
|
+
fix_code:
|
|
68
|
+
- language: yaml
|
|
69
|
+
label: "Replace snap install with apt or official action"
|
|
70
|
+
code: |
|
|
71
|
+
jobs:
|
|
72
|
+
deploy:
|
|
73
|
+
runs-on: ubuntu-latest
|
|
74
|
+
steps:
|
|
75
|
+
- uses: actions/checkout@v4
|
|
76
|
+
|
|
77
|
+
# Instead of: sudo snap install kubectl --classic
|
|
78
|
+
- name: Set up kubectl (official action)
|
|
79
|
+
uses: azure/setup-kubectl@v4
|
|
80
|
+
with:
|
|
81
|
+
version: 'v1.30.0'
|
|
82
|
+
|
|
83
|
+
# Instead of: sudo snap install terraform
|
|
84
|
+
- name: Set up Terraform (official action)
|
|
85
|
+
uses: hashicorp/setup-terraform@v3
|
|
86
|
+
with:
|
|
87
|
+
terraform_version: "1.9.0"
|
|
88
|
+
|
|
89
|
+
- run: kubectl version --client
|
|
90
|
+
- language: yaml
|
|
91
|
+
label: "Build snap packages with snapcore/action-build (handles LXD)"
|
|
92
|
+
code: |
|
|
93
|
+
jobs:
|
|
94
|
+
snapcraft:
|
|
95
|
+
runs-on: ubuntu-latest
|
|
96
|
+
steps:
|
|
97
|
+
- uses: actions/checkout@v4
|
|
98
|
+
|
|
99
|
+
- name: Build snap
|
|
100
|
+
uses: snapcore/action-build@v1
|
|
101
|
+
|
|
102
|
+
- name: Upload snap artifact
|
|
103
|
+
uses: actions/upload-artifact@v4
|
|
104
|
+
with:
|
|
105
|
+
name: my-snap
|
|
106
|
+
path: '*.snap'
|
|
107
|
+
prevention:
|
|
108
|
+
- "Check the GitHub Actions Marketplace for an official setup-* action before reaching for snap"
|
|
109
|
+
- "Use direct binary downloads from tool vendors' GitHub Releases when no setup-* action exists"
|
|
110
|
+
- "Avoid copying local Ubuntu setup scripts verbatim into CI — apt/brew/direct-download are the CI-safe equivalents"
|
|
111
|
+
- "Self-hosted runners on Ubuntu can have snapd installed if snap packages are genuinely required"
|
|
112
|
+
docs:
|
|
113
|
+
- url: "https://docs.github.com/en/actions/using-github-hosted-runners/using-github-hosted-runners/about-github-hosted-runners#preinstalled-software"
|
|
114
|
+
label: "GitHub Docs — Pre-installed software on GitHub-hosted runners"
|
|
115
|
+
- url: "https://github.com/snapcore/action-build"
|
|
116
|
+
label: "snapcore/action-build — official snap build action (uses LXD)"
|
|
117
|
+
- url: "https://snapcraft.io/docs/build-on-github"
|
|
118
|
+
label: "Snapcraft Docs — Building snaps on GitHub Actions"
|
|
@@ -0,0 +1,113 @@
|
|
|
1
|
+
id: runner-environment-121
|
|
2
|
+
title: "macOS-15 and macOS-26 Apple system Ruby (/usr/bin/ruby 2.6) removed — bare ruby and gem commands fail"
|
|
3
|
+
category: runner-environment
|
|
4
|
+
severity: error
|
|
5
|
+
tags:
|
|
6
|
+
- macos-15
|
|
7
|
+
- macos-26
|
|
8
|
+
- ruby
|
|
9
|
+
- system-ruby
|
|
10
|
+
- gem
|
|
11
|
+
- cocoapods
|
|
12
|
+
- breaking-change
|
|
13
|
+
patterns:
|
|
14
|
+
- regex: '/usr/bin/ruby.*[Nn]o such file|[Nn]o such file.*/usr/bin/ruby'
|
|
15
|
+
flags: 'i'
|
|
16
|
+
- regex: 'ruby: No such file or directory'
|
|
17
|
+
flags: 'i'
|
|
18
|
+
- regex: 'rbenv: version .* is not installed'
|
|
19
|
+
flags: 'i'
|
|
20
|
+
- regex: 'Your Ruby version is .*, but your Gemfile specified'
|
|
21
|
+
flags: 'i'
|
|
22
|
+
error_messages:
|
|
23
|
+
- "/usr/bin/ruby: No such file or directory"
|
|
24
|
+
- "bash: /usr/bin/ruby: No such file or directory"
|
|
25
|
+
- "rbenv: version '2.6.10' is not installed"
|
|
26
|
+
- "Your Ruby version is 3.3.4, but your Gemfile specified ~> 2.6"
|
|
27
|
+
- "[!] CocoaPods requires your terminal to be using UTF-8 encoding. Consider adding the following to ~/.profile: export LANG=en_US.UTF-8"
|
|
28
|
+
root_cause: |
|
|
29
|
+
Apple removed the system Ruby installation (/usr/bin/ruby, version 2.6.10) from
|
|
30
|
+
macOS 15 Sequoia. This Ruby shipped as part of macOS since macOS 10.5 and was
|
|
31
|
+
installed at /usr/bin/ruby via Xcode Command Line Tools. It was used as the
|
|
32
|
+
runtime for Bundler, CocoaPods, Fastlane, and other Ruby-based iOS/macOS build
|
|
33
|
+
tools that shipped their own invocation scripts pointing to /usr/bin/ruby.
|
|
34
|
+
|
|
35
|
+
GitHub-hosted macOS-15 and macOS-26 runner images reflect this Apple change.
|
|
36
|
+
macOS-14 runners still include /usr/bin/ruby 2.6.10. GitHub pre-installs Ruby 3.3
|
|
37
|
+
via rbenv on macOS-15 and macOS-26, but:
|
|
38
|
+
|
|
39
|
+
1. Scripts or Makefiles that explicitly reference /usr/bin/ruby fail immediately
|
|
40
|
+
with "No such file or directory"
|
|
41
|
+
2. Gemfiles pinned to ruby "~> 2.6" fail — pre-installed Ruby is 3.3.x
|
|
42
|
+
3. CocoaPods legacy install scripts (including some older Fastfiles) called
|
|
43
|
+
/usr/bin/ruby directly; those fail on macOS-15 runners
|
|
44
|
+
4. rbenv configurations referencing the Apple system Ruby slot (2.6.10) fail
|
|
45
|
+
with "rbenv: version '2.6.10' is not installed"
|
|
46
|
+
5. brew install ruby may install a different version than expected, and its
|
|
47
|
+
PATH precedence may conflict with rbenv-managed Ruby
|
|
48
|
+
|
|
49
|
+
The macOS-latest label resolves to macOS-15 and eventually macOS-26 as Apple
|
|
50
|
+
releases new macOS versions. Workflows using macOS-latest are affected even
|
|
51
|
+
without changing their runner specification.
|
|
52
|
+
fix: |
|
|
53
|
+
Use the ruby/setup-ruby action to install and pin a specific Ruby version.
|
|
54
|
+
This is the recommended approach for all macOS GitHub Actions workflows and
|
|
55
|
+
works correctly on macOS-14, macOS-15, and macOS-26.
|
|
56
|
+
|
|
57
|
+
For CocoaPods: add a Gemfile with the cocoapods gem and use Bundler
|
|
58
|
+
(bundle exec pod install) instead of calling pod directly. This also gives
|
|
59
|
+
reproducible CocoaPods version pinning across all environments.
|
|
60
|
+
|
|
61
|
+
Search the repository for any hardcoded /usr/bin/ruby references before
|
|
62
|
+
migrating to macOS-15 runners.
|
|
63
|
+
fix_code:
|
|
64
|
+
- language: yaml
|
|
65
|
+
label: "Use ruby/setup-ruby to install and pin Ruby (recommended)"
|
|
66
|
+
code: |
|
|
67
|
+
jobs:
|
|
68
|
+
build:
|
|
69
|
+
runs-on: macos-15
|
|
70
|
+
steps:
|
|
71
|
+
- uses: actions/checkout@v4
|
|
72
|
+
|
|
73
|
+
- name: Set up Ruby
|
|
74
|
+
uses: ruby/setup-ruby@v1
|
|
75
|
+
with:
|
|
76
|
+
ruby-version: '3.3'
|
|
77
|
+
bundler-cache: true # runs bundle install automatically
|
|
78
|
+
|
|
79
|
+
- name: Run tests
|
|
80
|
+
run: bundle exec rspec
|
|
81
|
+
- language: yaml
|
|
82
|
+
label: "CocoaPods via Bundler — replace direct pod invocation"
|
|
83
|
+
code: |
|
|
84
|
+
jobs:
|
|
85
|
+
ios-build:
|
|
86
|
+
runs-on: macos-15
|
|
87
|
+
steps:
|
|
88
|
+
- uses: actions/checkout@v4
|
|
89
|
+
|
|
90
|
+
- uses: ruby/setup-ruby@v1
|
|
91
|
+
with:
|
|
92
|
+
ruby-version: '3.3'
|
|
93
|
+
bundler-cache: true
|
|
94
|
+
|
|
95
|
+
# Gemfile must include: gem 'cocoapods', '~> 1.15'
|
|
96
|
+
- name: Install pods via Bundler
|
|
97
|
+
run: bundle exec pod install
|
|
98
|
+
working-directory: ios/
|
|
99
|
+
prevention:
|
|
100
|
+
- "Never hardcode /usr/bin/ruby — always invoke ruby via PATH after ruby/setup-ruby"
|
|
101
|
+
- "Add ruby/setup-ruby with an explicit ruby-version to every macOS workflow that uses Ruby, Bundler, or CocoaPods"
|
|
102
|
+
- "Pin CocoaPods in a Gemfile and use bundle exec pod install — not the global pod command"
|
|
103
|
+
- "Search CI scripts and Fastfiles for /usr/bin/ruby before migrating to macOS-15 or macOS-26 runners"
|
|
104
|
+
- "Use the macos-15 label explicitly in CI for testing before it becomes the macos-latest default"
|
|
105
|
+
docs:
|
|
106
|
+
- url: "https://github.com/ruby/setup-ruby"
|
|
107
|
+
label: "ruby/setup-ruby action — official Ruby installer for GitHub Actions"
|
|
108
|
+
- url: "https://github.com/actions/runner-images/blob/main/images/macos/macos-15-Readme.md"
|
|
109
|
+
label: "GitHub Actions macOS-15 runner image — installed software"
|
|
110
|
+
- url: "https://guides.cocoapods.org/using/a-gemfile.html"
|
|
111
|
+
label: "CocoaPods — using a Gemfile (Bundler-based installation)"
|
|
112
|
+
- url: "https://www.ruby-lang.org/en/documentation/installation/"
|
|
113
|
+
label: "Ruby installation options — setup-ruby vs system Ruby"
|
|
@@ -0,0 +1,134 @@
|
|
|
1
|
+
id: runner-environment-122
|
|
2
|
+
title: "ubuntu-24.04 cgroup v2 only — Docker containers and JVMs built for cgroup v1 fail"
|
|
3
|
+
category: runner-environment
|
|
4
|
+
severity: error
|
|
5
|
+
tags:
|
|
6
|
+
- ubuntu-24
|
|
7
|
+
- cgroup-v2
|
|
8
|
+
- docker
|
|
9
|
+
- systemd-in-container
|
|
10
|
+
- java
|
|
11
|
+
- kubernetes
|
|
12
|
+
- breaking-change
|
|
13
|
+
patterns:
|
|
14
|
+
- regex: 'cgroup.*v1.*not supported|v1.*cgroup.*not available'
|
|
15
|
+
flags: 'i'
|
|
16
|
+
- regex: 'failed to create.*cgroup|cgroup.*permission denied'
|
|
17
|
+
flags: 'i'
|
|
18
|
+
- regex: 'write.*cgroup.*read-only file system|cgroup.*read.only'
|
|
19
|
+
flags: 'i'
|
|
20
|
+
- regex: 'OCI runtime create failed.*cgroup'
|
|
21
|
+
flags: 'i'
|
|
22
|
+
error_messages:
|
|
23
|
+
- "OCI runtime create failed: cgroup v1 not supported on this system"
|
|
24
|
+
- "Error response from daemon: failed to create shim task: cgroup v1 is not available"
|
|
25
|
+
- "failed to create cgroup: write /sys/fs/cgroup/memory/docker/...: read-only file system"
|
|
26
|
+
- "cannot enter cgroupv2 namespace: invalid argument"
|
|
27
|
+
root_cause: |
|
|
28
|
+
ubuntu-24.04 GitHub-hosted runners use Linux kernel 6.5+ with cgroup v2 (the
|
|
29
|
+
unified hierarchy) exclusively. cgroup v1 subsystems are not mounted and not
|
|
30
|
+
available. ubuntu-22.04 runners supported both cgroup v1 and v2 simultaneously
|
|
31
|
+
(the hybrid mode enabled in the 5.x kernel era), so containers built for v1
|
|
32
|
+
worked without modification.
|
|
33
|
+
|
|
34
|
+
This affects four main workflow categories:
|
|
35
|
+
|
|
36
|
+
1. systemd-in-container testing: Docker images using systemd as PID 1 (Ansible
|
|
37
|
+
role tests, Molecule, infrastructure integration tests) require cgroup v2
|
|
38
|
+
support in the container's systemd version. Images based on older base images
|
|
39
|
+
(Ubuntu 18.04, CentOS 7/8, RHEL 7) with systemd < 248 fail to start because
|
|
40
|
+
their systemd was compiled for the cgroup v1 hierarchy.
|
|
41
|
+
|
|
42
|
+
2. Old JVM containers: JVM releases before JDK 11u16, JDK 17u4, and JDK 19+
|
|
43
|
+
do not correctly detect container memory and CPU limits under cgroup v2.
|
|
44
|
+
These JVMs either crash with OutOfMemoryError (using the host memory limit
|
|
45
|
+
instead of the container limit) or report the wrong available processor count.
|
|
46
|
+
|
|
47
|
+
3. Kubernetes-in-Docker (kind, k3d): older versions of kind (pre-v0.17) and k3d
|
|
48
|
+
fail to initialize cluster nodes due to cgroup v2 incompatibility in the
|
|
49
|
+
bundled containerd or runc version.
|
|
50
|
+
|
|
51
|
+
4. eBPF and networking tools: eBPF programs that attach to cgroup v1 BPF program
|
|
52
|
+
type (BPF_PROG_TYPE_CGROUP_SOCK, etc.) using the v1 subsystem hierarchy fail
|
|
53
|
+
because the v1 cgroup paths (/sys/fs/cgroup/memory/, /sys/fs/cgroup/cpu/)
|
|
54
|
+
are not present.
|
|
55
|
+
|
|
56
|
+
The ubuntu-latest label resolved to ubuntu-24.04 in 2025. Workflows that relied
|
|
57
|
+
on ubuntu-latest and had cgroup v1 dependent containers are now affected.
|
|
58
|
+
fix: |
|
|
59
|
+
1. Update base images to cgroup v2 compatible versions:
|
|
60
|
+
- systemd: use Ubuntu 22.04+ or Debian Bookworm base images (systemd 249+)
|
|
61
|
+
- Java: update to JDK 11.0.16+, JDK 17.0.4+, or JDK 19+ (full cgroup v2 support)
|
|
62
|
+
- kind: use v0.17.0+ which ships containerd 1.7+ with cgroup v2 support
|
|
63
|
+
- k3d: use v5.6.0+
|
|
64
|
+
|
|
65
|
+
2. For systemd containers: mount /sys/fs/cgroup with rw access and use
|
|
66
|
+
--cgroupns=host if the container requires the host cgroup namespace
|
|
67
|
+
|
|
68
|
+
3. Pin to ubuntu-22.04 as a short-term workaround while updating container images.
|
|
69
|
+
ubuntu-22.04 will eventually be retired from GitHub-hosted runners.
|
|
70
|
+
fix_code:
|
|
71
|
+
- language: yaml
|
|
72
|
+
label: "Run systemd containers with cgroup v2 compatible mounts"
|
|
73
|
+
code: |
|
|
74
|
+
jobs:
|
|
75
|
+
ansible-test:
|
|
76
|
+
runs-on: ubuntu-24.04
|
|
77
|
+
steps:
|
|
78
|
+
- uses: actions/checkout@v4
|
|
79
|
+
|
|
80
|
+
- name: Start systemd container (cgroup v2 compatible)
|
|
81
|
+
run: |
|
|
82
|
+
docker run -d \
|
|
83
|
+
--name test-node \
|
|
84
|
+
--cgroupns=host \
|
|
85
|
+
--tmpfs /tmp \
|
|
86
|
+
--tmpfs /run \
|
|
87
|
+
-v /sys/fs/cgroup:/sys/fs/cgroup:rw \
|
|
88
|
+
ubuntu:22.04
|
|
89
|
+
|
|
90
|
+
- name: Run Ansible role test
|
|
91
|
+
run: docker exec test-node ansible-playbook site.yml
|
|
92
|
+
- language: yaml
|
|
93
|
+
label: "Use kind v0.17+ for Kubernetes-in-Docker on ubuntu-24.04"
|
|
94
|
+
code: |
|
|
95
|
+
jobs:
|
|
96
|
+
k8s-test:
|
|
97
|
+
runs-on: ubuntu-24.04
|
|
98
|
+
steps:
|
|
99
|
+
- uses: actions/checkout@v4
|
|
100
|
+
|
|
101
|
+
- name: Create kind cluster (v0.17+ required for cgroup v2)
|
|
102
|
+
uses: helm/kind-action@v1
|
|
103
|
+
with:
|
|
104
|
+
version: v0.23.0
|
|
105
|
+
cluster_name: test-cluster
|
|
106
|
+
|
|
107
|
+
- run: kubectl cluster-info
|
|
108
|
+
- language: yaml
|
|
109
|
+
label: "Pin to ubuntu-22.04 temporarily for cgroup v1 dependent workflows"
|
|
110
|
+
code: |
|
|
111
|
+
jobs:
|
|
112
|
+
integration-test:
|
|
113
|
+
# TODO: update container images to cgroup v2 compatible versions
|
|
114
|
+
runs-on: ubuntu-22.04
|
|
115
|
+
steps:
|
|
116
|
+
- uses: actions/checkout@v4
|
|
117
|
+
- run: docker compose up -d
|
|
118
|
+
prevention:
|
|
119
|
+
- "Test Docker container images on ubuntu-24.04 before migrating — check cgroup v2 compatibility with `docker run --rm ubuntu:24.04 ls /sys/fs/cgroup/`"
|
|
120
|
+
- "Use JDK 17.0.4+ or JDK 21+ in all containerized Java workloads for correct cgroup v2 memory/CPU detection"
|
|
121
|
+
- "Audit Dockerfiles for hardcoded cgroup v1 subsystem paths (/sys/fs/cgroup/memory/, /sys/fs/cgroup/cpu/)"
|
|
122
|
+
- "Use kind v0.17+ and k3d v5.6+ for Kubernetes-in-Docker CI on ubuntu-24.04"
|
|
123
|
+
- "Base images on Ubuntu 22.04+ or Debian Bookworm for any container running systemd as PID 1"
|
|
124
|
+
docs:
|
|
125
|
+
- url: "https://www.kernel.org/doc/html/latest/admin-guide/cgroup-v2.html"
|
|
126
|
+
label: "Linux kernel — cgroup v2 unified hierarchy documentation"
|
|
127
|
+
- url: "https://github.com/actions/runner-images/blob/main/images/ubuntu/Ubuntu2404-Readme.md"
|
|
128
|
+
label: "ubuntu-24.04 runner image — kernel version and installed software"
|
|
129
|
+
- url: "https://kind.sigs.k8s.io/docs/user/known-issues/#pod-errors-due-to-too-many-open-files"
|
|
130
|
+
label: "kind known issues — cgroup v2 and containerd requirements"
|
|
131
|
+
- url: "https://docs.docker.com/engine/security/userns-remap/"
|
|
132
|
+
label: "Docker — cgroup v2 compatibility and container isolation"
|
|
133
|
+
- url: "https://bugs.openjdk.org/browse/JDK-8230305"
|
|
134
|
+
label: "OpenJDK — JDK-8230305: Container Metrics: Support cgroup v2 (fixed in JDK 15, backported 11u16/17u4)"
|
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
id: silent-failures-060
|
|
2
|
+
title: 'Reusable workflow outputs not declared at on.workflow_call.outputs are silently empty in callers'
|
|
3
|
+
category: silent-failures
|
|
4
|
+
severity: silent-failure
|
|
5
|
+
tags:
|
|
6
|
+
- reusable-workflow
|
|
7
|
+
- workflow_call
|
|
8
|
+
- outputs
|
|
9
|
+
- empty-string
|
|
10
|
+
- silent-failure
|
|
11
|
+
patterns:
|
|
12
|
+
- regex: 'needs\.[a-z][a-z0-9_-]*\.outputs\.[a-z][a-z0-9_-]*'
|
|
13
|
+
flags: 'i'
|
|
14
|
+
error_messages:
|
|
15
|
+
- '(no error emitted — callers receive empty strings silently)'
|
|
16
|
+
- 'Error: Input required and not supplied'
|
|
17
|
+
root_cause: |
|
|
18
|
+
Reusable workflows require a two-level output declaration. Developers
|
|
19
|
+
correctly declare job-level outputs under jobs.<job-id>.outputs, but omit
|
|
20
|
+
the second required declaration: the workflow-level outputs block under
|
|
21
|
+
on.workflow_call.outputs.
|
|
22
|
+
|
|
23
|
+
Without the workflow-level outputs declaration, any caller that references
|
|
24
|
+
${{ needs.<call-job>.outputs.<name> }} receives an empty string. GitHub
|
|
25
|
+
Actions does not emit any error, warning, or annotation — downstream steps
|
|
26
|
+
silently receive empty values, producing wrong behavior or spurious failures
|
|
27
|
+
(e.g., artifact path is empty, deployment target is blank).
|
|
28
|
+
|
|
29
|
+
The root cause is that GitHub's reusable workflow output model requires two
|
|
30
|
+
separate declarations:
|
|
31
|
+
1. job.outputs: maps a step output to a job-scoped output
|
|
32
|
+
2. on.workflow_call.outputs: hoists a job output up to the workflow level
|
|
33
|
+
so external callers can reference it
|
|
34
|
+
|
|
35
|
+
Omitting level 2 is invisible — the job output exists internally but is
|
|
36
|
+
never exposed to the calling workflow.
|
|
37
|
+
fix: |
|
|
38
|
+
Add an outputs block directly under on.workflow_call that maps each desired
|
|
39
|
+
workflow output name to ${{ jobs.<job-id>.outputs.<output-name> }}. This is
|
|
40
|
+
in addition to (not a replacement for) the job-level outputs block.
|
|
41
|
+
fix_code:
|
|
42
|
+
- language: yaml
|
|
43
|
+
label: 'Reusable workflow: declare outputs at both job level and on.workflow_call level'
|
|
44
|
+
code: |
|
|
45
|
+
on:
|
|
46
|
+
workflow_call:
|
|
47
|
+
outputs:
|
|
48
|
+
build-version:
|
|
49
|
+
description: 'The semantic version produced by this workflow'
|
|
50
|
+
value: ${{ jobs.build.outputs.build-version }}
|
|
51
|
+
artifact-path:
|
|
52
|
+
description: 'Path to the uploaded artifact'
|
|
53
|
+
value: ${{ jobs.build.outputs.artifact-path }}
|
|
54
|
+
|
|
55
|
+
jobs:
|
|
56
|
+
build:
|
|
57
|
+
runs-on: ubuntu-latest
|
|
58
|
+
outputs:
|
|
59
|
+
build-version: ${{ steps.version.outputs.version }}
|
|
60
|
+
artifact-path: ${{ steps.upload.outputs.artifact-path }}
|
|
61
|
+
steps:
|
|
62
|
+
- id: version
|
|
63
|
+
run: echo "version=1.2.3" >> "$GITHUB_OUTPUT"
|
|
64
|
+
shell: bash
|
|
65
|
+
- id: upload
|
|
66
|
+
uses: actions/upload-artifact@v4
|
|
67
|
+
with:
|
|
68
|
+
name: my-artifact
|
|
69
|
+
path: dist/
|
|
70
|
+
- language: yaml
|
|
71
|
+
label: 'Calling workflow: access reusable workflow outputs via needs context'
|
|
72
|
+
code: |
|
|
73
|
+
jobs:
|
|
74
|
+
call-build:
|
|
75
|
+
uses: ./.github/workflows/build.yml
|
|
76
|
+
|
|
77
|
+
deploy:
|
|
78
|
+
needs: call-build
|
|
79
|
+
runs-on: ubuntu-latest
|
|
80
|
+
steps:
|
|
81
|
+
- name: Use build outputs
|
|
82
|
+
run: |
|
|
83
|
+
echo "Version: ${{ needs.call-build.outputs.build-version }}"
|
|
84
|
+
echo "Artifact: ${{ needs.call-build.outputs.artifact-path }}"
|
|
85
|
+
shell: bash
|
|
86
|
+
prevention:
|
|
87
|
+
- 'Always declare outputs under on.workflow_call.outputs in addition to any job-level outputs blocks — they are two distinct YAML nodes'
|
|
88
|
+
- 'Immediately echo needs.<call-job>.outputs.* in the caller after wiring up to verify outputs are populated during development'
|
|
89
|
+
- 'Use actionlint locally or in CI to catch missing workflow-level output declarations before they ship'
|
|
90
|
+
- 'Treat the two-level declaration as a checklist: job outputs block + workflow_call outputs block'
|
|
91
|
+
docs:
|
|
92
|
+
- url: 'https://docs.github.com/en/actions/sharing-automations/reusing-workflows#using-outputs-from-a-reusable-workflow'
|
|
93
|
+
label: 'GitHub Docs: Using outputs from a reusable workflow'
|
|
94
|
+
- url: 'https://github.com/orgs/community/discussions/17245'
|
|
95
|
+
label: 'GitHub Community: Outputs from reusable workflow missing in caller'
|
|
@@ -0,0 +1,101 @@
|
|
|
1
|
+
id: triggers-044
|
|
2
|
+
title: 'pull_request_target checks out base branch by default — PR head requires explicit ref'
|
|
3
|
+
category: triggers
|
|
4
|
+
severity: silent-failure
|
|
5
|
+
tags:
|
|
6
|
+
- pull_request_target
|
|
7
|
+
- checkout
|
|
8
|
+
- ref
|
|
9
|
+
- base-branch
|
|
10
|
+
- security
|
|
11
|
+
- fork
|
|
12
|
+
patterns:
|
|
13
|
+
- regex: 'on:\s*\n\s*pull_request_target'
|
|
14
|
+
flags: 'im'
|
|
15
|
+
- regex: 'uses:\s*actions/checkout.*\n(?!.*ref:)'
|
|
16
|
+
flags: 'im'
|
|
17
|
+
error_messages:
|
|
18
|
+
- '(no error — workflow runs against base branch code, not PR changes)'
|
|
19
|
+
root_cause: |
|
|
20
|
+
pull_request_target runs in the context of the BASE repository rather than
|
|
21
|
+
the contributor's fork. This is an intentional security boundary: because
|
|
22
|
+
the workflow has access to repository secrets and typically runs with write
|
|
23
|
+
permissions, GitHub executes it against trusted code on the base branch
|
|
24
|
+
rather than potentially untrusted PR code.
|
|
25
|
+
|
|
26
|
+
As a direct consequence, actions/checkout without an explicit ref: parameter
|
|
27
|
+
checks out the TARGET BRANCH (e.g., main), not the contributor's changes.
|
|
28
|
+
The workflow appears to run successfully — tests pass, linters pass — but
|
|
29
|
+
only because they are testing the existing base branch code. The PR's actual
|
|
30
|
+
changes are completely ignored. CI gives a false green for every PR
|
|
31
|
+
regardless of what was submitted.
|
|
32
|
+
|
|
33
|
+
This is among the most common misuses of pull_request_target, appearing
|
|
34
|
+
frequently in workflows that were migrated from pull_request to gain write
|
|
35
|
+
access (e.g., to post PR comments or add labels) without understanding the
|
|
36
|
+
checkout difference.
|
|
37
|
+
fix: |
|
|
38
|
+
If the goal is to build and test PR code, use on: pull_request instead of
|
|
39
|
+
pull_request_target. pull_request runs in the fork context with limited
|
|
40
|
+
permissions, which is the correct and safe choice for CI testing.
|
|
41
|
+
|
|
42
|
+
Reserve pull_request_target only for operations that specifically need write
|
|
43
|
+
permissions or secrets AND that do NOT execute untrusted PR code (e.g.,
|
|
44
|
+
adding labels based on event metadata, posting a comment using a stored
|
|
45
|
+
token). If pull_request_target must check out PR code, consult the GitHub
|
|
46
|
+
Security Lab advisory on pwn requests first — the attack surface is
|
|
47
|
+
significant.
|
|
48
|
+
fix_code:
|
|
49
|
+
- language: yaml
|
|
50
|
+
label: 'Preferred: use pull_request for code testing workflows (runs against PR head safely)'
|
|
51
|
+
code: |
|
|
52
|
+
on:
|
|
53
|
+
pull_request:
|
|
54
|
+
branches: [main]
|
|
55
|
+
|
|
56
|
+
jobs:
|
|
57
|
+
test:
|
|
58
|
+
runs-on: ubuntu-latest
|
|
59
|
+
permissions:
|
|
60
|
+
contents: read
|
|
61
|
+
steps:
|
|
62
|
+
- uses: actions/checkout@v4
|
|
63
|
+
# No ref needed — pull_request automatically checks out the merge commit
|
|
64
|
+
- run: npm ci && npm test
|
|
65
|
+
shell: bash
|
|
66
|
+
- language: yaml
|
|
67
|
+
label: 'Safe pull_request_target: metadata-only operations — no checkout of PR code'
|
|
68
|
+
code: |
|
|
69
|
+
on:
|
|
70
|
+
pull_request_target:
|
|
71
|
+
types: [opened, synchronize, labeled]
|
|
72
|
+
|
|
73
|
+
jobs:
|
|
74
|
+
label:
|
|
75
|
+
runs-on: ubuntu-latest
|
|
76
|
+
permissions:
|
|
77
|
+
pull-requests: write
|
|
78
|
+
steps:
|
|
79
|
+
# Safe: uses only github.event data, does NOT check out PR code
|
|
80
|
+
- name: Add triage label
|
|
81
|
+
uses: actions/github-script@v7
|
|
82
|
+
with:
|
|
83
|
+
script: |
|
|
84
|
+
await github.rest.issues.addLabels({
|
|
85
|
+
owner: context.repo.owner,
|
|
86
|
+
repo: context.repo.repo,
|
|
87
|
+
issue_number: context.payload.pull_request.number,
|
|
88
|
+
labels: ['needs-review']
|
|
89
|
+
});
|
|
90
|
+
prevention:
|
|
91
|
+
- 'Default to on: pull_request for all CI testing workflows — it checks out PR code correctly and runs with limited permissions'
|
|
92
|
+
- 'Only use pull_request_target when write permissions or secrets are required AND untrusted PR code is never executed'
|
|
93
|
+
- 'If pull_request_target is in a workflow, verify there is NO actions/checkout step (or that it explicitly uses a trusted ref)'
|
|
94
|
+
- 'Review the GitHub Security Lab pwn requests advisory before combining pull_request_target with any form of code execution from the PR'
|
|
95
|
+
docs:
|
|
96
|
+
- url: 'https://docs.github.com/en/actions/writing-workflows/choosing-when-your-workflow-runs/events-that-trigger-workflows#pull_request_target'
|
|
97
|
+
label: 'GitHub Docs: pull_request_target event'
|
|
98
|
+
- url: 'https://securitylab.github.com/research/github-actions-preventing-pwn-requests/'
|
|
99
|
+
label: 'GitHub Security Lab: Preventing pwn requests in GitHub Actions'
|
|
100
|
+
- url: 'https://github.com/orgs/community/discussions/15669'
|
|
101
|
+
label: 'GitHub Community: pull_request_target and checkout behavior'
|
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
id: yaml-syntax-042
|
|
2
|
+
title: 'Composite action run steps require explicit shell property — no default shell is applied'
|
|
3
|
+
category: yaml-syntax
|
|
4
|
+
severity: error
|
|
5
|
+
tags:
|
|
6
|
+
- composite-action
|
|
7
|
+
- shell
|
|
8
|
+
- run-step
|
|
9
|
+
- action-yaml
|
|
10
|
+
- validation-error
|
|
11
|
+
patterns:
|
|
12
|
+
- regex: 'Required property is missing: shell'
|
|
13
|
+
flags: 'i'
|
|
14
|
+
- regex: 'The `shell` property must be set'
|
|
15
|
+
flags: 'i'
|
|
16
|
+
- regex: 'shell is required for `run` step in composite action'
|
|
17
|
+
flags: 'i'
|
|
18
|
+
error_messages:
|
|
19
|
+
- 'Required property is missing: shell'
|
|
20
|
+
- 'The `shell` property must be set for step `run` in composite actions'
|
|
21
|
+
- "Error: Unexpected value ''"
|
|
22
|
+
root_cause: |
|
|
23
|
+
Regular workflow jobs default to bash on Linux and macOS, and pwsh on
|
|
24
|
+
Windows, when the shell property is omitted from a run step. Composite
|
|
25
|
+
actions (using: composite) do not inherit any default shell — every run
|
|
26
|
+
step must explicitly declare a shell value such as bash, pwsh, sh, or cmd.
|
|
27
|
+
|
|
28
|
+
This inconsistency frequently catches developers who copy run steps from a
|
|
29
|
+
workflow job into a composite action's action.yml without adding shell: bash.
|
|
30
|
+
The error surfaces immediately on the first run and is caught by the runner's
|
|
31
|
+
action schema validation, but the message can be confusing because shell is
|
|
32
|
+
a property developers rarely need to specify in regular workflows.
|
|
33
|
+
|
|
34
|
+
The GitHub Actions runner enforces this requirement because composite actions
|
|
35
|
+
must be portable across multiple callers (Linux, macOS, Windows) and the
|
|
36
|
+
runner has no basis to assume which shell is appropriate without the caller
|
|
37
|
+
specifying one.
|
|
38
|
+
fix: |
|
|
39
|
+
Add shell: bash (or shell: pwsh on Windows-targeted steps, shell: sh for
|
|
40
|
+
minimal Alpine images) to every run step in the composite action's
|
|
41
|
+
action.yml. If the action must support multiple operating systems, use a
|
|
42
|
+
conditional expression to select the shell based on runner.os.
|
|
43
|
+
fix_code:
|
|
44
|
+
- language: yaml
|
|
45
|
+
label: 'action.yml: add explicit shell to every run step in a composite action'
|
|
46
|
+
code: |
|
|
47
|
+
name: My Composite Action
|
|
48
|
+
description: 'Example composite action with correct shell declarations'
|
|
49
|
+
runs:
|
|
50
|
+
using: composite
|
|
51
|
+
steps:
|
|
52
|
+
- name: Install dependencies
|
|
53
|
+
run: npm ci
|
|
54
|
+
shell: bash
|
|
55
|
+
|
|
56
|
+
- name: Build
|
|
57
|
+
run: npm run build
|
|
58
|
+
shell: bash
|
|
59
|
+
|
|
60
|
+
- name: Run tests
|
|
61
|
+
run: npm test
|
|
62
|
+
shell: bash
|
|
63
|
+
- language: yaml
|
|
64
|
+
label: 'Cross-platform composite action: select shell via runner.os expression'
|
|
65
|
+
code: |
|
|
66
|
+
runs:
|
|
67
|
+
using: composite
|
|
68
|
+
steps:
|
|
69
|
+
- name: Platform-aware step
|
|
70
|
+
run: echo "Running on ${{ runner.os }}"
|
|
71
|
+
shell: ${{ runner.os == 'Windows' && 'pwsh' || 'bash' }}
|
|
72
|
+
|
|
73
|
+
- name: Windows-only step
|
|
74
|
+
if: runner.os == 'Windows'
|
|
75
|
+
run: Write-Host "Windows step"
|
|
76
|
+
shell: pwsh
|
|
77
|
+
|
|
78
|
+
- name: Unix step
|
|
79
|
+
if: runner.os != 'Windows'
|
|
80
|
+
run: echo "Unix step"
|
|
81
|
+
shell: bash
|
|
82
|
+
prevention:
|
|
83
|
+
- 'Add shell: bash to every run step when authoring or editing a composite action — treat it as required boilerplate'
|
|
84
|
+
- 'Use actionlint or the VS Code GitHub Actions extension to surface missing shell properties before committing'
|
|
85
|
+
- 'Keep a composite action template or snippet that includes shell: bash by default in every run step'
|
|
86
|
+
- 'When converting a workflow job to a composite action, do a search for all run: blocks and add shell: to each'
|
|
87
|
+
docs:
|
|
88
|
+
- url: 'https://docs.github.com/en/actions/sharing-automations/creating-actions/metadata-syntax-for-github-actions#runsusing-for-composite-actions'
|
|
89
|
+
label: 'GitHub Docs: Metadata syntax for composite actions'
|
|
90
|
+
- url: 'https://github.com/actions/runner/issues/835'
|
|
91
|
+
label: 'actions/runner #835: Composite actions should have a default shell'
|
|
92
|
+
- url: 'https://docs.github.com/en/actions/writing-workflows/workflow-syntax-for-github-actions#jobsjob_idstepsshell'
|
|
93
|
+
label: 'GitHub Docs: Workflow syntax — steps.shell'
|
package/package.json
CHANGED