Repository navigation
OSAC-1680: Add GitHub Actions e2e job #317
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||||||
|---|---|---|---|---|---|---|---|---|---|---|
| @@ -0,0 +1,38 @@ | ||||||||||
| --- | ||||||||||
| name: E2E Tests | ||||||||||
|
|
||||||||||
| on: | ||||||||||
| pull_request: | ||||||||||
| branches: [main] | ||||||||||
| workflow_dispatch: {} | ||||||||||
|
|
||||||||||
| jobs: | ||||||||||
| build-pr-image: | ||||||||||
| runs-on: ubuntu-latest | ||||||||||
| permissions: | ||||||||||
| contents: read | ||||||||||
| packages: write | ||||||||||
| outputs: | ||||||||||
| image: ${{ steps.meta.outputs.image }} | ||||||||||
| steps: | ||||||||||
| - name: Checkout | ||||||||||
| uses: actions/checkout@v4 | ||||||||||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🔒 Security & Privacy | 🟠 Major | ⚡ Quick win Disable persisted checkout credentials before running PR-controlled build steps. Line 19 uses default checkout behavior, which persists auth credentials for later steps in the job. Suggested change - name: Checkout
uses: actions/checkout@<full_commit_sha>
+ with:
+ persist-credentials: falseAs per path instructions, 📝 Committable suggestion
Suggested change
🧰 Tools🪛 zizmor (1.26.1)[warning] 18-19: credential persistence through GitHub Actions artifacts (artipacked): does not set persist-credentials: false (artipacked) [error] 19-19: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy) (unpinned-uses) 🤖 Prompt for AI AgentsSources: Path instructions, Linters/SAST tools 🔒 Security & Privacy | 🟠 Major 🧩 Analysis chain🏁 Script executed: #!/bin/bash
set -euo pipefail
git ls-files .github/workflows/e2e-test.yml
wc -l .github/workflows/e2e-test.yml
cat -n .github/workflows/e2e-test.yml | sed -n '1,220p'Repository: osac-project/osac-operator Length of output: 1591 Pin both workflow refs to immutable SHAs. 🧰 Tools🪛 zizmor (1.26.1)[warning] 18-19: credential persistence through GitHub Actions artifacts (artipacked): does not set persist-credentials: false (artipacked) [error] 19-19: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy) (unpinned-uses) 🤖 Prompt for AI AgentsSources: Path instructions, Linters/SAST tools |
||||||||||
|
|
||||||||||
| - name: Set image metadata | ||||||||||
| id: meta | ||||||||||
| run: | | ||||||||||
| IMAGE="ghcr.io/osac-project/osac-operator:pr-${{ github.event.pull_request.number || github.run_id }}" | ||||||||||
| echo "image=${IMAGE}" >> "$GITHUB_OUTPUT" | ||||||||||
|
|
||||||||||
| - name: Build and push PR image | ||||||||||
| run: | | ||||||||||
| echo "${{ secrets.GITHUB_TOKEN }}" | podman login ghcr.io -u "${{ github.actor }}" --password-stdin | ||||||||||
| podman build -t "${{ steps.meta.outputs.image }}" -f Containerfile . | ||||||||||
| podman push "${{ steps.meta.outputs.image }}" | ||||||||||
|
Comment on lines
+27
to
+31
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🩺 Stability & Availability | 🟠 Major 🧩 Analysis chain🏁 Script executed: #!/bin/bash
set -euo pipefail
# Map relevant workflow files and inspect the target workflow around the referenced lines.
git ls-files .github/workflows
echo '---'
wc -l .github/workflows/e2e-test.yml
echo '---'
cat -n .github/workflows/e2e-test.yml | sed -n '1,220p'Repository: osac-project/osac-operator Length of output: 1781 🌐 Web query:
💡 Result: In GitHub Actions, pull requests coming from forks get a read-only GITHUB_TOKEN, so your workflow cannot use GITHUB_TOKEN to push to GitHub Container Registry (GHCR) with packages:write in that context. GitHub states that for pull requests from forks the GITHUB_TOKEN “will be … always read” and that “Pull requests from public forks are still considered a special case and will receive a read token regardless of these settings” [1]. What you need to write/push to GHCR with GITHUB_TOKEN 1) Use a workflow/job permissions block that includes packages: write. GitHub documents that GITHUB_TOKEN permissions are controlled via the workflow/job Citations:
🌐 Web query:
💡 Result: In GitHub Actions, behavior depends on (a) whether the workflow runs on a pull_request from a fork vs from the same repo, and (b) the permissions you request for GITHUB_TOKEN. 1) What GITHUB_TOKEN can do on forked pull_request events - GitHub has a special rule for pull requests from forks: the GITHUB_TOKEN is provided with read-only permissions (and no secrets access) even if your workflow/job requests broader permissions in most cases. This is explicitly called out in GitHub’s docs for “Run workflows from fork pull requests”, which states it uses a GITHUB_TOKEN with read-only permission and no access to secrets.[1] - GitHub also states that pull requests from public forks are treated as a special case and will receive a read token regardless of the permissions settings you specify in workflow/job scope.[2] Net effect for your query: If your workflow is triggered by pull_request from a fork, you should assume GITHUB_TOKEN will be read-only for scopes like packages (and other write scopes), so attempts to push to GHCR will fail unless you use an alternative trusted execution model. 2) Can you push to GitHub Container Registry (GHCR) with GITHUB_TOKEN? - GHCR / GitHub Packages support using GITHUB_TOKEN for container registry operations. GitHub’s changelog notes that you can authenticate to the Packages Container registry with GITHUB_TOKEN in Actions workflows, and that it supports reading/creating/updating/deleting containers.[3] - For package/container registry actions, GitHub Packages permissions correspond to scopes like read:packages and write:packages.[4] So: pushing to GHCR with GITHUB_TOKEN is supported when the workflow’s GITHUB_TOKEN actually has write:packages (and the workflow is allowed to obtain write permissions). 3) Why forked pull_request workflows often can’t push, even if you set permissions - If you request permissions in the workflow YAML (for example packages: write) but the event is a pull_request coming from a fork, GitHub’s special-case handling means the token still ends up read-only.[2] - Additionally, GitHub documents that the “fork pull requests” policy mode (run workflows from fork pull requests) uses a GITHUB_TOKEN with read-only permission and no secrets, which prevents privileged operations such as pushing images.[1] 4) Recommended pattern: separate build (untrusted fork) from publish (trusted) - To safely build PR code from forks but still publish artifacts (like pushing to GHCR), the typical approach is: a) Run a pull_request workflow on forks with read-only permissions to build/test (no publishing). b) Use a separate trusted trigger (for example push to main, workflow_dispatch, or a protected internal job) to publish using a token that can be granted write access. - If you instead use pull_request_target to get a token with write permissions, be aware this can run with more privilege and can be dangerous if it checks out untrusted code; this is widely considered a security anti-pattern unless done very carefully. 5) How to check/set the exact token permissions - You can set the default permissions for GITHUB_TOKEN at repository settings (“Workflow permissions”). GitHub documents that the default/restricted setting can be “read access for contents and packages”.[1] - You can also set explicit permissions in workflow/job YAML using the permissions key, including packages: read/write and pull-requests: read/write, etc. But remember that fork pull requests are still treated specially and will receive a read token.[2] Practical takeaway for your exact query keywords - “pull_request forked pull requests” + “GITHUB_TOKEN packages write” + “GHCR push”: generally will not work with pull_request from forks, because GitHub issues a read-only GITHUB_TOKEN for fork pull_request runs.[1][2] - “GITHUB_TOKEN packages read-only” works for fork PRs (pull/build/use), because read scopes are allowed.[1] - “push to GHCR” requires write:packages on GITHUB_TOKEN, which you can get in trusted workflows/events, and GitHub Packages supports using GITHUB_TOKEN for container operations.[3][4] If you share your workflow YAML (especially the trigger and permissions block) and whether the images should be pushed for public forks or only for internal contributors, I can suggest a safe configuration that matches what you’re trying to do. Citations:
Guard the GHCR push on forked PRs
🧰 Tools🪛 zizmor (1.26.1)[warning] 29-29: code injection via template expansion (template-injection): may expand into attacker-controllable code (template-injection) [error] 29-29: code injection via template expansion (template-injection): may expand into attacker-controllable code (template-injection) [info] 30-30: code injection via template expansion (template-injection): may expand into attacker-controllable code (template-injection) [info] 31-31: code injection via template expansion (template-injection): may expand into attacker-controllable code (template-injection) 🤖 Prompt for AI Agents |
||||||||||
|
|
||||||||||
| e2e: | ||||||||||
| needs: build-pr-image | ||||||||||
| uses: osac-project/osac-test-infra/.github/workflows/e2e.yml@main | ||||||||||
| with: | ||||||||||
| component-image: ${{ needs.build-pr-image.outputs.image }} | ||||||||||
| component-image-name: ghcr.io/osac-project/osac-operator | ||||||||||
|
Comment on lines
+9
to
+38
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🔒 Security & Privacy | 🟠 Major | 🏗️ Heavy lift Add/attach SAST and SCA gating before this image is consumed. The workflow currently builds/pushes and triggers E2E without an in-pipeline static/dependency security gate. As per path instructions, 🧰 Tools🪛 zizmor (1.26.1)[warning] 18-19: credential persistence through GitHub Actions artifacts (artipacked): does not set persist-credentials: false (artipacked) [warning] 24-24: code injection via template expansion (template-injection): may expand into attacker-controllable code (template-injection) [warning] 29-29: code injection via template expansion (template-injection): may expand into attacker-controllable code (template-injection) [error] 29-29: code injection via template expansion (template-injection): may expand into attacker-controllable code (template-injection) [info] 30-30: code injection via template expansion (template-injection): may expand into attacker-controllable code (template-injection) [info] 31-31: code injection via template expansion (template-injection): may expand into attacker-controllable code (template-injection) [error] 19-19: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy) (unpinned-uses) [error] 35-35: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy) (unpinned-uses) [warning] 14-14: permissions without explanatory comments (undocumented-permissions): needs an explanatory comment (undocumented-permissions) [info] 10-10: workflow or action definition without a name (anonymous-definition): this job (anonymous-definition) 🤖 Prompt for AI AgentsSource: Path instructions
Comment on lines
+27
to
+38
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🔒 Security & Privacy | 🟠 Major 🧩 Analysis chain🏁 Script executed: #!/bin/bash
set -euo pipefail
echo "== Workflow file map =="
git ls-files '.github/workflows/*'
echo
echo "== e2e-test workflow (line numbered) =="
cat -n .github/workflows/e2e-test.yml
echo
echo "== Search for cosign/signing/provenance in workflows =="
rg -n --hidden -S 'cosign|sigstore|provenance|attest|sign' .github/workflows . || true
echo
echo "== Search for GHCR / image signing references =="
rg -n --hidden -S 'ghcr.io|podman build|podman push|image:' .github/workflows . || trueRepository: osac-project/osac-operator Length of output: 50383 🏁 Script executed: #!/bin/bash
set -euo pipefail
echo "== Workflow file map =="
git ls-files '.github/workflows/*'
echo
echo "== e2e-test workflow (line numbered) =="
cat -n .github/workflows/e2e-test.yml
echo
echo "== Search for cosign/signing/provenance in workflows =="
rg -n --hidden -S 'cosign|sigstore|provenance|attest|sign' .github/workflows . || true
echo
echo "== Search for GHCR / image signing references =="
rg -n --hidden -S 'ghcr.io|podman build|podman push|image:' .github/workflows . || trueRepository: osac-project/osac-operator Length of output: 50383 🏁 Script executed: #!/bin/bash
set -euo pipefail
echo "== Workflow file map =="
git ls-files '.github/workflows/*'
echo
echo "== e2e-test workflow (line numbered) =="
cat -n .github/workflows/e2e-test.yml
echo
echo "== Search for cosign/signing/provenance in workflows =="
rg -n --hidden -S 'cosign|sigstore|provenance|attest|sign' .github/workflows . || true
echo
echo "== Search for GHCR / image signing references =="
rg -n --hidden -S 'ghcr.io|podman build|podman push|image:' .github/workflows . || trueRepository: osac-project/osac-operator Length of output: 50383 🏁 Script executed: #!/bin/bash
set -euo pipefail
cat -n .github/workflows/e2e-test.yml
rg -n --hidden -S 'cosign|sigstore|provenance|attest|sign' .github/workflows . || trueRepository: osac-project/osac-operator Length of output: 50383 Sign the PR image before E2E handoff 🧰 Tools🪛 zizmor (1.26.1)[warning] 29-29: code injection via template expansion (template-injection): may expand into attacker-controllable code (template-injection) [error] 29-29: code injection via template expansion (template-injection): may expand into attacker-controllable code (template-injection) [info] 30-30: code injection via template expansion (template-injection): may expand into attacker-controllable code (template-injection) [info] 31-31: code injection via template expansion (template-injection): may expand into attacker-controllable code (template-injection) [error] 35-35: unpinned action reference (unpinned-uses): action is not pinned to a hash (required by blanket policy) (unpinned-uses) 🤖 Prompt for AI AgentsSource: Path instructions |
||||||||||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🩺 Stability & Availability | 🟡 Minor | ⚡ Quick win
Add workflow concurrency to avoid PR tag races.
Multiple runs for the same PR can push the same
pr-<number>tag concurrently, making E2E consume nondeterministic image content.Suggested change
on: pull_request: branches: [main] workflow_dispatch: {} + +concurrency: + group: e2e-pr-${{ github.event.pull_request.number || github.run_id }} + cancel-in-progress: trueAlso applies to: 24-24
🧰 Tools
🪛 zizmor (1.26.1)
[warning] 4-7: insufficient job-level concurrency limits (concurrency-limits): workflow is missing concurrency setting
(concurrency-limits)
🤖 Prompt for AI Agents
Source: Linters/SAST tools