Skip to content

fix: skip code agent when human PR already exists for issue#473

Open
fullsend-ai-coder[bot] wants to merge 1 commit into
mainfrom
agent/460-skip-duplicate-human-pr
Open

fix: skip code agent when human PR already exists for issue#473
fullsend-ai-coder[bot] wants to merge 1 commit into
mainfrom
agent/460-skip-duplicate-human-pr

Conversation

@fullsend-ai-coder
Copy link
Copy Markdown

The pre-code script now checks for existing open PRs linked to the target issue before the sandbox is created. If a human-authored PR is found (not from the fullsend bot), the script applies a "pr-open" label and posts a comment linking the existing PR(s), then exits cleanly — preventing the code agent from creating a duplicate competing PR.

The check is best-effort: it only runs when GH_TOKEN is available and can be overridden with CODE_FORCE=true (set when a user comments /code --force on the issue). Bot-authored PRs are filtered out so the agent can still update its own previous work.

Uses gh's built-in --jq flag for filtering, avoiding a standalone jq dependency.

Note: go-test and go-vet could not run (Go not available in sandbox). post-triage-test.sh has pre-existing failures (jq not available in sandbox). pre-code-test.sh passed. Manual verification of Go tests is required.

Closes #460

Changed files

  • Makefile
  • internal/scaffold/fullsend-repo/scripts/pre-code-test.sh
  • internal/scaffold/fullsend-repo/scripts/pre-code.sh

Closes #460

Post-script verification

  • Branch is not main/master (agent/460-skip-duplicate-human-pr)
  • Secret scan passed (gitleaks — de54df26a206ba6edb543a5cfd22bed59dffa7b9..HEAD)
  • Pre-commit hooks passed (authoritative run on runner)
  • Tests ran inside sandbox

Created by fullsend code agent

The pre-code script now checks for existing open PRs linked to
the target issue before the sandbox is created. If a human-authored
PR is found (not from the fullsend bot), the script applies a
"pr-open" label and posts a comment linking the existing PR(s),
then exits cleanly — preventing the code agent from creating a
duplicate competing PR.

The check is best-effort: it only runs when GH_TOKEN is available
and can be overridden with CODE_FORCE=true (set when a user
comments `/code --force` on the issue). Bot-authored PRs are
filtered out so the agent can still update its own previous work.

Uses gh's built-in --jq flag for filtering, avoiding a standalone
jq dependency.

Note: go-test and go-vet could not run (Go not available in
sandbox). post-triage-test.sh has pre-existing failures (jq not
available in sandbox). pre-code-test.sh passed. Manual
verification of Go tests is required.

Closes #460
@fullsend-ai-coder fullsend-ai-coder Bot added the ready-for-review Agent PR ready for human review label Apr 27, 2026
@github-actions
Copy link
Copy Markdown

Site preview

Preview: https://0ee55c09-site.fullsend-ai.workers.dev

Commit: 2858f6857163de8bfff4503bd99f540a17013843

Copy link
Copy Markdown

@fullsend-ai-review fullsend-ai-review Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review: #473

Head SHA: 2858f68
Timestamp: 2026-04-27T21:00:00Z
Outcome: request-changes

Summary

The PR adds a pre-code check to detect existing human PRs before the code agent runs, along with comprehensive tests. The intent aligns well with issue #460. However, the core feature does not work as implemented: the script exits 0 when human PRs are found, but both invocation paths (GHA workflow steps and the harness CLI) interpret exit 0 as "proceed" — the code agent will still run and may create a duplicate PR. Additionally, the GH_TOKEN environment variable the script requires is not set in the workflow step where pre-code.sh runs, so the check is always skipped in production.

Findings

Critical

  • [Correctness] internal/scaffold/fullsend-repo/scripts/pre-code.sh:113 — Script exits 0 when existing human PRs are found, but this does not prevent the code agent from running. In the GHA workflow (code.yml), exit 0 from the "Validate inputs" step causes subsequent steps (including "Run code agent") to proceed. In the harness CLI (run.go:174-186), exit 0 from the pre-script likewise continues to sandbox creation and agent execution. The PR description claims "exits cleanly — preventing the code agent from creating a duplicate competing PR" but this is incorrect — the core feature is non-functional.
    Remediation: The script needs a mechanism to signal "skip" to the caller. Options: (1) exit with a non-zero code and add continue-on-error: true to the workflow step plus a conditional if: on subsequent steps checking the step outcome; (2) write a step output (via $GITHUB_OUTPUT) and gate the agent step with if: steps.validate.outputs.skip != 'true'; (3) in the harness path, define a convention (e.g., exit code 78 or a sentinel file) that run.go checks to skip agent execution without treating it as a failure.

High

  • [Correctness] internal/scaffold/fullsend-repo/.github/workflows/code.yml:96-101 — The "Validate inputs" step does not set GH_TOKEN in its env block. The script checks ${GH_TOKEN:-} and exits early with "GH_TOKEN not set — skipping existing-PR check" when it is empty. In GitHub Actions, GITHUB_TOKEN is available but GH_TOKEN is not (they are different variables). The gh CLI accepts both, but the explicit bash check for GH_TOKEN means the PR-detection feature is dead code in the production workflow.
    Remediation: Either add GH_TOKEN: ${{ steps.sandbox-token.outputs.token }} (or ${{ github.token }}) to the step's env block, or change the script to check for GITHUB_TOKEN as a fallback (e.g., ${GH_TOKEN:-${GITHUB_TOKEN:-}}).

Medium

  • [Correctness] internal/scaffold/fullsend-repo/scripts/pre-code.sh:82 — The search query --search "${ISSUE_NUMBER} in:body,title" performs text matching, so low issue numbers (e.g., #1, #4) will match any PR that coincidentally contains that digit in its title or body. This could cause false positives that incorrectly block the code agent (once the exit-code issue is fixed).
    Remediation: Consider a more targeted search strategy, such as searching for Closes #N, Fixes #N, or Resolves #N patterns, or using the GitHub timeline/events API to find PRs actually linked to the issue.

Low

  • [Style/conventions] Makefile:28 — The help text for script-test still reads "Run shell script tests (post-triage, validate-output-schema)" and does not mention the newly added pre-code-test.sh.
    Remediation: Update the help echo to include pre-code.

  • [Correctness] internal/scaffold/fullsend-repo/scripts/pre-code-test.sh:195-199 — The "bot-pr-does-not-block" test passes empty pr_list_output rather than providing bot-authored PR data and verifying the --jq filter excludes it. The test validates the "no results" path but does not exercise the actual bot-filtering logic. Since the --jq filter runs inside gh and the mock replaces gh, this filter is untested.
    Remediation: Consider an integration-level note or a separate test that validates the jq expression against sample JSON.

Footer

Outcome: request-changes
This review applies to SHA 2858f6857163de8bfff4503bd99f540a17013843. Any push to the PR head clears this review and requires a new evaluation.

@rh-hemartin rh-hemartin self-requested a review April 29, 2026 11:24
@waynesun09
Copy link
Copy Markdown
Contributor

/fix Rebase onto main and resolve conflicts. Fix critical issue number substring matching false positives by replacing --search "${ISSUE_NUMBER} in:body,title" with timeline/cross-reference API or word-boundary regex on closing keywords. Validate FULLSEND_BOT_LOGIN with regex before jq interpolation. Distinguish gh pr list failure from empty results instead of blanket || true. Refactor GH_TOKEN check to skip only the PR check block, not exit the entire script. Add comment idempotency to prevent duplicates on re-runs. Wire up CODE_FORCE parsing or remove override reference. Add missing tests: substring false positive, gh failure path, FULLSEND_BOT_LOGIN override, real bot PR filtering, duplicate comment prevention, malformed gh output.

waynesun09 added a commit that referenced this pull request May 2, 2026
Replace the bash pre-code.sh script with a Go CLI command that runs
in the workflow before sandbox creation. This addresses the review
findings on PR #473:

- Fix skip semantics: write skip=true to GITHUB_OUTPUT and gate all
  downstream workflow steps with if: steps.gate.outputs.skip != 'true'
- Fix dead GH_TOKEN: pass push-token to the gate step env
- Fix search false positives: use timeline API instead of text search
- Add cross-validation between ISSUE_NUMBER/REPO_FULL_NAME/GITHUB_ISSUE_URL
- Add bot-login regex validation against injection

Extend forge.Client with ListIssueTimeline, AddIssueComment,
EnsureLabel, and AddIssueLabels. Implement on both LiveClient
(GitHub API) and FakeClient (test double).

Closes #460

Signed-off-by: Wayne Sun <gsun@redhat.com>
@ascerra
Copy link
Copy Markdown
Contributor

ascerra commented May 6, 2026

/fix

1 similar comment
@ascerra
Copy link
Copy Markdown
Contributor

ascerra commented May 6, 2026

/fix

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

ready-for-review Agent PR ready for human review

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Code agent creates duplicate PR when a human PR already exists for the issue

3 participants