feat(review-pr): add abuse safeguards for review requests#13
Open
Sayt-0 wants to merge 3 commits into
Open
Conversation
Harden the comment and event triggered PR review pipeline against abuse on every trigger path (review_requested, /review, @docker-agent mention, automatic opened/synchronize, and the workflow_run fork path). - Org membership: verify the PR author on the direct pull_request auto-review path (previously an empty comment author was checked) via a new resolveUsername helper with a live PR-author lookup fallback; fail closed when no user resolves. - Audit log: new src/audit-log module emits one structured record per request (requester, time, trigger, PR, reviewed SHA, allow/deny/throttle decision) as a notice, a job-summary line, and a 90 day JSONL artifact, on allow and deny paths, with an inline fallback when setup-credentials is unavailable. - Rate anomaly: new src/rate-limit module skips the review when too many agent review/reply comments land on a PR within a window; per-PR concurrency groups collapse same-trigger bursts; the existing cache lock still prevents concurrent reviews. - Force push: new src/check-staleness module compares the requested SHA against current head, records the actually reviewed SHA, and posts a notice on rebase. Documented in SECURITY.md and review-pr/README.md. Unit tests added for all new modules.
CodeQL (actions/untrusted-checkout-toctou/critical) flagged the new "Audit review request" run-step because it executed after "Checkout PR head" checks out untrusted PR code in an issue_comment-privileged workflow. The audit decision is fully determined before checkout (membership, rate, staleness), so move the audit and audit-upload steps ahead of the checkout. No post-checkout run-step is introduced by this change; behavior and recorded fields are unchanged.
docker-agent
left a comment
Contributor
There was a problem hiding this comment.
Assessment: 🟢 APPROVE
The PR introduces three new modules (src/audit-log, src/rate-limit, src/check-staleness) and wires them into the review workflow with a clear security-first design. The changes are well-structured and the logic holds up under scrutiny.
What was reviewed:
src/audit-log/index.ts— JSONL artifact, job summary, audit record emission: no data-loss paths in the CLI call chainsrc/rate-limit/index.ts— comment counting withsince/updated_atvs.created_at: the explicit client-sidecreated_atfilter correctly compensates for GitHub'supdated_at-basedsinceparameter; no under-count scenario is possible sinceupdated_at ≥ created_atalways holds on GitHubsrc/check-staleness/index.ts— SHA comparison and stale-post logic: correctsrc/check-org-membership/index.ts—resolveUsernamefallback on non-event paths: the PR-author fallback ontrigger/inputpaths is intentional design; both paths are gated by trusted callers who control the PR number, so there is no bypass.github/workflows/review-pr.yml— rate check ordering, concurrency groups,needs:dependencies: correctly ordered; rate check precedes check creation as documented- The fail-open behavior for the rate-limit step and the audit decision logging are consistent with the documented design
No confirmed or likely bugs were found in the changed code.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Adds safeguards against abuse of review requests on every trigger path
(review_requested, /review, @docker-agent mention, automatic opened/synchronize,
and the workflow_run fork path).
resolveUsernamewith a live PR-author fallback; fails closed. review_requested relies on GitHub-native reviewer-request enforcement, now documented.src/audit-logwrites one structured record per request (requester, time, trigger, PR, reviewed SHA, decision) as a notice, a job-summary line, and a 90 day JSONL artifact, on allow and deny paths.src/rate-limitskips the review above a per-PR frequency threshold; per-PRconcurrency:groups collapse same-trigger bursts; existing cache lock prevents concurrent reviews.src/check-stalenesscompares the requested SHA to current head, records the reviewed SHA, and posts a notice on rebase.Validation
An adversarial review pass found and fixed two defects: a throttled request could
create a green "PR Review" check (rate check now precedes and gates check
creation), and an audit record could be lost on a setup-credentials failure (an
inline fallback now records it).
Residual design notes
catches sustained driving rather than the very first instantaneous burst; that
first burst is bounded by the concurrency groups and the 600s cache lock.
enforcement (only triage/write can request a reviewer) for the requester.
Files
New modules: src/audit-log, src/rate-limit, src/check-staleness (each with tests).
Changed: src/check-org-membership, src/post-mention-reply, tsup.config.ts,
.github/workflows/review-pr.yml, .github/workflows/self-review-pr-trigger.yml,
SECURITY.md, review-pr/README.md.