Skip to content

feat(tooling): dispatch confirmed campaign findings - #1864

Closed
gfyrag wants to merge 1 commit into
release/v3.0from
feat/confirmed-finding-dispatch-binding
Closed

feat(tooling): dispatch confirmed campaign findings#1864
gfyrag wants to merge 1 commit into
release/v3.0from
feat/confirmed-finding-dispatch-binding

Conversation

@gfyrag

@gfyrag gfyrag commented Sep 2, 2026

Copy link
Copy Markdown
Contributor

What changed

Adds ai-campaign dispatch to bind an owned confirmed finding to a deterministic work identity, exact-base branch, isolated worktree, immutable claim lineage, and reconstructable ai-campaign-work/v1 artifact.
Extends inspect/next projection, exact PR-marker discovery, claim renewal/takeover preservation, crash recovery, and adversarial bare-remote coverage.
Dispatch does not create Jira issues or PRs, invoke an engineering agent, implement a finding, decide readiness, or merge.

Why

Atomic claims coordinate ownership but do not provide a durable, recoverable engineering-work binding. Starting or resuming confirmed-finding work currently depends on conversation context and manual branch/worktree reconstruction.

Product / operational motivation

Need: A confirmed finding with an owned live claim can be handed to an engineering agent deterministically and recovered after session loss.
Current limitation: Campaign state stops at claim ownership; branch, worktree, Jira, provenance, and future PR identity are not durably bound as one exact work item.
Requirement / constraint: Dispatch must fail closed on stale, ambiguous, expired, conflicting, or raced state; create no product fix; and preserve exact campaign/claim/base/branch identity through remote CAS.
Evidence: Campaign orchestration milestone CONFIRMED_FINDING_DISPATCH_AND_BINDING; adversarial tests in scripts/aicampaign/dispatch_test.go.
Durable repository evidence: docs/technical/contributing/ai-campaign.md, docs/technical/contributing/ai-audit-jira.md, and scripts/ai-campaign-work.schema.json.

Technical decision

Decision: Derive a digest-backed work identity from campaign/finding/qualified-result/Jira identity; create the exact remote work branch with an empty-value lease; attach an isolated worktree; then append the binding to the existing claim through exact CAS and write a reconstructable local artifact.
Why now / why proportionate: The preceding campaign schema, freshness, adoption, and atomic-claim milestones now provide the authoritative inputs needed for deterministic dispatch without expanding into engineering or readiness automation.
Alternatives considered: Conversation-only handoff is not recoverable; branch-name-only binding is ambiguous; automatic Jira/PR/agent invocation would cross explicit authorization and workflow boundaries; replacing the claim backend would duplicate established CAS semantics.

Risk

MEDIUM — this changes distributed orchestration and claim schemas, but not Ledger runtime/product behavior. Exact-CAS transitions, empty-value branch leases, fail-closed classifications, and bare-remote race/crash tests bound the risk.

Validation

  • bash scripts/agent-check
  • Pinned Nix Go 1.26.5: go test ./scripts/aicampaign -count=1
  • Pinned Nix Go 1.26.5 race tests for concurrent dispatch/claim/renew
  • go test ./scripts/... -count=1 during candidate validation
  • Dispatch, claim concurrency, worktree/branch, PR-marker, crash recovery, idempotency, stale-base, and local bare-remote integration tests
  • Mutation challenge: disabling the existing-PR stop made the duplicate-dispatch regression fail; restored implementation passed
  • Trusted pre-commit normalization reached a byte-identical fixpoint

The requirement is satisfied when one owned live confirmed finding yields at most one exact branch/claim binding and another clean session can reconstruct the work item without duplicate Jira, branch, worktree, claim, or PR creation.

Architecture / behavior impact

Tooling only. Extends unreleased ai-claim/v1 and campaign observation schemas with immutable dispatch binding fields and adds local ai-campaign-work/v1. No product storage, API, protobuf, FSM, checker, or compatibility behavior changes.

Review focus

Please focus on CAS transition invariants, last-mile target/PR races, worktree isolation, idempotent crash recovery, and whether structured stop classifications fail closed.

Known concerns

None. Automatic PR creation/publication, resume/event journal, composite readiness, structured failure envelopes, terminal claim cleanup, and multi-finding scheduling remain intentionally deferred.

@NumaryBot

NumaryBot commented Sep 2, 2026

Copy link
Copy Markdown
Contributor

🛑 Changes requested — automated review

Target advancement prevents the advertised crash-recovery path for an already-bound dispatch, leaving local work state unreconstructable through the CLI.

@NumaryBot NumaryBot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

NumaryBot posted 1 new inline finding.

Summary: #1864 (comment)

Comment thread scripts/aicampaign/dispatch.go Outdated
@codecov

codecov Bot commented Sep 2, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 77.01%. Comparing base (fa47912) to head (c6923c5).

Additional details and impacted files
@@               Coverage Diff                @@
##           release/v3.0    #1864      +/-   ##
================================================
- Coverage         77.06%   77.01%   -0.06%     
================================================
  Files               477      477              
  Lines             51141    51141              
================================================
- Hits              39413    39387      -26     
- Misses             8295     8321      +26     
  Partials           3433     3433              
Flag Coverage Δ
e2e 77.01% <ø> (-0.06%) ⬇️
scenario 77.01% <ø> (-0.06%) ⬇️
unit 77.01% <ø> (-0.06%) ⬇️

Flags with carried forward coverage won't be shown. Click here to find out more.

☔ View full report in Codecov by Harness.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@gfyrag
gfyrag force-pushed the feat/confirmed-finding-dispatch-binding branch from be14666 to 1347738 Compare September 2, 2026 14:41

@NumaryBot NumaryBot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

NumaryBot posted 1 new inline finding.

Summary: #1864 (comment)

Comment thread scripts/aicampaign/dispatch.go
@gfyrag
gfyrag force-pushed the feat/confirmed-finding-dispatch-binding branch from 1347738 to 0e4fead Compare September 2, 2026 14:59

@NumaryBot NumaryBot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

NumaryBot posted 1 new inline finding.

Summary: #1864 (comment)

Comment thread scripts/aicampaign/dispatch.go
@gfyrag
gfyrag force-pushed the feat/confirmed-finding-dispatch-binding branch from 0e4fead to 6f6d756 Compare September 2, 2026 15:11

@NumaryBot NumaryBot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

NumaryBot review complete: no remaining inline findings.

Resolved 1 stale NumaryBot review thread (1 fixed, 0 outdated).

Summary: #1864 (comment)

@gfyrag
gfyrag force-pushed the feat/confirmed-finding-dispatch-binding branch from 6f6d756 to c6923c5 Compare September 3, 2026 11:54

@NumaryBot NumaryBot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

NumaryBot posted 1 new inline finding.

Summary: #1864 (comment)

if observed.ObservedTargetSHA == "" {
return dispatchStopped(result, "REMOTE_UNAVAILABLE", "target branch could not be resolved", "REFRESH_REQUIRED")
}
if observed.ObservedTargetSHA != campaign.AuditedSHA {

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

🟠 [major] Resume bound dispatches after the target advances

When the CLI repeats dispatch after the target branch advances, the fresh inspection reports the new target SHA and this early return prevents reading the already-bound claim, so it returns BASE_UPDATE_REQUIRED without reconstructing a missing worktree or artifact. This contradicts the documented recovery behavior in docs/technical/contributing/ai-campaign.md:320-325; defer this check until after determining whether the claim is already dispatched.

@gfyrag

gfyrag commented Sep 3, 2026

Copy link
Copy Markdown
Contributor Author

SUPERSEDED_BY_SIMPLIFICATION

PR #1872 removes the campaign orchestration layer, including dispatch prerequisites and claim state. This PR was not cherry-picked or merged as part of that work.

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

Labels

None yet

Development

Successfully merging this pull request may close these issues.

2 participants