Before approving a workflow, identify the exact revision, executable inputs, runner, and permissions it will use. Keep untrusted pull request code away from privileged execution, and treat artifacts produced from that code as untrusted inputs too.
A contributor submits a useful fix. The checks are waiting, and a comment asks a maintainer to approve the run so work can continue. That request may be entirely legitimate. It is still a request to execute code somewhere with a particular set of permissions.
For maintainers, the question is larger than whether the proposed feature looks reasonable. What code will run, where will it run, and what can that environment access? A friendly exchange does not answer those questions. Neither does a green check on an earlier revision.
Approving one workflow run differs from giving someone a maintainer role, which grants ongoing authority. A single run can cross an important boundary even when the contributor receives no permanent role.
What “run the tests” actually means
Continuous integration, or CI, runs automated tasks when code changes or another event occurs. A workflow defines the jobs; a runner is the machine that executes them. A pull request proposes changes, often from a fork, which is a separate copy of a repository.
Tests, build scripts, configuration, and dependencies can all influence what executes. GitHub Security Lab’s guidance explains why checking only an application feature is insufficient: attacker-controlled build or installation steps may execute before the visible test suite begins. The same article distinguishes handling pull request material as data from executing code it controls. GitHub Security Lab: preventing pwn requests
That means the review includes the path from the proposed changes to the runner. A workflow file can remain unchanged while a script it calls changes. A reviewer should follow the invoked script and relevant dependency changes far enough to understand the requested run.
What the Solana workflow disclosure showed
In December 2021, GitHub Security Lab published an advisory about Solana’s Explorer workflow. The reported workflow used pull_request_target, checked out potentially untrusted pull request code, and executed it in a context able to access secrets and modify the base repository. The disclosure timeline records a fix on October 27, 2021.
This was a reported implementation vulnerability. The advisory does not establish that a social engineer exploited a maintainer or that the project remains vulnerable today. Its value here is the documented boundary: code supplied by a contributor reached an environment with authority belonging to the target repository. GitHub Security Lab: Solana workflow advisory
A request in a comment can encourage a maintainer to overlook that boundary. But the risky configuration may also trigger automatically. Human persuasion and workflow design are separate parts of the assessment; do not assume that every vulnerable run requires an approval click.
Before approving the test run
GitHub Actions review example
- Contributor
Submits a pull request and may ask for checks to run.
Request review
- Maintainer review
Check exact revision, executable inputs, runner, and effective permissions.
Approve only after review
- Untrusted test job
Use an approved restricted runner. No production authority is needed.
Produce results
- Output artifact
Still untrusted data. Validate before consuming.
Validated data only
- Privileged consumer
Uses separate authority for its task. Do not execute untrusted output.
Approval is a decision, not a sandbox. Automation may run without a human gate.
Approval does not create isolation
GitHub documents that some fork-triggered runs require approval from a maintainer with write access, depending on repository, organization, or enterprise policy. Its approval instructions tell reviewers to inspect proposed changes, especially workflow changes, before allowing the run. Approval requirements therefore need checking in the repository you manage; they are not universal. GitHub: approving workflow runs from forks
Approval does not remove the runner’s credentials or network access. Check both whether this revision should run and whether the runner is suitable for untrusted code.
GitHub’s current secure-use guidance warns about privileged workflows that process untrusted pull request code. It also warns that self-hosted runners lack the clean, ephemeral environment guarantees associated with GitHub-hosted runners. The actual risk depends on accessible data, credentials, services, and configuration. GitHub: secure workflow use
A disposable runner can still have valuable credentials during its lifetime. Conversely, a carefully restricted run does not become a repository takeover simply because it processes an unfamiliar contributor’s code. Read the actual permissions and connections before describing the exposure.
Check the revision, code, permissions, and handoff
The revision. Identify the commit that the requested run will use. Do not rely on the pull request title or on having read the conversation yesterday. If the contributor has pushed changes since review, revisit the executable inputs affected by those changes.
The code path. Identify the workflow’s trigger and the source revision it checks out or otherwise processes. Then follow build, install, and test commands into the files they use. A change to a test helper or package script can matter even when the workflow YAML is untouched.
The authority. Ask the workflow owner what credentials and token permissions the job receives and which services the runner can reach. Record the effective configuration rather than assuming that a named trigger always grants the same access.
The handoff. Identify what the run produces and which later job consumes it. A file created by untrusted code does not become trusted because it is now called an artifact. Review the consumer as well as the producer.
If the maintainer cannot answer one of them, the workflow owner can resolve it before execution. The contributor should not be asked to certify the safety of the environment they want to use.
A legitimate helper-script change still needs an appropriate runner. Code review does not justify exposing a broad internal service to future contributors. Confirm the revision that ran and its effective access through approved configuration and audit evidence; a passing test suite does not establish that the runner lacked unnecessary access.
Do not move the risk into the next job
Splitting an untrusted build from a privileged follow-up can be useful. The follow-up still has to interpret what it receives safely. GitHub Security Lab explicitly cautions that artifacts originating from untrusted pull requests remain untrusted; executing such a binary in a privileged follow-up recreates the problem. Its guidance also discusses treating narrow results as data instead. GitHub Security Lab: artifact trust
For a review, draw the output beside its consumer: test summary to a reporting job, package to a publication job, or archive to an extraction step. Ask what the consumer does with each. Storing the output as an artifact does not approve its contents.
If a team needs a privileged release action, define the approved input and provenance checks for that action. Avoid solving an inconvenient test failure by giving the test job broader credentials. The application owner and CI owner should agree on the smallest access needed for the intended operation.
If the run already happened
Preserve the pull request, relevant revisions, workflow configuration, run identifiers, logs, and output references through your normal incident process. Record who approved what and when, if approval was part of the path. Keep sensitive values out of broad chat threads.
Then distinguish the evidence stages. A run record shows that a job started or completed. The workflow and effective configuration help establish which access was available. Service-side records may show whether that access was used. An unusual contributor comment alone proves none of those outcomes.
Where the team identifies an exposed credential or a compromised runner, the responsible owners should follow the established containment process. Rotating a credential without addressing the workflow that exposed it can leave the same path available for the replacement. Preserve relevant evidence before disruptive cleanup where the response process permits.


