Commit Graph
1813 Commits
Author SHA1 Message Date
Nicky LeachandPaperclip 2a5a323e57 Add execution-owned Runner launch preparation (#16997)
## Thinking Path

> - Paperclip manages work for AI agents.
> - Runner can execute in a different environment from Core.
> - Core owns provider selection, policy, and resource assignments.
> - The execution environment must prepare its own files and paths.
> - A shared contract must keep these responsibilities separate.
> - This PR adds that contract to the Runner execution driver.

## Linked Issues or Issue Description

**Problem or motivation**
Runner transport prepares provider files on the controller before
launch. An execution owner cannot prepare those files in its own
environment through the existing driver.

**Proposed solution**
Add `prepareLaunch` to the execution driver. Supply versioned Core
requirements. Accept a configuration ID, requirements digest, and
ordinary provider descriptor. Validate Core policy and assignments
before launch. Keep existing provider session checks.

**Alternatives considered**
Provider-specific ownership flags would spread the boundary across
backends. Shell preparation would expose process details in the plugin
API.

Refs #16993, #16977. Both prerequisites are merged. This PR now targets
master. Native plugin integration and execution-host preparation follow
separately.

PR #16978 contains an earlier, unmerged prototype. Its
`persistentAgentHome` mode and skill path-map call will be replaced by
this preparation contract before activation. This PR preserves current
master callers of the skill helper.

## What Changed

- Add the optional preparation callback and an explicit Runner artifact
identity.
- Keep the built-in preparation path as the default.
- Validate provider policy and resource assignment identity. Preserve
instruction text when resource locations change.
- Persist the attachment seed after an authority epoch rotation, so a
later controller restart can recover the same run.
- Preserve explicit context removal on a new run. Only an omitted
context can reuse the saved context. Remove its registered instruction
framing when context is removed.
- Save exact requirements and configurations in a private file outside
Runner commands. Retain the active record across failed attachments. Use
current grants for new runs. Keep incompatible session changes rejected.
- Join delayed preparation during startup and warm attachment cleanup.
Retain an unsettled checkpoint after a timeout. Prevent work after
cancellation.
- Use the supplied Runner artifact for interrupted handoff recovery.
Restore the exact target configuration at each handoff crash boundary.
Check the Runner state when the final ACK may be lost.
- Bind the changed shared sources to Copilot profile v51. Preserve the
v50 receipt and current integrity checks.

## Verification

- Workspace typecheck passed.
- All 487 affected Runner transport, control-plane, preparation store,
builder, policy, and profile tests passed on commit `eaf8ae8d1`.
- Workspace build and typecheck passed again on commit
`eaf8ae8d12c7ef2d22d226e4b3f05fdbf79ef4cb`.
- Both warm attachment cleanup regressions fail before the fix. They
pass after the fix. The tests cover delayed preparation, timeout
retention, and concurrent attachment rejection.
- The routed handoff regression fails with a missing controller binary
before the fix. It passes after the fix. The execution owner launches
the real fixture Runner.
- The 200,000-byte instruction regression fails before the fix and
passes after it. Four prepared handoff crash cases verify exact request
and configuration recovery. The store tests verify private file mode,
conflicting records, corrupt data, and active-run retention.
- A real Runner with a controlled fake provider verifies execution-host
paths, exact recovery, warm reuse, incompatible profile rejection, and
cancellation. It does not contact an external provider.
- The regression found undefined settings in strict PRP command hashing.
Requirements now contain only JSON values. The warm transition test
passes without changing PRP validation.
- The broader root suite on the prerequisite finished with 22,420
passing tests, seven failed tests in unchanged Git and diagnostic code,
and two suite setup errors because Cargo was absent from its PATH. This
PR does not claim a passing full root suite.
- The CI Build job passed compilation and production runtime boot, then
its runner received a shutdown signal during the clean public install
check. Other jobs reported lost communication with their self-hosted
runners. The failed jobs passed on retry on the same commit; successful
jobs kept their results.
- The current Superagent security scan is inconclusive because its
pinned merge-base checkout failed or timed out. GitHub rejected the
check rerun request through the available API. This is not a passing
security scan.
- Standard Greptile and Greptile Apex each returned 5/5 on `eaf8ae8d1`.
All review threads are resolved. CI passed on attempt 2. Current checks
have 55 successes, four optional skips, and the inconclusive security
scan described above. The branch is ready, mergeable, and current with
master.
- No live provider qualification or deployment was run.

## Risks

- A preparation owner must store configurations and keep retries bound
to the same task and requirements.
- Copilot source binding requires a new profile identity. This PR does
not claim fresh live qualification.
- The callback is an SDK extension. This PR does not connect it to a
plugin task process owner or add a Launcher endpoint.

## Model Used

- OpenAI Codex, GPT-6. Reasoning and repository tools. The exact serving
model identifier and context size are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-20 14:24:13 -07:00
Devin FoleyandPaperclip a2d26a83fe fix(inbox): keep automatic work out of Mine by default
Keep channel and routine attribution out of Mine unless the person participates directly, is assigned the task, or receives a current addressed request. Apply the same source rules to unread state, archives, and task notifications. Preserve direct comments and current human action requests.

Restore the two expressions damaged by redaction during the earlier master merge.

Co-Authored-By: Paperclip <noreply@paperclip.ing>
2026-10-20 13:46:10 -05:00
Nicky LeachandPaperclip dc6dd23ea4 Add plugin Runner preparation task contract (#16993)
## Thinking Path

> - Paperclip manages work for AI agents.
> - Environment plugins can own Runner tasks.
> - Core selects provider policy and runtime assignments.
> - The execution environment must resolve its own paths and
configuration.
> - The task API needs a preparation exchange before execution.
> - This PR adds that exchange under the existing lease authority.

## Linked Issues or Issue Description

**Problem or motivation**
The environment task API can start a Runner. It cannot return a prepared
provider configuration from Core requirements.

**Proposed solution**
Add a versioned `prepare` request and `prepared` result. Keep the
provider configuration bound to its task and requirements. Check the
same company, run, project, and retained-session authority as
submission.

**Alternatives considered**
A shell preparation command would expose execution details in the API.
Provider-specific ownership flags would spread this contract across
backends.

**Roadmap alignment**
This extends the existing plugin and remote execution APIs. It does not
add a separate execution system.

Refs #16977, #15406. The prerequisite #16977 is merged. This PR now
targets master. Runner transport and provider implementations follow
separately.

## What Changed

- Add strict launch requirements and prepared result schemas.
- Add the preparation capability version and saved configuration ID.
- Apply existing lease and resource checks to preparation.
- Document idempotency, cancellation, recovery, and cleanup
requirements.

## Verification

- `pnpm -r typecheck` passed.
- Plugin SDK build passed.
- All 55 Dot Runner and native Codex server integration tests passed
with Cargo available on PATH.
- All 18 environment task runtime tests passed. These include
preparation dispatch, inactive leases, wrong run identity, unauthorized
projects, result identity, and unknown command rejection.
- The broader root suite on the parent refactor finished with 22,420
passing tests, seven failed tests in unchanged Git and diagnostic code,
and two suite setup errors because Cargo was absent from its PATH. This
PR does not claim a passing full root suite.
- No live provider calls or deployment were run. 
- Standard Greptile and Apex each scored commit
`d3ac15906240b7066f5ff505ed2ffd9ef5dd43c1` 5/5. There are no unresolved
review threads.
- All 55 CI checks passed. Two optional checks were skipped. The branch
is ready and mergeable against master.
- A fresh master fetch and merge-base check passed immediately before
the Apex request.

## Risks

- This defines a new optional worker operation. Existing providers keep
their current operations.
- A provider must validate policy and resource bindings. Schema
validation alone does not validate a concrete provider descriptor.
- This PR defines the exchange. It does not connect native execution to
a preparation provider.

## Model Used

- OpenAI Codex, GPT-6. Reasoning and repository tools. The exact serving
model identifier and context size are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-20 11:41:49 -07:00
Nicky LeachandPaperclip 05f7079ecb Extract Runner provider launch preparation (#16977)
## Thinking Path

> - Paperclip manages work for AI agents.
> - Runner starts providers in local and remote environments.
> - Core selects the provider and task policy.
> - The execution environment supplies paths and installed files.
> - The transport currently combines these inputs in one large method.
> - This PR extracts provider descriptor construction before a separate
plugin preparation change.

## Linked Issues or Issue Description

**What existing behavior does this improve?**
Runner provider launch preparation.

**Current behavior**
The PRP transport constructs each provider descriptor inside startup.
This couples provider configuration to transport lifecycle code.

**Proposed behavior**
The transport calls one built-in descriptor builder. The builder takes
Core provider requirements and execution-environment locations as
separate inputs. File staging, provider validation logic, and session
rules keep their current behavior. The required Copilot source-identity
update changes profile admission metadata.

**Reason and benefit**
This gives launch preparation a separate unit of code. A later PR can
add plugin-owned preparation without adding ownership flags to each
provider backend.

Refs #15406, #16486. This replaces the earlier installed-home
implementation in this PR. #16978 remains a draft.

## What Changed

- Extract provider descriptor construction and its existing permission
helpers.
- Keep helper exports at their previous import path.
- Add focused tests for selection, permissions, locations, and managed
profile rejection.
- Update the Copilot source identity. Bind the extracted file and retain
the v49 history. The source attestation requires v50 after this move.
This changes the admitted profile identity even though no execution
behavior changes are intended.
- Document the boundary and its current limits.

## Verification

- 338 focused builder, transport, Codex security, and Copilot identity
tests passed on the rebased head.
- `pnpm -r typecheck` passed. `pnpm build` passed.
- The full root `pnpm test:run` on the pre-rebase head is still in
progress. It has reported five failures in unchanged server tests. One
isolated failure rejects the word `private` from this checkout's
`/private/tmp` stack path. The full root suite is not reported as
passing.
- All 56 CI checks passed on the rebased head. Four optional checks were
skipped. The branch is mergeable. Workspace typecheck and build passed
on this head.
- Standard Greptile and Apex each scored commit
`47f631883d8f417f6a818500ebe4e77e22cc70b8` 5/5. The rebase onto master
changed only Copilot identity metadata, history handling, and related
tests. `git range-diff` confirms that the launch-preparation
implementation is unchanged. The existing Apex result remains the review
evidence; it did not review the new commit hash.
- No live provider calls or Cloud deployment were run.

## Risks

- A moved field could change provider startup. Existing transport tests
and the new boundary tests check the projection.
- Copilot source binding requires a new identity after the move.
Existing artifacts and retained sessions must match the new admitted
profile. This PR does not claim fresh live qualification.
- This PR does not enable plugin-owned preparation. File materialization
remains in the existing SDK path.

## Model Used

- OpenAI Codex, GPT-6. Reasoning and repository tools. The exact serving
model identifier and context size are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-20 11:20:49 -07:00
DottaandPaperclip 505e1a5582 feat(cases): add persistent workflows with same-task agent handoffs (#16959)
## Thinking Path

> - Paperclip manages AI agents and their work.
> - An agent workflow needs persistent facts and a safe way to transfer
work.
> - Creating a task for each phase splits the objective, discussion,
workspace, and review policy.
> - A case can retain the facts while one primary task moves between
agents.
> - Transfers must survive process failure and preserve private access,
budgets, and completion gates.
> - This pull request adds durable case handoffs, native case tools, and
read-only case pages.
> - Prompts describe the workflow. Existing task controls decide when
work can run and finish.

## Linked Issues or Issue Description

**Problem or motivation**

Prompt-driven agent teams need a persistent record that can move through
triage, implementation, verification, and correction. Ordinary
reassignment does not provide a durable instruction, safe release
barrier, or recoverable delivery receipt for an agent handing off its
own running task.

**Proposed solution**

Extend standalone cases with one primary task, a descriptive phase,
retained access sources, and a handoff ledger. Apply assignments after
source execution and workspace settlement. Deliver each transfer through
the existing durable wake queue. Provide `create_case`, `read_case`,
`update_case`, and `handoff_case` in the native runner. Creation
requires kickoff and explicit workflow text. An explicit handoff to
`done` closes the case when normal task completion is accepted.

**Alternatives considered**

Do not add a workflow engine, filesystem queue, configured state graph,
or one task per phase. The workflow document combines transition prose
with an optional Mermaid `stateDiagram-v2` map. The server does not
execute the diagram. The Pipelines experiment removed on master stays
removed.

**Roadmap alignment**

This extends Agent Reviews and Approvals, Enforced Outcomes, Bounded Run
Recovery, and Activity Log attribution. Existing approval, review,
budget, privacy, workspace, and responsible-user rules remain
authoritative.

Related work: [ordinary handoff wake
recovery](https://github.com/paperclipai/paperclip/pull/15019). This
feature adds a separate persisted case-handoff receipt and release
barrier.

## What Changed

- Add case routing fields, retained access sources, durable handoff
history, delivery leases, and replay-safe migrations.
- Keep the same primary task across agent phases. Preserve each
returning agent's own session and the task's workspace.
- Fence outgoing mutations, wait for provider and workspace release, and
recover delivery without duplicate task comments or runs. Recheck
current assignment permissions as the original caller before applying a
delayed transfer. Scope a run Stop to that run’s own handoff intents, so
repeated old Stop requests preserve newer work. Cancelling terminal
intent without a source run also requires fenced current task ownership,
including native retries and preparation with an old checkout. For Cloud
callers, revalidate current stack membership with an uncached Cloud RPC
and derive owner elevation from the current managed setting.
- Keep case reads, documents, assets, Audit, and live events inside
retained task/project permissions.
- Add native case creation/read/update/handoff tools. Store required
workflow text and initial documents on the first task. Page oversized
case facts and referenced document bodies through the dedicated tool
with bounded UTF-8 JSON, current routing versions, snapshot conflicts,
and current source authorization on every page.
- Add read-only case lists and detail pages, task-style list controls,
compact dotted field tables, linked handoff tasks, and case filters in
Audit.
- Add native/legacy integration tests, migration/restart tests, browser
coverage, and bounded live receipt fixtures. Extend the trusted sandbox
condition to cover the new subscription fixture profile.
- Hide obsolete paused-agent warnings on completed or cancelled task
threads.
- Synchronize the company-switch settings test with React effects after
a CI failure. Preserve its security assertions and production remount
behavior.

## Verification

The branch directly includes master `9ef434fe79`. The required `ci /
verify` and `ci / e2e` gates pass on head `765fccd67c`. [Current-head
CI](https://github.com/paperclipai/paperclip/actions/runs/39464348614)
passes typecheck, build, tests, and all eight browser shards. Security
checks pass. [Greptile gives this exact head
5/5](https://github.com/paperclipai/paperclip/pull/16959#issuecomment-6291156549),
with no unresolved review threads. The optional Paperclip Review check
remains queued because its assigned agent is paused. It is not a
required branch check. No check result was overridden.

Local workspace typecheck and build pass after the master merge, along
with database migration checks, token gates, map checks, Storybook
catalog checks, and the Copilot profile identity check. Standard builds
refresh Runner vendor output. Focused checks pass 2,008
API/paging/context tests and 7 strict case protocol tests. The final
commit changes one test fixture only; its ten tests, UI typecheck, and
token gates pass. No production source changed in that commit.

On current head `765fccd67c`, all **194 critical workflow tests**
executed and passed with no skipped tests in those files:

- 38 Stop/ownership tests, including board completion intent, native
retries, stale Stop, and preparation with an old checkout.
- 2 actual legacy process/HTTP handoff tests, including scratch failure,
a closed-stdio child that continues writing, and recovery through a
fresh worker after the process group stops.
- 5 migration tests, including SQL column metadata, preserved null
authority context, and all six prior-numbering receipts.
- 3 process-settlement and 5 scratch tests.
- 88 handoff-service, 18 heartbeat handoff, and 21 native case-tool
integration tests.
- 7 bounded case/document-read projection tests and 7 strict
protocol-contract tests.

The current CI checkout was `fed65d49`, merging `765fccd67c` into master
`9ef434fe79`. Its new document regressions reconstruct exact
Unicode/escaped bodies and revisions through real native authority and
authenticated HTTP with generic API tools disabled. They cover
case-owned, primary-task, and linked-task documents; routing on every
page; stale document snapshots; access loss and unlinking;
unrelated/foreign/private sources; system documents; and quarantined
content. Active-task document tools retain their existing behavior.
These are current-head test results from the first CI attempt; the
browser-only retry did not rerun these suites.

The full `64fdd3403f` CI failed one separate settings test: after a
company switch, it observed an unsettled API-key draft. The production
component and test were unchanged from prior green source. Production
switches remount both keyed settings layers; the test directly reused an
unkeyed view and used a timer tick instead of waiting for React effects.
The final commit replaces that fixture synchronization with React `act`.
The exact secret-clearing assertions and all timeouts remain unchanged.
The original assertion failure remains recorded; no unchanged retry was
used. The narrow unchanged baseline and fixed fixture each pass 10
tests.

The upstream result-paging merge preserves case capture namespaces and
current asset privacy. Its API integration suite executed 39 of 41 tests
successfully, with two skipped; the optional assigned-result PRP
integration test was skipped. Neither skipped suite is counted in the
194 critical tests or as live provider proof.

All 361 upstream migration entries and SQL bodies remain unchanged. Six
case migrations follow master as 0363–0368 with identical SQL hashes.
Official Drizzle generators produced the combined metadata and five
retained snapshots. Generation reports no schema changes, and the
snapshot drift test passes. The earlier `ce361ae5d0` CI passed on
attempt 1, including its then-current 179 critical tests. Fresh review
later identified unusable document references with generic API tools
disabled; the bounded document reads and ten additional authenticated
HTTP tests address that finding.

The full local `pnpm test:run` attempt was cancelled after this Mac
exhausted PostgreSQL semaphore capacity; it is **not** counted as a
pass. Later database attempts also stopped before assertions or skipped,
including one sandbox socket denial. Two original stale-Stop regressions
did reproduce the bug against the old source. A REST serialization
assertion passed after two preserved database-startup failures. No test
timeout was increased. All 194 assertions listed above executed and
passed in current-head CI. The complete 385-file, 3,963-test UI shard
also passed after the fixture repair.

A configured-provider receipt workflow passed 13 backend checks across
triage → implementation → verification → correction → done, using one
task and four work runs. The saved receipt is revision 2 with total 6
USD; case and task both closed. The original canonical attempt remains
failed because its browser assertion confused the terminal destination
with completed-task tooltips. The corrected full browser verifier passed
on the same retained database and original runs, with no additional
provider calls. The last clean-build browser readback is on
`6a86c54a53`; later changes affect recovery, authorization, bounded
reads, and settlement. Accounted work cost is a $1.010574 rate-card
estimate; provider billing and setup-probe usage are unavailable.

Copilot profile 49 passed the unchanged seven-fixture private protocol
pack (46/46 checks, no retries) and the product file-edit canary after
master's completion-replay change. All 60 bound implementation hashes
remain unchanged on the current source. Historical profile-47/48
identities and results remain intact. See the [profile-49 compatibility
record](https://github.com/paperclipai/paperclip/blob/codex/persistent-case-handoffs/doc/plans/2026-10-20-copilot-completion-recovery-compatibility-v49.json).
This is bounded compatibility evidence, not a fresh full matrix,
installed-package product test, or Daytona rollout.

Preserved CI failures and retries:

- On `20662930ac`, Slack managed setup failed a five-second success
assertion after reload. Its test/application path was unchanged from a
prior green head. One unchanged-source retry passed all 25 tests in that
shard; no source or timeout changed.
- On `9402b4f17a`, two CI workers received shutdown signals at 15:24:19
UTC. Neither log had an assertion failure before interruption. One
unchanged-source retry of each passed all Runner static checks and all
32 tests in browser shard 6; both aggregates passed. The next head,
`7b4374edaf`, passed all CI without retries.
- On `295f289b5a`, serialized shard 9 timed out during its first
device-login test, then the next test found an active login lease.
Direct login/test paths were unchanged from a prior green head. Cold
import plus a timed-out async body using the next test's mutable
actor/store is the supported fixture-race explanation; no request trace
proves that sequence. The original failure remains recorded. One
unchanged-source retry passed all 294 tests in 19 files, including all
41 device-login tests. No login source or timeout changed. The
subsequent `ce361ae5d0` CI passed without retries.
- On `64fdd3403f`, one company-switch settings assertion observed an
unsettled draft. The final test-only commit uses React `act` without
changing assertions, timeouts, or production code. On `765fccd67c`, all
ten settings tests and the complete 385-file, 3,963-test UI shard
passed.
- On `765fccd67c`, browser shard 3 completed the split-handoff
assertions, then cleanup received HTTP 500 from run cancellation after a
one-second PostgreSQL row-lock timeout. The extra chat run was reporting
completed work while teardown began. Cleanup stopped before restoring a
global experiment flag, causing a later assertion to fail. Relevant
production and test paths are unchanged from an earlier green commit.
Stop's lock order is consistent, and no nested self-lock was found; the
exact PostgreSQL blocker was not recorded. One unchanged-shard retry
passed. The original failure, trace, and downstream flag failure remain
recorded. No Stop implementation, cleanup assertion, or timeout changed.
The retry supports intermittent cleanup contention; it does not identify
the original blocking transaction.


## Risks

- Local process transfers require host-owned PID/group absence. Missing
or uncertain termination evidence keeps delivery pending, independently
of scratch setup.
- Handoff admission and task cancellation share execution ownership. New
regression tests cover temporary holds, late source writes, and
uncertain provider termination.
- Retained private sources use an intersection of existing permissions.
This intentionally fails closed when a source is missing or an existing
task cannot preserve that boundary.
- Migrations add tables and indexes. They preserve master history and
can replay over prior feature installs. Migration 0368 adds nullable
internal authorization provenance with no default or authority backfill.
Historical transfers still awaiting release without this context fail
closed; an operator must cancel them and request a new handoff.
- Delayed Cloud handoffs depend on the current Cloud membership RPC. An
unavailable, ambiguous, expired, or mismatched response holds the
handoff for retry; it does not reuse cached authority or grant access.
- Bounded reads reload and reauthorize the selected projection per page.
Underlying work grows with the data size and number of pages. Changed
data or routing requires restarting from offset zero without the old
snapshot.
- Phase names and workflow diagrams remain advisory. They do not satisfy
review or approval gates.
- This is a large, cross-cutting PR. The maintainer requested one PR for
the whole feature; the commits separate data, runtime, UI, and
qualification work.

## Model Used

OpenAI Codex, GPT-6 family, with tool use, code execution, and delegated
code review. The exact deployment model ID and context-window size were
not exposed in the session. Live fixture agents used the explicitly
configured provider model recorded in their test evidence.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-20 12:46:14 -05:00
DottaandPaperclip 2c96f76780 feat(connections): add model-backed prompt injection prevention
Add opt-in OpenRouter checks at existing tool-result boundaries with regex fallback, service accounting, and settings on Connections. Make migration 0362 safe to replay over existing or partially applied schema state.

Co-Authored-By: Paperclip <noreply@paperclip.ing>
2026-10-20 11:32:25 -05:00
Nicky LeachandPaperclip 33cc567f75 Add lease-scoped Runner task hooks to environment plugins (#15406)
## Thinking Path

> - Paperclip coordinates AI agents and their runs.
> - Environment plugins own remote capacity.
> - A plugin needs a typed API to start and stop its installed Runner.
> - Core must derive authority from the saved lease.
> - A lost reply or controller restart must not lose cleanup authority.
> - This PR adds the worker contract and the host task service.
> - Native execution and Runner changes are separate PRs.

## Linked Issues or Issue Description

**Subsystem affected**

Plugin SDK and environment lease services.

**Current behavior**

Environment plugins have no typed Runner task hook. Core cannot dispatch
these tasks or recover their credential handoff through a saved lease.

**Proposed behavior**

Add validated task operations, worker negotiation, company and project
checks, retained-session authorization, and durable cleanup. Keep
credentials out of lease metadata.

**Additional context**

This PR is the first part of a smaller series. Runner installed-home
support is in #16977. Native execution and setup are in #16978. Both are
stacked drafts. This PR does not enable native plugin execution, change
default environments, add a route, or add a database migration.

## What Changed

- Add `supportsTasks` and `onEnvironmentTask` with seven typed
operations.
- Validate worker requests and responses. Reject shell commands and file
transfer operations.
- Pin dispatch and cleanup to the saved company, lease, plugin, and
driver.
- Authorize projects and retained sessions. Validate the current run
separately from the retained PRP identity.
- Save dispatch before the provider call. Fence admission during
cleanup. Require observed process termination.
- Save account writeback authority on the lease. Recover Codex refreshes
through the existing account and secret services.
- Document the task API. Keep the Runner, heartbeat, setup, workspace,
and provider changes in later PRs.

## Verification

- Full `pnpm -r typecheck` and `pnpm build` passed on the separated API
scope.
- 201 focused tests passed: SDK worker dispatch, task validation,
PostgreSQL task lineage, credential recovery, and existing environment
cleanup.
- The lineage test covers a third run, repeated same-run replacements, a
stale submitting run, and exact termination receipts.
- Initial commands hit sandbox socket/IPC restrictions. The permitted
runs executed PostgreSQL and passed. A typecheck attempt lacked Cargo in
PATH; the run with the installed toolchain passed.
- The earlier combined implementation had a full local run with 22,286
passing tests, 120 skips, and eight failed assertions. Task fixture
failures were fixed before this split. Remaining host Git and
temporary-path assertions are recorded in the previous PR revision. This
split does not claim a fresh full local suite pass.
- The standard Greptile review scored this API head 5/5 with no
unresolved threads. CI is green. The single Apex review also scored this
head 5/5 with no actionable findings.
- Fresh API CI lost a self-hosted runner during server shard 9. GitHub
reported lost communication, with no failed test step. The affected jobs
passed on retry without code changes.
- CI on the prior combined head failed an unchanged workspace dev-server
readiness case. No unrelated test fix is included here. Fresh CI is
required for this smaller head.
- This scope does not run a provider or a Cloud test. The user owns
deployment and the intermediate Cloud test.

## Risks

- The API is opt-in. Native plugin execution requires the later
integrations.
- Providers must make task submission idempotent and prove descendant
termination.
- A failed status read or credential export keeps the lease available
for cleanup.
- Codex refresh writeback requires the same active grant, secret
reference, and session epoch. Revocation or account replacement discards
the old refresh.

## Model Used

OpenAI GPT-6 through Codex. Used source inspection, code execution,
tests, and GitHub tools. The exact served model ID and context-window
size are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run local checks and recorded failures and their results
above
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-20 09:14:23 -07:00
DottaandPaperclip 4b05795712 fix(github): reuse review instructions across native turns (#16971)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - GitHub events continue an ordinary task and can reuse its provider
conversation.
> - Each automatic event appended the full review policy and PR
description.
> - Native GitHub follow-ups also repeated task history because only
Slack used the compact path.
> - This pull request separates admitted review configuration from
commit updates.
> - A verified resume sends the current messages and changed
configuration. A fresh session gets full context.
> - This reduces repeated input while retaining review rules and current
tool checks.

## Linked Issues or Issue Description

Refs #13959, #16645, #16901.

**What happened?**

Opening a PR and pushing twice stored three full review prompts. A later
native turn repeated all three in a retained provider conversation.

**Expected behavior**

A new event supplies its commit and event data. The harness delivers
stable review instructions once per retained conversation and
configuration. Fresh sessions receive full instructions.

**Steps to reproduce**

1. Enable automatic GitHub reviews for a repository.
2. Open a PR, let the review finish, and push two new commits.
3. Inspect task messages and the native submitted envelopes. Before this
fix, the policy and old requests repeat.

## What Changed

- Store compact automatic event messages. Fetch the PR description
through the existing metadata tool when needed.
- Load review instructions from processed deliveries bound to the
company, task, agent, and source comments. Preserve each admitted policy
snapshot.
- Use the existing verified native continuation path for complete GitHub
text batches. Deliver configuration changes using a key over endpoint,
PR conversation, revision, and instructions.
- Keep full bootstrap input for fresh sessions and failed resume,
including board follow-ups with no new GitHub event. Retain existing
framing for incomplete batches, attachments, interactions, and recovery.
- Keep the same configuration identity across automatic review,
discussion, and automatic review. Coalesced requests use the last
accepted request's admitted policy.
- Add regression and database coverage. Update the execution contract
and verification recipe.

## Verification

- Red: the new event-size regression failed because policy and PR body
repeated. The GitHub continuation regression failed because it returned
no compact prompt.
- Green: focused policy, continuation, native input, and adapter prompt
tests passed (231 tests). Native resume/fresh-bootstrap cases passed (9
tests).
- The signed-webhook/database case passed at `6296168253`. It checks
configuration edits, queued older snapshots, coalesced policy selection,
discussion continuity, board follow-ups, and company/task/agent/comment
boundaries. The private PostgreSQL template used 12 connections because
the host reached its semaphore limit with the default settings.
- The earlier broad channel/session integration run passed 1,432 tests.
Later review fixes invalidated that run. The latest focused database
case passed after those fixes.
- Reviewer regressions failed against the previous lookup, then passed
with the fix: a mixed-revision batch delivered multiple policies, and a
discussion lost the configuration identity. The board
wake-to-rendered-prompt regression also failed before repair.
- `pnpm -r typecheck`, `pnpm build`, `node scripts/check-maps.mjs`, and
`git diff --check` passed on the final source.
- Full local `pnpm test:run` exposed follow-up/fixture failures during
development. Those cases are fixed and pass separately. The stale run
was stopped after source edits. Full-suite validation for the final
commit passed in CI.
- All required CI checks passed for `6296168253`, including tests,
typechecks, build, and clean public npm install checks. The two
unrelated Storybook checks were skipped.
- A live two-turn Codex smoke could not start: the local macOS sandbox
helper rejected execution of the installed Codex 0.153.4 binary. No live
GitHub/provider acceptance or deployment is claimed.

## Risks

Skipping instructions is safe only after a verified checkpoint resume
with the correct previous run. The full bootstrap remains available if
resume fails. Changed or previously unknown configuration is sent again.
Tests cover these cases. Tool authorization and publication checks still
run under the current server policy. No database migration is required.

## Model Used

OpenAI GPT-6 through Codex, with tool use and code execution. The exact
deployment model identifier and context window are not exposed in this
session. No delegated agents were used.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-20 10:39:17 -05:00
Nicky Leach 34be1b831b Fix duplicate ACPX skills cleanup in test teardown (#16937) 2026-10-20 07:44:28 -07:00
DottaandPaperclip 813e808af4 Remove filesystem history authorization from workspace preparation (#16963)
Remove physical-root source/reader authorization and sticky directory classifications from workspace preparation. Preserve current task/run authority, app-record privacy, credential authorization, containment, and lifecycle/publication integrity.

Validate replacement selections against persisted new inputs and refresh verified checkout ownership so bounded reuse survives earlier workspace relocation. Add real PostgreSQL/Git regressions, a reproducible history-scaling benchmark, and documentation.

Full CI passed all 48 jobs and Greptile scored 5/5 at 3d5da6c259. Five preparation-guard medians improved from 20,512.99 ms to 52.22 ms on the 8,500-workspace fixture; these are not end-to-end startup timings.

Co-Authored-By: Paperclip <noreply@paperclip.ing>
2026-10-20 09:19:59 -05:00
DottaandPaperclip d84061b923 fix(runner): recover journaled completion proposals (#16962)
## Thinking Path

> - Paperclip manages AI agents and their work.
> - Native runs preserve provider sessions across controller restarts.
> - A completion event can reach durable storage before the next session
checkpoint.
> - Recovery advanced the event cursor but lost the saved completion
proposal.
> - The completed turn then appeared to need another provider turn to
report its result.
> - This change restores the exact active turn's proposal before
advancing the cursor.
> - Recovery can finalize completed work without repeating its external
actions.

## Linked Issues or Issue Description

**What happened?**

After a controller restart, a native run could fail with
`native_finalization_missing` even though `run.result.proposed` was
already durable. The recovered driver skipped that event when its cursor
advanced, so the result was absent from its state. Automatic disposition
retries could then encounter outstanding tool receipts and exhaust
recovery.

**Expected behavior**

Restore the saved result for the exact active turn. Wait for provider
termination, then use normal finalization. Do not start another provider
turn to repeat completed work.

**Steps to reproduce**

1. Start a native Codex task and save its active-turn checkpoint.
2. Persist its completion proposal, then lose the controller before
another checkpoint.
3. Recover the same run after the provider completes. Before this
change, finalization reports a missing result.

**Paperclip version or commit**

Reproduced on `92b238137b`. The repair is based on `7c247243e5`.

**Deployment mode**

Native Runner with Codex. The incident used a remote sandbox; the
regression covers controller event recovery.

Related: #12845 and #15297. The older #12241 addresses provider process
continuity; this change repairs the controller's saved event projection.

## What Changed

- Restore valid completion proposals for the checkpoint's exact active
turn during event replay.
- Reject conflicting, invalid, or incorrectly bound proposals. Ignore
proposals from another turn and prevent adoption after a newer turn
starts.
- Keep provider termination and normal finalization as separate
requirements.
- Add eight behavioral cases using the real Codex driver and a simulated
transport, and document the recovery contract and verification scope.

## Verification

- Red: the new restart regression failed with
`native_finalization_missing` before the production change.
- Green: 254 tests passed across the native runtime, backend adapter,
and Codex recovery suites. The new cases check no repeated provider
work, no early finalization, duplicate proposals, conflicts, invalid
proposals, and stale turn/session bindings.
- `node scripts/check-maps.mjs` and `git diff --check` passed.
- `pnpm -r typecheck` and `pnpm build` passed locally. All CI gates
passed on `2ac025a15c`; Greptile rated that commit 5/5 with no
outstanding findings. The full local `pnpm test:run` was started after
completing the embedded PostgreSQL installation, then stopped while
still running once the complete CI test matrix passed; it is not
reported as a completed local run.
- Real local acceptance passed on `2ac025a15c` with the production Rust
Runner transport, Codex CLI `0.160.0`, and `gpt-6.1-sol` on macOS arm64.
Persisted the completion proposal while retaining the older active-turn
checkpoint; let the provider finish without persisting its later
controller events; stopped the exact owned runner/provider; recovered
the same provider session and turn. Observed one accepted result, one
durable `turn.start` command, and one line in the receipt file. Hosted
sandbox restart and recovery of the original stopped task have not been
performed.
- Initial setup failures are retained: dependency drift caused
diff-viewer type errors, and skipped PostgreSQL postinstall links
prevented database startup. Dependency alignment and the package
postinstall repaired those local prerequisites. Probe setup iterations
failed on a direct-provider response schema, invalid probe input fields,
and an original provider that still held its writer lock. Acceptance
uses the production transport, validated input, and exact-owner
shutdown. No production code changes were made for those probe setup
failures.

## Risks

- A stale proposal could finalize the wrong work. Recovery requires the
checkpoint's active turn and matching run, session, and source. It
rejects conflicting results and waits for provider termination.
- The change uses the existing paginated recovery scan. It adds no
database query per event or new retry allowance.
- No schema migration or change to task authorization is included.

## Model Used

OpenAI GPT-6, running as Codex with reasoning, tool use, and code
execution. The exact served model snapshot and context-window size are
not exposed in this session. The live acceptance probe uses
`gpt-6.1-sol`.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-20 09:09:22 -05:00
628993fc59 fix(runner): name the tool receipts that block the next provider turn (#16961)
When a resumed run cannot start a turn because the semantic tool bridge
still holds pending or unsettled completed receipts, the error now names
each blocking receipt by operation and call ID (bounded to four per set).
Tool input and result content stay inside the bridge. Adds an integration
test covering the four-receipt limit and the trailing "...".

Co-Authored-By: Paperclip <Paperclip-Paperclip@users.noreply.github.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-20 06:49:17 -07:00
DottaandPaperclip 96824a71d1 fix(db): migrate connector hooks on SQL_ASCII databases (#16958)
## Thinking Path

> - Paperclip manages work for AI agents.
> - Server startup applies database migrations before accepting work.
> - Some older embedded databases use SQL_ASCII encoding.
> - Migration 0355 uses a Unicode escape literal that PostgreSQL rejects
on those databases.
> - A source rebuild can pass but the updated server cannot start.
> - This change makes that migration portable and preserves its shipped
receipt.
> - Existing databases retain their newer connector triggers during
upgrades.

## Linked Issues or Issue Description

**What happened?**

A source deployment failed at startup with `conversion between UTF8 and
SQL_ASCII is not supported`. Migration 0355 could not compile its
connector policy function on an older embedded database. The previous
app was restored while this repair was prepared.

**Expected behavior**

Supported legacy databases complete startup migrations. Connector
selector trimming matches JavaScript `trim()`. A database that already
applied 0355 must not replay it over the later 0356 connector trigger
definition.

**Steps to reproduce**

Create a PostgreSQL database from template0 with SQL_ASCII encoding,
then apply the current migration chain. The new regression fails with
the observed conversion error before this change.

**Paperclip version or commit**

Reproduced on `92b238137ba716cdf1746dd49969e2f5ab7af8fe`. The branch
includes current master `f57ed25385`.

**Database mode**

Embedded PostgreSQL 18.1; legacy SQL_ASCII database. The UTF-8 path is
also covered.

Related background: #645 fixed encoding for new databases. Existing
SQL_ASCII installations still need portable migrations. #16956 fixes a
separate workspace lock timeout that motivated this deployment.

## What Changed

- Build the whitespace pattern from UTF-8 bytes instead of a Unicode
escape literal.
- Match whole whitespace sequences so SQL_ASCII does not trim partial
multibyte characters.
- Recognize the original 0355 checksum as a valid receipt. This prevents
replay of its older trigger body over 0356.
- Add real PostgreSQL coverage for both encodings, selector behavior,
and preservation of the later trigger definition and receipt count.
- Document the legacy encoding and migration-history contract.

## Verification

- Red: SQL_ASCII migration failed with the same conversion error; UTF-8
passed.
- Second red: fixing only the SQL caused an existing receipt to replay
and overwrite the later connector function.
- Green: 29 focused tests passed across the new regression, migration
replay tests, and database client tests.
- Rebased regression: all 29 focused tests passed.
- `pnpm -r typecheck`, `pnpm build`, and `pnpm --filter @paperclipai/db
check:migrations` passed.
- Linux ARM64: clean build and 37 focused tests passed, including both
encoding and workspace-lock regressions.
- Live acceptance: the same legacy SQL_ASCII database completed all
seven remaining migrations. The server reports the tested commit and
healthy status. The restart report has no lost runs.
- All 55 current-head checks passed; two unrelated Storybook checks were
skipped. Full test, typecheck, build, runner, release, and E2E CI gates
passed. The complete suite ran in CI; local verification used focused
tests.
- Greptile reviewed this exact commit at 5/5 with no findings.
- Preserved failures: the initial unmodified-master startup failed at
migration 0355 and was rolled back. A later build-cache path error in
the deployment commands was corrected before the successful clean build;
it required no source change.

## Risks

The migration content changes, so receipt compatibility matters. The
original checksum remains recognized to avoid replaying historical DDL.
The tests compare complete later function definitions and receipt
counts. The whitespace pattern contains encoded bytes; tests cover every
ECMAScript whitespace character and preserve non-whitespace Unicode
input. Database data and schema shape are unchanged by this repair.

## Model Used

OpenAI GPT-6 through Codex, with repository tools, code execution, and
browser verification. The exact served model variant and context window
are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-20 07:56:32 -05:00
DottaandPaperclip 92b238137b Connect and configure GitHub Copilot through Apps (#15705)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Apps and AI Connections store credentials and govern access to agent
runtimes.
> - Users need a supported saved-token connection and config values that
survive save and reopen.
> - The release must preserve saved-token access and task lifecycle
guarantees.
> - This pull request will connect Copilot through the normal Apps and
AI Connections path.
> - The benefit is a reviewable part of the Copilot production release.

## Linked Issues or Issue Description

Refs #15701 and #15703. Supersedes setup work in #15562. Base: #15703.
Next: #15706.

## What Changed

- Require configuration update authority before Copilot
credential-bearing model discovery; default to the saved environment and
preserve explicit selection for editors.

- Keep Copilot discovery passive during reconnect reconciliation;
refresh on explicit opening, account/environment changes and reconnect.

- Add GitHub AI token connections with encrypted storage, ownership,
grants and audit logging.
- Keep repository access separate from Copilot runtime authentication.
- Probe the selected environment without sending a model prompt and
preserve authenticated model selection through save/reopen.
- Keep fresh execution admission consistent with normal Copilot setup;
persist task model choices without changing provider or permission
policy.
- Refresh authenticated models after reconnecting the same saved Copilot
account, including recovery from a previous authentication error.
- Apply the additive provider-default constraint migration through the
normal generated migration workflow.

## Verification

Runtime #15701 is merged at `d855e550ad8d2a267312983f26457aabf5393c3a`.
History #15703 is merged at `df80616d98119cbf5abd40549794d9980a5fabf6`.
Remaining source
[`42bcbd61299655f7e37aabe6bb5f19bba770ad1d`](https://github.com/paperclipai/paperclip/commit/42bcbd61299655f7e37aabe6bb5f19bba770ad1d)
contains the four-file authorization repair. The remaining PR trees
preserve six nonoverlapping files from the newer public mainline
managed-settings fix and the CI-owned lockfile. No unrelated provider is
enabled.

The security finding is repaired: existing-agent discovery requires
`agent_config:update` before connection selection or token resolution.
The saved environment is the default. Authorized editors can select a
prospective environment. Both denied board-viewer and agent-reader
regressions fail on the original source. All49 route tests and server
typecheck pass with the fix. Denied requests perform no connection
selection, credential resolution or probe. Current-head security scans
pass on both remaining PRs; the repaired thread is resolved.

Copilot CLI1.0.88 and profile47 retain digest
`sha256:55044aa235e88b3fe36ec8a556ee1e3382590870aab907e4462ef7d64af49cea`.
The [qualification
record](https://github.com/paperclipai/paperclip/blob/42bcbd61299655f7e37aabe6bb5f19bba770ad1d/doc/plans/2026-10-20-copilot-qualification-v47.json)
reports20/20 Product cells,154 assertions and7/7 protocol cases,46
assertions against frozen normal installed source
`c2616370800f5f6df45246b0890ba35a7cd2faab`. The exact qualification
model is `gpt-5.6-luna`. Every passing Product case confirms cleanup.
Original failures remain recorded; automatic behavior retries are
disabled. The route-only authorization repair changes no bound
runtime/profile bytes and does not relabel the frozen campaign.

The ordinary installed remote journey passed saved-token selection,
model discovery, normal UI save/reopen, metadata-only Test, completed
task, accepted receipt and exact19-byte browser download. An open model
catalog caused no additional discovery requests during117seconds. Actual
installed runtime smokes passed on macOS ARM64, macOS x64 under Rosetta
and native Linux x64 on Daytona. Raw token browser entry was not
exercised; encrypted connection creation used the normal API.

The first Daytona file attempt timed out during delayed semantic
dispatch; its precise stalled layer remains unresolved. Independent
ordinary remote delivery and the other19 Product cells passed before one
instrumented recheck passed8/8 with unchanged source,prompt,assertions
and deadlines. No causal latency repair is claimed.

Before the authorization repair, all four final PR heads passed required
verify/E2E and fresh Greptile5/5 reviews with zero unresolved threads.
Current-head CI/review is running for the two repaired heads. Local
focused checks retain129 connection,59 runner,72 shared-eval and88
recovery/workspace passes, plus migration safety and token gates. The
additive Copilot migration is361; released master history is preserved.

[Cloud normal-package
run39414239704](https://github.com/paperclipai/paperclip/actions/runs/39414239704)
builds the pre-security source4f3f. All four native producers and Linux
package assembly pass; the final clean installed consumers are
finishing. All18 retained archives match their hashes;37,863 regular
files contain zero selected credentials. That package does not contain
the later route repair. The actual final published package must include
it and pass the local/Daytona live canaries. The frozen Daytona image
remains published and independently verified. No separate full-image
scan is claimed. Docker builds run in the cloud.

**Remaining:** current-head CI/review, setup and qualification merges,
final publication, and ordinary local/Daytona canaries against the
actual shipped package. The user explicitly authorizes the maintainer
review override; CI remains a merge gate. No production deployment is
claimed. Provider USD remains unknown and GitHub-attributed.

## Risks

Bad credentials, missing entitlement, runtime installation and
unavailable models must remain distinct failures. A connection must not
adopt ambient credentials. The constraint migration changes accepted
provider values, with no credential-storage migration.

Current-master NewAgent fixture extraction is retained. Copilot cases
use that shared support and test both passive discovery and explicit
reconnect under the same setup lifecycle.

The onboarding retry regression shares the component suite’s
saved-connection, authenticated-model, draft, agent-list, hire and
render lifecycle fixtures. Keeping it beside the existing onboarding
failures makes adoption versus duplicate hire observable under the same
lifecycle; this is the concrete cohesion reason for the existing large
test file.

## Model Used

OpenAI Codex, based on GPT-6. The exact serving model ID and context
window are not exposed in this task. Used for code changes, review and
tool-assisted verification.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [ ] All Paperclip CI gates are green
- [ ] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-20 07:02:22 -05:00
DottaandPaperclip df80616d98 Preserve Copilot historical runtime attestations (#15703)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Runner recovery must distinguish old profile identities from the
current launch identity.
> - The long integration produced historical attestations that must
remain inspectable after consolidation.
> - The release must preserve saved-token access and task lifecycle
guarantees.
> - This pull request will retain the historical Copilot profile records
without granting old profiles launch access.
> - The benefit is a reviewable part of the Copilot production release.

## Linked Issues or Issue Description

Refs #15701. Supersedes the provenance work in #15561. Base: #15701.
Next: #15705.

## What Changed

- Retain historical Copilot profile attestations as separate immutable
records.
- Preserve the mainline and candidate histories when version numbers
overlap.
- Keep exact current-profile launch checks in the runtime PR.

## Verification

Final reviewed source
[`4f3f1af807d2ed21adabb04c2f27f4df9c4bc8d5`](https://github.com/paperclipai/paperclip/commit/4f3f1af807d2ed21adabb04c2f27f4df9c4bc8d5)
includes master `cde944ed75648adfb569e86133adc8b118b55dd6`. The combined
four-part PR tree matches it except for the CI-owned lockfile. Every
prior public PR head remains an ancestor. Released master migrations
remain unchanged; Copilot adds migration361. No unrelated provider is
enabled.

Copilot CLI1.0.88 and profile47 retain digest
`sha256:55044aa235e88b3fe36ec8a556ee1e3382590870aab907e4462ef7d64af49cea`.
The pending qualification marker is removed. The [qualification
record](https://github.com/paperclipai/paperclip/blob/4f3f1af807d2ed21adabb04c2f27f4df9c4bc8d5/doc/plans/2026-10-20-copilot-qualification-v47.json)
reports **20/20 Product cells,154 assertions;7/7 protocol cases,46
assertions** against frozen installed application
`c2616370800f5f6df45246b0890ba35a7cd2faab`. Both environments use the
exact authenticated model `gpt-5.6-luna`. Every passing Product case
confirms cleanup. Automatic behavior retries are disabled. Original
failed attempts remain recorded.

The ordinary installed remote journey passed saved-token selection,
authenticated model discovery, normal UI save/reopen, metadata-only
Test, task completion, accepted receipt and an exact19-byte browser
download. An open model catalog caused no new discovery requests
during117seconds. Actual installed runtime smokes passed on macOS ARM64,
macOS x64 under Rosetta and native Linux x64 on Daytona. Raw token
browser entry was not exercised; the encrypted connection was created
through the normal API.

The original Daytona file attempt timed out during delayed semantic
dispatch. Its precise stalled layer remains unresolved. Independent
ordinary delivery and the other19 cells passed before one instrumented
recheck passed8/8 with unchanged source,prompt,assertions and deadlines.
No causal latency repair is claimed.

After current-master reconciliation,129 connection tests,59 runner
tests,72 shared eval tests and88 recovery/workspace tests pass.
Migration generation/safety, unchanged profile identity and UI token
gates pass. Prior required CI was green. Fresh exact-head required CI
and E2E are green for all four updated heads. Each has a fresh
Greptile5/5 review and zero unresolved review threads. The [final
normal-package cloud
build](https://github.com/paperclipai/paperclip/actions/runs/39414239704)
is running. Recursive typecheck,full CI test shards,build and all8
browser shards pass. These checks cover the final source; no additional
local full-suite pass is claimed.

The [frozen image
build](https://github.com/paperclipai/paperclip/actions/runs/39334401638)
and [original normal package
build](https://github.com/paperclipai/paperclip/actions/runs/39334407471)
passed. The exact image is published and independently retrieved
anonymously. No separate full-image scan is claimed. All18 original
normal archives were scanned with zero selected credentials. Docker
builds run in the cloud. Provider USD remains unknown and
GitHub-attributed.

**Qualification is complete on the recorded frozen build. Normal
protected merge, automatic master canary publication and final
shipped-package local/Daytona canaries remain. No production deployment
is claimed.**

## Risks

Historical records are evidence only. They must not be treated as
current qualification or as permission to launch an old provider
profile.

## Model Used

OpenAI Codex, based on GPT-6. The exact serving model ID and context
window are not exposed in this task. Used for code changes, review and
tool-assisted verification.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [ ] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-20 11:44:30 +00:00
DottaandPaperclip d855e550ad Finish Copilot native runtime on current master (#15701)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Paperclip Runner controls provider processes, permissions and task
completion.
> - Copilot needs its pinned distribution, native message identities and
accepted semantic completion receipts.
> - The release must preserve saved-token access and task lifecycle
guarantees.
> - This pull request will keep the current completion and recovery
fixes while adding the Copilot runtime.
> - The benefit is a reviewable part of the Copilot production release.

## Linked Issues or Issue Description

Refs #14434. Supersedes the runtime work in #15560. This is the first PR
in the stack; #15703, #15705 and #15706 follow. Related alternative
adapter work: #15881. This change uses the shared Runner path.

## What Changed

- Pin Copilot CLI 1.0.88 and bind the integrated implementation as
profile45.
- Keep native instruction, permission, receipt, process ownership and
cancellation boundaries.
- Preserve current master completion continuation and remote
verification behavior. Other provider release identities stay unchanged.

## Verification

Final reviewed source
[`4f3f1af807d2ed21adabb04c2f27f4df9c4bc8d5`](https://github.com/paperclipai/paperclip/commit/4f3f1af807d2ed21adabb04c2f27f4df9c4bc8d5)
includes master `cde944ed75648adfb569e86133adc8b118b55dd6`. The combined
four-part PR tree matches it except for the CI-owned lockfile. Every
prior public PR head remains an ancestor. Released master migrations
remain unchanged; Copilot adds migration361. No unrelated provider is
enabled.

Copilot CLI1.0.88 and profile47 retain digest
`sha256:55044aa235e88b3fe36ec8a556ee1e3382590870aab907e4462ef7d64af49cea`.
The pending qualification marker is removed. The [qualification
record](https://github.com/paperclipai/paperclip/blob/4f3f1af807d2ed21adabb04c2f27f4df9c4bc8d5/doc/plans/2026-10-20-copilot-qualification-v47.json)
reports **20/20 Product cells,154 assertions;7/7 protocol cases,46
assertions** against frozen installed application
`c2616370800f5f6df45246b0890ba35a7cd2faab`. Both environments use the
exact authenticated model `gpt-5.6-luna`. Every passing Product case
confirms cleanup. Automatic behavior retries are disabled. Original
failed attempts remain recorded.

The ordinary installed remote journey passed saved-token selection,
authenticated model discovery, normal UI save/reopen, metadata-only
Test, task completion, accepted receipt and an exact19-byte browser
download. An open model catalog caused no new discovery requests
during117seconds. Actual installed runtime smokes passed on macOS ARM64,
macOS x64 under Rosetta and native Linux x64 on Daytona. Raw token
browser entry was not exercised; the encrypted connection was created
through the normal API.

The original Daytona file attempt timed out during delayed semantic
dispatch. Its precise stalled layer remains unresolved. Independent
ordinary delivery and the other19 cells passed before one instrumented
recheck passed8/8 with unchanged source,prompt,assertions and deadlines.
No causal latency repair is claimed.

After current-master reconciliation,129 connection tests,59 runner
tests,72 shared eval tests and88 recovery/workspace tests pass.
Migration generation/safety, unchanged profile identity and UI token
gates pass. Prior required CI was green. Fresh exact-head required CI
and E2E are green for all four updated heads. Each has a fresh
Greptile5/5 review and zero unresolved review threads. The [final
normal-package cloud
build](https://github.com/paperclipai/paperclip/actions/runs/39414239704)
is running. Recursive typecheck,full CI test shards,build and all8
browser shards pass. These checks cover the final source; no additional
local full-suite pass is claimed.

The [frozen image
build](https://github.com/paperclipai/paperclip/actions/runs/39334401638)
and [original normal package
build](https://github.com/paperclipai/paperclip/actions/runs/39334407471)
passed. The exact image is published and independently retrieved
anonymously. No separate full-image scan is claimed. All18 original
normal archives were scanned with zero selected credentials. Docker
builds run in the cloud. Provider USD remains unknown and
GitHub-attributed.

**Qualification is complete on the recorded frozen build. Normal
protected merge, automatic master canary publication and final
shipped-package local/Daytona canaries remain. No production deployment
is claimed.**

## Risks

Shared Runner behavior can affect active tasks. Exact profile admission
rejects stale runtime identities. The final campaign and installed
canaries remain release gates.

## Model Used

OpenAI Codex, based on GPT-6. The exact serving model ID and context
window are not exposed in this task. Used for code changes, review and
tool-assisted verification.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [ ] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-20 06:31:47 -05:00
b448710986 fix: derive startup warmth from per-layer reuse evidence (#16908)
## Thinking Path

> - Paperclip helps people manage AI agents and inspect their work.
> - Agent startup can reuse a lease, workspace, Runner, process, or
session.
> - A session ID can remain the same when other resources are new.
> - The old cold/warm label did not show these separate decisions.
> - This pull request records closed reuse receipts and derives labels
from them.
> - Reports now show partial reuse and missing evidence.

## Linked Issues or Issue Description

Refs #11685. That issue tracks a specific ACPX fingerprint repair. This
change records reuse evidence across startup resources. It does not
repeat that repair.

**What existing behavior does this improve?**

Startup labels in the operator trace and Product E2E reports.

**Current behavior**

A cached runtime or a continuous session can suggest a warm startup even
when workspace staging or provider launch work occurs.

**Proposed behavior**

Record each layer's reuse decision and a closed reason. Record observed
provider launch counts. Use `warm`, `cold`, `partial_reuse`, or
`unknown` from those receipts. Keep old runs unknown when they have no
receipts.

## What Changed

- Add local run-log receipts for the lease, workspace, Runner, provider
process, and provider session.
- Count physical ACPX launches, including respawns. Preserve the reason
for a new process.
- Reuse native workspace adoption and session lifecycle evidence. Keep
native and bridged remote provider-process reuse and launch counts
unknown where physical evidence is absent.
- Show the per-run summary in retained results and the dashboard. Keep
missing legacy values explicit.
- Set the legacy trace boolean only for fully evidenced cold or warm
startup. Keep the operator OTLP gate. Add no first-party Telemetry.
- Test full reuse, workspace invalidation, two direct provider launches
with session continuity, and report generation.
- Start the final diagnostic write without waiting for persistence. Keep
lease cleanup independent of a stalled event sink.
- Keep remote provider evidence unknown after runtime setup fails or the
host relay starts twice.
- Align a stale Pi support-test expectation with current master profile
28 and its suite fingerprint. Keep the qualification rules unchanged.

## Verification

- Passed: all 319 runtime, startup-timing, reuse-summary, and native
workspace-history tests. Disposable local Git tests used the native Git
binary.
- Passed on the current commit: all 2,768 Runner E2E support tests
across 128 files. This includes report and history tests for generated
HTML and normalized JSON.
- Passed: `pnpm --filter @paperclipai/adapter-utils typecheck`.
- Passed on `df60f8dbdbfcb6d80c84cd3bf563f8d58b2f9f03`: all PR CI gates,
including repository typecheck and build, all test shards, and browser
tests. Both automated reviews are 5/5. GitHub reports 55 successful
checks, one neutral review, and two skipped Storybook checks.
- The first server shard run failed because an unchanged
workspace-runtime fixture did not accept health connections within 10
seconds. Its isolated local test and the single failed-jobs rerun both
pass. This establishes recovery; the cause of the first timeout remains
unknown.
- Passed in the hosted source run on this exact commit: recursive
typecheck, token gates, the large Runner E2E typecheck, Runner E2E unit
tests, and build. The retained `source.txt` matches this PR head.
- The extra unsharded `pnpm test:run` reached its 60-minute limit (exit
124). It has no complete verdict. The broad workflow therefore reports
failure. No assertion-failure marker appears in the retained partial
log. Full-suite acceptance uses the passing canonical PR CI partitions.
A read-only inventory check found no gaps across 1,023 general server
files, 161 serialized suites, and 20 workspace projects. The separate
chat/native Runner lanes cover the excluded server files. No tests or
timeouts were weakened. The local environment has 4 GiB of memory. Use
CI for the large Runner E2E typecheck.
- The initial report tests failed because the harness could not resolve
package imports from the repository root. Relative source imports fixed
that failure.
- The first broad local run had timeouts from the environment Git
bridge. Native Git resolves the ancestry timeout and all runtime tests
pass. The added report fixture lacked its required screenshot; the
corrected report tests pass. A stale master assertion expected Pi
profile 27, while the generated profile is 28. Updated its expectation
and exact suite fingerprint; all 78 targeted support tests pass. The
clean full support run passes all 2,768 tests.
- The three review regression cases failed before repair. They showed
remote counts of zero and two, and a completed run that waited for the
final diagnostic sink. They now pass. The stalled-sink case keeps
persistence pending while the run returns, both bridge stops run once,
and the staging lock map becomes empty.
- Hosted evidence for this commit: [source
verification](https://github.com/paperclipai/paperclip/actions/runs/39335475416),
[retained command logs and status
table](https://github.com/paperclipai/paperclip/actions/runs/39335475416/artifacts/12228829282).
All listed commands exited zero except the incomplete unsharded test
command described above.
- The physical-launch test drives the executor's spawn callback twice.
The native workspace test uses real Git repositories and verifies reuse
and invalidation. These are deterministic tests, not a paid provider
qualification campaign.

## Risks

- Consumers must handle `partial_reuse` and `unknown`. Partial evidence
no longer produces a legacy cold/warm boolean.
- Native and remote bridged provider process evidence is still
unavailable on some paths. The report shows unknown values for those
paths.
- Receipt emission is best effort. Missing receipts reduce confidence in
a label and must not change execution or settlement.
- No schema migration, first-party Telemetry event, or endpoint default
changes are included.

## Model Used

OpenAI Codex, based on GPT-6, used reasoning, repository tools, and code
execution. The exact provider model ID and context window are not
exposed to this session. The existing implementation checkpoint was
preserved from the earlier agent run.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
Co-authored-by: devinfoley <139239+devinfoley@users.noreply.github.com>
2026-10-19 21:52:57 -05:00
DottaandPaperclip bc091f0a21 fix(recovery): recover retained workspaces before saved messages (#16906)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - A stopped run can leave useful files in its original sandbox.
> - The server keeps that sandbox when it cannot confirm file copyback.
> - The task can then save new user input but offers no safe way to
recover the files.
> - A retry of the old agent turn can repeat work that already finished.
> - This pull request recovers files through the existing workspace
owner and delivers only saved human input.
> - The user can recover a task without certifying infrastructure facts
or losing completed work.

## Linked Issues or Issue Description

Refs #16883 and #16835 for publication receipts and verified process
termination.
Related: #16478 clears stale holds after copyback already succeeded.
This change performs the missing export and records its proof. #16901
manages the main GitHub response comment and does not perform workspace
repair.

**What happened?**

A failed run retained its workspace. A later user message stayed saved
behind a file-repair hold. The task asked the user to verify process
termination and file recovery but offered no repair control. Sending a
message could show an optimistic Working state and move the task to Todo
before admission succeeded.

**Expected behavior**

The harness should recover the original files when it can prove
ownership and termination. It should preserve newer edits and completed
operations. Only waiting user input may start another turn. Missing
evidence must keep the source held with a specific explanation.

**Steps to reproduce**

1. Interrupt a sandbox run before workspace finalization succeeds.
2. Retain its exact allocation and save a user follow-up.
3. Observe the file-repair hold and missing end-user repair path.

## What Changed

- Add source-bound background recovery for native and legacy runs. An
accepted native result is not required.
- Share the physical copyback lock and durable owner. Resume only the
exact stopped allocation, export files, verify persistence and obtain a
fresh stop receipt.
- Persist retry limits and idempotent requests on the existing recovery
record. Limit each server to two background exports. Add an indexed
candidate scan and a separate cleanup obligation.
- Add a task-editor recovery endpoint. Deny agents and viewers. Reject
caller-supplied stop or repair claims.
- Deliver waiting human input once through ordinary admission. Preserve
pause, approval, budget and assignment gates. Require historical
conversational-adapter evidence for legacy-to-Runner continuation.
- Include exact GitHub publication receipts in continuation context.
Preserve unknown effects and the original failed run.
- Show observed recovery progress, a transient-failure retry action and
specific service blockers. Keep saved messages visible. Suppress false
startup feedback and implicit Todo promotion behind a file hold. Hide
unavailable workspace links.
- Update execution semantics, capability maps and production-component
stories.

## Verification

- Red: the original read model failed the new recovery-progress
assertion; the other 23 checks in that file passed.
- Passed: recovery regressions with 28 cases with real PostgreSQL,
files, tar and Git operations. Lifecycle provider calls are controlled
test boundaries. Coverage includes native/legacy export, concurrent
owners, rollback after export, interrupted archive export with a new
database connection, lost replies, historical discovery, durable retry
limits, separate cleanup and saved-input delivery. The actual candidate
query uses its partial index with 3,000 unrelated history rows. A first
automatic repair can bind verified old-controller stop proof without an
accepted native result. Review also reproduced and fixed export-only
continuation and cleanup lost after a committed repair. Cleanup remains
discoverable without waiting input and after task reconciliation.
- Passed: two GitHub integration cases verify that continuation context
carries the existing publication receipt and does not write another
response. Company and task boundaries are checked.
- Passed: 293 continuation, workspace-sync, platform-receipt and OpenAPI
checks. After file repair, actual dispatch retains pause, cancellation,
approval, real budget-policy and assignment gates.
- Passed: 174 route checks, including editor admission, agent/viewer
denial and rejection of fabricated repair claims.
- Passed: 351 task detail, workspace properties and comment-reopen
checks after updating the new read boundaries and asynchronous
workspace-link expectations. Two new route cases keep held tasks Blocked
when a comment is saved.
- Passed: 265 task-thread and recovery-notice checks. The broader
continuation suite also passed; its new legacy migration case first
exposed a gap that the focused recovery suite now covers.
- Passed after rebase: `pnpm -r typecheck` and `pnpm build`. The later
master merge adds an unrelated permission migration; recovery migration
generation and safety checks passed after the merge.
- Passed: token gates, module boundaries, map structure and migration
checks. The recovery index is migration 0360 after current master.
- Browser: inspected the production recovery component and its
retry-to-queued transition with fixture data. The first dev dependency
load failed; a reload after optimization resolved it. This is UI
evidence, not a live provider recovery claim.
- Every test shard passed on final commit `bbbc09efb4`. The older local
`pnpm test:run` was stopped after the complete CI test matrix passed.
Local full typecheck and production build passed. The first CI build
compiled and booted, then lost its runner during the clean public
npm-install check. An isolated retry passed the build, production boot
and clean public npm-install verification.
- Greptile reviewed final commit `bbbc09efb4` at 5/5. All review threads
are resolved.
- The change is not deployed. Hosted recovery remains unverified until
the served revision includes this change.

## Risks

- Recovery crosses process, provider and persistence boundaries. Missing
or mismatched ownership, stop, descriptor or file evidence keeps the
hold. It never selects a replacement allocation or silently starts over.
- File recovery does not certify external action outcomes or authorize
replay. New input still uses normal execution admission.
- Historical sources without sufficient durable evidence can remain
blocked. Destructive reconstruction stays separate.
- The index migration is idempotent. It changes no task data. Snapshot
pruning follows repository policy.

## Model Used

OpenAI Codex, `gpt-6.1-sol`, with code execution and browser tools.
`gpt-6-astra` assisted earlier investigation. The runtime does not
expose the context-window size.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 21:51:46 -05:00
DottaandPaperclip 16689de291 fix: add one-click retry for restricted workspace setup (#16909)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Tasks need a clear way to resume after a setup failure.
> - A shared repository can contain another task that the assigned agent
cannot read.
> - Paperclip correctly stops before the agent starts, but the user must
then understand workspace settings to recover.
> - This pull request gives that failure a single Retry button and
selects a clean copy of the configured repository through normal
admission.
> - The task keeps its assigned agent and execution settings, while
access checks and existing work remain protected.

## Linked Issues or Issue Description

Related: #16895 classifies the restricted source failure. This change
adds the user recovery action. #16906 handles retained files after
execution; this change handles a setup failure before execution starts.

**What existing behavior does this improve?**

Recovery of a task whose shared repository includes a task workspace the
assigned agent cannot read.

**Current behavior**

The task stops before provider work and asks the user to understand
workspace choices or access grants.

**Proposed behavior**

Show Retry above the task message box, independent of loaded
conversation history. One click requests one attempt using a clean
checkout of the configured remote. Show Retrying while the request is
pending. Show an error only if the request fails.

**Reason and benefit**

The user can resume work without understanding repository isolation or
changing access to another task.

**Breaking changes**

None. The recovery source value is server-owned. The public workspace
selection request does not accept it. No migration is required.

## What Changed

- Add one Retry control above the composer in both task conversation
views. It stays available when an older notice is outside the loaded
comment pages.
- Bind recovery to the latest failed run, current assignee, and recorded
proof that provider work did not start.
- Use the existing atomic recovery route and pending workspace
selection. Normal admission clears the old session and creates the
isolated checkout.
- Choose a fresh task-owned branch for recovery, including fixed project
branches, existing task branches, and adapter branch overrides. Preserve
the model, environment, setup commands, pending user workspace choices,
previous files, and all execution gates.
- Update execution documentation and both workspace maps.

## Verification

- Passed all 461 tests in the eight affected database, Git, HTTP,
workspace binding, and conversation suites after the review fixes. An
additional 292 tests passed after the final compatibility fixes,
including IssueDetail and recovery action routing.
- Concurrent HTTP retries produce one wakeup. Paused projects and runs
that started provider work reject recovery without changing the
workspace.
- Real Git tests exclude private files, private commits, and unpublished
original files from the clean checkout, preserve the original, and
exercise reuse, cleanup, and reopen.
- Verified in a running local app: a task failed twice, displayed only
Retry, and reached Done after one click. A second browser test put the
failure notice behind 501 newer comments and used a fixed project
branch. Retry stayed visible and the task reached Done. The
credential-free process worker used the selected checkout and wrote its
result there. This does not claim a live model-provider run.
- The first manual fixture lacked a responsible-user membership and
failed after successful workspace recovery. Corrected the fixture,
retained that failure evidence, and verified the full flow with ordinary
authorization.
- Full typecheck, build, token gates, and map checks passed. The full
local suite was stopped after review changed its source during
execution; current-head CI provides the complete suite result.
- An earlier unrelated peer-comment read test hit a socket hangup. The
next complete affected-suite run passed; the first failure is retained
in local evidence.
- Current-head CI hit an unchanged runner credential-concurrency test
failure. That lane passed on the preceding commit, and all 42 credential
tests passed locally. The original failed job is retained; the one-time
rerun passed. All latest-head CI checks are green (55 success, 2
skipped, 1 neutral), and Greptile is 5/5 with both review threads
resolved.

## Risks

- A remote repository outage can still prevent the next attempt. Retry
does not grant access or copy unpublished files from the old checkout.
- Recovery accepts only the latest recorded pre-provider failure and
preserves normal execution gates. This limits duplicate work and stale
recovery requests.
- No database migration, dependency, or lockfile change.
- The first review found fixed-branch retry loops and dependence on
paginated notice history. Both had failing regressions before the fixes
and now pass targeted tests and the combined browser journey.
- Full CI then caught assumptions about missing run evidence and
unrelated recovery actions. The final changes tolerate absent evidence
and scope the new lookup to board-owned actions with valid run IDs. The
previously failing suites now pass locally.

## Model Used

OpenAI Codex, GPT-6 family, with reasoning, repository tools, code
execution, and browser verification. The exact serving model ID and
context window are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 21:49:44 -05:00
DottaandPaperclip 7ec6e1a237 fix(runner): explain invalid arguments for assigned tools (#16905)
## Thinking Path

> - Paperclip coordinates agents through authorized tools.
> - The native runner validates arguments before it dispatches a tool
call.
> - Schema failures give repair guidance for only five built-in tools.
> - Assigned-tool discovery receives a generic rejection, so an agent
can mistake invalid arguments for missing access.
> - This PR applies the existing safe schema feedback to every
authorized tool.
> - Agents can correct their calls while authorization, approval, and
replay checks remain in force.

## Linked Issues or Issue Description

**What happened?**

An invalid `paperclip_search_assigned_tools` call returned only
`Paperclip rejected this semantic tool call`. The call never reached the
assigned-tool gateway. The same feedback gap affects arbitrary assigned
app tools.

**Expected behavior**

Identify argument validation as the cause. Return bounded schema
locations and ask the provider to correct its arguments. Do not expose
submitted values or grant access to unassigned tools.

**Steps to reproduce**

Prepare an authorized discovery tool. Submit an invalid query or
optional argument through the native runner. Observe the generic error
before this fix. Correct the arguments and confirm one dispatch after
this fix.

**Paperclip version or commit**

Reproduced on master at `4970d5ed3d`. The incident did not retain its
rejected arguments, so the tests cover representative invalid inputs
rather than claim to replay that exact payload.

**Deployment mode**

Native runner with the Codex app-server driver. Local verification uses
macOS ARM64 and controlled provider fixtures.

Related: #16868 added bounded monitor validation feedback. #16723
changes runtime MCP catalog loading; this PR changes the Rust runner
validation response and does not depend on that work.

## What Changed

- Supply generic repair guidance for any authorized tool whose arguments
fail JSON Schema validation. Preserve specific built-in hints.
- Keep the existing three-location and 512-byte limits. Do not include
input values or unknown keys. Preserve generic authorization failures
and the existing retry flag.
- Cover missing fields, wrong types, null optional fields, bounds,
unknown fields, unchanged rejected-call state, corrected calls, and
completed-call replay protection.
- Exercise rejection, correction, one dispatch, and successful
completion through the real Codex driver with a controlled provider
subprocess.
- Document the behavior and its verification scope in execution
semantics and the agent access map.

## Verification

- Red: both new runner regressions failed on the original generic
rejection. The existing API-validation regression passed.
- Green: all seven selected validation tests passed. The new Codex
transport regression passed with one rejection and one corrected
dispatch.
- `cargo fmt --manifest-path packages/paperclip-runner/runner/Cargo.toml
--all -- --check`, `node scripts/check-maps.mjs`, and `git diff --check`
passed.
- Full Rust workspace tests, the repository build, and sequential
repository typecheck passed. The existing assigned-tool gateway suite
passed all 30 tests. All hosted test and end-to-end jobs passed on this
head. The duplicate local `test:run` was interrupted after the hosted
suites passed; its local result is incomplete. The hosted build and
clean public npm installation check also passed. All current-head CI
gates are green, including the final verify and e2e aggregates.
- Greptile reviewed commit `3e2743e1e15b3b13a7d803ce4d828510e41fb22a`:
5/5, no actionable findings.
- Setup evidence: master has a stale dependency lockfile. Dependencies
were resolved with the pinned pnpm 9.15.4; lockfile changes are
excluded. The first full typecheck overlapped the build and failed
copying a generated shared-package file. The sequential rerun passed
with no source change. The initial copy failure remains recorded here;
the concurrent build-output race was not separately reproduced.
- The provider is simulated. This proves runner validation and transport
recovery, not that a live model always retries or that GitHub
credentials work.

## Risks

The provider now sees schema locations for all authorized tools. The
existing sanitizer and bounds still apply. Unknown input keys and values
remain excluded. No schema, permission, approval, automatic tool replay,
database, or connection-auth changes are made. Unauthorized tools still
get a generic rejection.

## Model Used

OpenAI Codex (GPT-6), with reasoning, source inspection, and tool
execution. The exact runtime model ID and context-window size are not
exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 17:03:42 -05:00
DottaandPaperclip e5927e1db9 fix: give commentary its own default read permission (#16903)
## Thinking Path

> - Paperclip lets people manage AI agents and inspect their work.
> - Commentary collects agent suggestions and complaints for company
members.
> - Commentary used the permission for detailed agent-action audits.
> - Owners, admins and viewers could therefore receive a permission
error when they opened Commentary.
> - This pull request gives commentary its own permission and enables it
for all human company roles.
> - Members can read feedback while task privacy and detailed audit
access keep their own checks.

## Linked Issues or Issue Description

Refs #16884, which added the Commentary browser. A search found no open
PR for this permission fix.

**What happened?**

Commentary returned `Missing permission: audit:view_agent_actions` for
company members without the detailed audit grant. Default owners, admins
and viewers did not receive that grant.

**Expected behavior**

All human company roles can read commentary by default. A separate
`commentary:view` permission controls this access. Private source tasks
remain private. Commentary access does not grant detailed agent-action
audits or CSV exports.

**Steps to reproduce**

1. Sign in as an active company owner, admin or viewer without
`audit:view_agent_actions`.
2. Open Audit, then Commentary.
3. Observe the permission error before this change.

**Paperclip version or commit**

Base commit: `7c58ea07b2`.

**Deployment mode**

Authenticated server or Cloud tenant.

## What Changed

- Add `commentary:view` to the shared permission contract and all human
role defaults.
- Require that permission for commentary list and detail reads.
- Add an idempotent upgrade migration for existing active human members.
Preserve existing grants and scopes.
- Add the commentary default when approving saved human invitation
grants that omit it, including pre-upgrade invitations. Preserve
explicit commentary scopes.
- Add regression coverage for role defaults, permission removal, audit
separation, private tasks and migration replay.
- Update the API description, specifications, database notes and access
maps.

## Verification

- Passed 68 tests across commentary reads, role grants, old-invitation
HTTP acceptance, migration replay, agent audit routes, access services
and migration snapshot drift under the repository's locked dependencies.
- Confirmed the new role and read tests failed before the
implementation.
- `node scripts/check-maps.mjs` passed.
- Migration numbering and safety checks passed during the build.
- Full `pnpm -r typecheck` and `pnpm build` passed locally after the
invitation fix.
- The final-commit CI matrix passed, including all test shards,
typecheck, build, public-install checks and canary smoke. The redundant
local `pnpm test:run` was stopped after the full CI matrix completed;
the 68 focused local regressions passed separately.
- The first install bypassed the stale lockfile and selected a newer
diff-viewer API. The initial typecheck and build failed in that
unrelated plugin. Installing the locked versions cleared both failures;
the tracked lockfile is unchanged.
- The first locked-dependency regression run hit the 15-second limit
while importing the audit route graph in its first test. Moving that
import into suite setup fixed the timeout; all 58 regressions then
passed.
- Greptile found that pre-upgrade invitations retain old grant lists.
New helper and HTTP regressions reproduced this gap before the fix, then
passed after approval added the missing commentary default.
- Greptile reviewed the final commit at 5/5 with no remaining actionable
findings. Its earlier thread is resolved.
- No UI code changed. The permission tests use real disposable
PostgreSQL databases and HTTP routes.

## Risks

- The upgrade deliberately enables commentary for every existing active
human company member, including viewers. Existing commentary grants
retain their saved scopes.
- Source-task privacy still filters previews, counts, searches and full
messages. Agent-authenticated browsing remains denied.
- Agent-action audit grants, detailed filters and CSV export permissions
keep their current behavior.

## Model Used

OpenAI Codex, based on GPT-6, with reasoning, repository editing and
command execution. The exact runtime model ID and context window are not
exposed to this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 16:58:17 -05:00
DottaandPaperclip 7c58ea07b2 fix(issues): guard prepared task promotion by status version (#16893)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Integrations can prepare a backlog task before its assigned agent
starts.
> - A person can change its status or assignment during preparation.
> - An unconditional promotion can replace that newer decision.
> - Safe promotion needs a saved revision that includes every assignment
path.
> - This pull request checks that revision under the task row lock and
derives policy cleanup from the locked row.
> - The benefit is safe initialization recovery with the existing
company, task, and run authority.

## Linked Issues or Issue Description

Prerequisite #16896 has merged. This PR now targets master and contains
only the conditional promotion API. The prerequisite fixed the confirmed
baseline first-upload browser regression.

**What happened?**

A client that saves a task's initial documents and then sends an
unconditional status update can override a concurrent status or
assignment decision. The update validator previously dropped an expected
version, so clients could not make this promotion conditional. Some
direct assignment and release paths also did not advance the revision.

**Expected behavior**

A prepared task moves from backlog to todo only if its original status
and assignment revision still matches. A stale request returns 409
before a task mutation, audit publication, or wake. Policy cleanup
preserves unrelated saved settings.

**Steps to reproduce**

1. Create a backlog task and save its statusVersion before preparing it.
2. Release its assignment, or change an assignee and then restore that
assignee.
3. Send `{ "status": "todo", "expectedStatusVersion": <original
revision> }` to its PATCH endpoint.
4. The stale promotion must return 409. A matching revision on an
unchanged backlog task must succeed.

Duplicate and related PR searches found no existing prepared-task
promotion fix.

## What Changed

- Accept an optional nonnegative expectedStatusVersion for exactly a
status-only backlog-to-todo promotion. Reject extra public fields before
parsing can discard them.
- Check the current revision and backlog state under the issue row lock.
Reject stale requests before checkout adoption or execution-control
effects.
- Add SQL migration 0358 to advance the revision for both assignee
fields at the database boundary. Release, administrative release, direct
writes, and assignment round trips now invalidate an old version.
- Derive guarded policy cleanup from the locked row. Preserve review
limits and protected authorization when removing a monitor. Reject
derived ownership changes or review decisions.
- Add schema, real HTTP/PostgreSQL, concurrency, migration replay, and
policy regression coverage. Update the response type, OpenAPI, developer
docs, and access map.

## Verification

- Red before the initial fix: stale requests returned 200 instead of
409, validation removed the expected version, and a stale active task
could adopt a checkout.
- Review found two further defects. Four new release/direct-assignment
tests showed unchanged revisions. The real HTTP/service test returned
422 for a valid two-field promotion after monitor cleanup. Helper tests
also proved that cleanup lost valid review limits and protected
authorization. All now pass after focused repairs.
- Green: 124 route and policy tests, including 7 real Express/PostgreSQL
cases, 37 existing route tests, and 80 policy/helper tests. The real
row-lock race preserves a policy edit committed while promotion waits.
- Green: all 23 database client tests, plus 9 focused assignment and
replay checks. Historical migration 0227 receipt recovery cannot remove
the new assignment trigger. Reapplying migration 0358 leaves existing
rows unchanged and installs one trigger. Combined status/assignment
writes increment once; unchanged assignees do not increment.
- Earlier verification passed all 218 schema/route/service cases and the
generated OpenAPI capability test. Rebased focused regressions passed
all 27 selected cases. Final server TypeScript passed after all repairs;
shared TypeScript passed. Migration safety/numbering, five-snapshot
retention, map validation, and diff checks pass.
- The baseline browser attachment case failed twice on the earlier head.
Separate #16896 proved the lost-composer cause, passed 335 component
tests and the real first-upload journey, and has green CI with a 5/5
review. No assertion or timeout was weakened.
- Some early local checks were blocked by missing or stale sibling
dependency artifacts. This worktree now has its own frozen offline
install and standard SDK prerequisites. The failures and successful
reruns remain in the task evidence.
- Before rebasing, head `3304bb00de6ad6a248b5e046c008072ad20ac8f5`
passed all CI (55 successful checks and one neutral), Greptile 5/5, and
a secondary source review at 5/5 with no unresolved findings. The
secondary reviewer did not execute project tests, inspect CI, or
exercise a live agent journey. Earlier incomplete and must-fix
assessments remain visible; both established findings are repaired
above.
- After #16896 merged, all five CAS commits were rebased onto master
`87d9386ae637c652d1fed09d2046be1bcaeb413b`. Migration 0358 was
regenerated because master added another 0357. Range comparison shows no
other change to the CAS patches; inherited UI commits are absent. The
original head is preserved locally.
- Rebased head `1c0264e51a280b1dbf597725a7e42e72d4be1b1b` passes all 124
route/policy tests, 9 selected assignment/promotion tests, and all 24
database client/snapshot-drift tests. Database build, migration checks,
generated snapshot linkage, five-snapshot retention (0354–0358), maps,
and diff checks pass. Fresh-head CI and review are pending. No
deployment or live agent journey was performed for this API.

## Risks

- The guard supports prepared backlog promotion only. Other statuses or
mixed public mutation fields return 422. A stale revision or non-backlog
row returns 409.
- Preserve the original version from a server that already advertises
this guard before initialization. Older versions did not track every
assignment path. Reconcile older or uncertain initialization instead of
fetching a new revision and blindly retrying.
- Migration 0358 is SQL-only and idempotent. It adds no table, column,
or task backfill. Its separate trigger survives historical
status-migration replay.
- Existing authorization and unguarded updates remain in place. Guarded
promotion does not provide a general lifecycle or review-stage control
API.

## Model Used

OpenAI Codex, GPT-6 family. The exact serving model ID and context
window are not exposed by this session. Used tool calls, code execution,
and test-first regression verification.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [ ] All Paperclip CI gates are green
- [ ] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 16:27:11 -05:00
DottaandPaperclip c145475cae fix: admit documented sandbox task context routes (#16892)
## Thinking Path

> - Paperclip agents use task context to complete assigned work.
> - Sandboxed agents reach the controller through a bounded callback
bridge.
> - The bridge rejects several documented context routes before
controller authorization runs.
> - An authorized agent cannot read a task screenshot or referenced
skill file, or inspect a missed monitor wake.
> - This pull request admits only the exact context routes and supported
methods.
> - The controller continues to enforce company, resource, task and
monitor authority.

## Linked Issues or Issue Description

**What happened?**

Both callback transports return `Route not allowed` for task asset
content, company skill detail and files, wake diagnostics, and the
monitor check-now action. These operations already exist in the
controller.

**Expected behavior**

A sandboxed agent can use these documented operations when the
controller authorizes its request. Other methods, deeper paths, skill
mutations, and recovery resolution remain restricted.

**Steps to reproduce**

Use a sandbox callback to read an asset URL from a task description,
read a company skill's referenced file, or inspect a task's wake
diagnostics. The baseline bridge rejects each request. The new
regression matrix runs all five operations against both transport
allowlists.

Related: #16772 documents refused callback routes. This PR fixes the
context routes listed above; it does not add company-wide activity or
labels access.

## What Changed

- Admit asset content, skill detail/files, and wake diagnostic reads.
- Admit the existing monitor check-now action with controller
authorization.
- Add a focused allow/deny matrix for both transports.
- Update the operational API reference and access maps.

## Verification

- With the pre-fix bridge rules, all 10 allowed-request cases fail with
`Route not allowed` across the two transports; all 24 deny controls
still pass.
- With the fix restored, all 34 route cases pass. The matrix plus
existing callback suite passes 119 tests across two files.
- Local `pnpm -r typecheck` and `pnpm build` pass.
- The access-map checker, capability contract generation check, and
capability inventory check pass.
- Full repository CI passes on `97f9f06b2c`: typecheck/release registry,
all test shards, build, Docker context, canary dry run, and aggregate
verify.
- The duplicate local full-suite run was stopped after 24 minutes once
full CI passed; it is not claimed as a completed local pass.
- Greptile is 5/5 on the current head with no inline findings.
Independent source review checked asset, skill, wake-diagnostic, and
monitor controller authorization and found no actionable issues.
- The secondary Paperclip automated review is neutral/incomplete.
Independent review covered its missing controller checks; the real
Vitest cases and full CI provide execution evidence.

## Risks

This widens transport admission for five existing operations. It does
not change controller authorization. Asset reads still check
company/task visibility; skill reads keep source policy; monitor checks
keep ownership and management permission. No schema or UI change is
required.

## Model Used

OpenAI Codex, GPT-6 family, with tool use and code execution. The
session does not expose the exact serving model ID or context window.
The work used failing-before and passing-after regression tests.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 16:27:05 -05:00
DottaandPaperclip 6f045207bb fix(runner): explain rejected API response windows (#16889)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Agents use the API fallback when dedicated tools cannot express an
operation.
> - Large responses can be read in bounded text windows.
> - The declared schema rejects windows larger than 24576 bytes.
> - The runner hid the rejected field behind a generic semantic tool
error.
> - This pull request returns safe schema locations and the accepted
byte range.
> - Agents can correct a call without guessing or changing route
permissions.

## Linked Issues or Issue Description

Refs: #16868, which added repair guidance for task monitor arguments.

**What happened?**

A native call_api request with responseText.limitBytes set to 60000
returned invalid_tool_call with no field or size guidance. The declared
4..24576 byte range already matches the server validator. The missing
repair guidance is in the runner bridge.

**Expected behavior**

Reject invalid input before dispatch. Show bounded schema locations and
the accepted window range. Do not echo submitted values or unknown field
names. A corrected request can reuse the rejected call ID.

**Steps to reproduce**

1. Use the generated call_api tool contract to request a GET text window
with limitBytes 60000.
2. Read the semantic tool error. Before this fix, it contains only a
generic rejection.
3. Retry with limitBytes 16000. The corrected call must be admitted.

**Paperclip version or commit**

Reproduced on master 5739a53f5f.

**Deployment mode**

Built from source. This affects the native runner bridge.

## What Changed

- Add call_api to the existing provider-safe schema guidance path.
- Name the text-window byte range and pagination field.
- Exercise the actual generated production schema through the provider
bridge and its error result.
- Keep private values, unknown property names, authorization errors and
response-size limits unchanged.
- Document the response window and repair behavior.

## Verification

- Red: api_window_rejection_explains_limits_and_allows_corrected_call
failed on master because the provider error did not name
responseText.limitBytes.
- Green: the same regression passes with a corrected same-ID call,
unknown-key privacy checks and unchanged authorization rejection.
- Passed: the existing runner-api.test.ts suite, 1935 tests, including
server window validation before dispatch.
- Passed: all 394 Runner core Rust unit tests, cargo fmt --check and the
generated protocol manifest check. The focused test also passed after
extraction into its own Rust test module.
- Greptile: 5/5 with no actionable issues on the final head
95d65e1646.
- The first CI release-registry run found that a compile-time test
fixture was outside the release-cache input set. The fixture now reads
the same generated schema at test runtime. The Rust regression and all
10 runner-release-crate-cache tests pass after that repair.
- This pure error mapping adds no dependency calls, provider retries or
network work. No live provider or staging deployment was needed.
- Full current-head CI passed, including repository typecheck, tests,
build, Runner verification, canary and browser suites. At
95d65e1646 there are 56 successful and
four skipped checks. The separate Paperclip Review bot completed with a
neutral check and a 5/5 static assessment with no findings. It did not
run current-head Rust, full repository or live-provider tests; its older
local cache run is not counted as current-head test evidence. No check
remains pending or failed. No local full-suite or full-build pass is
claimed.

## Risks

- Feedback must not disclose submitted values. The regression checks
private values and unknown field names, a 512-byte bound and unchanged
generic authorization errors.
- Guidance names the current byte range. The regression uses the
generated production schema so a contract change must keep this repair
guidance accurate.

## Model Used

OpenAI Codex, GPT-6 family, with reasoning, tool use and code execution.
The exact runtime model suffix and context window are not exposed to
this session.

## Checklist


- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 16:10:58 -05:00
DottaandPaperclip ac9459bae3 feat: configure company agent observability (#16874)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Companies use several agent harnesses and execution environments.
> - Operators need one place to select where native agent logs and
traces go.
> - An inference proxy would add a dependency to the agent request path.
> - This pull request supplies native OpenTelemetry settings to managed
Codex and Claude Code processes.
> - Company secrets protect destination credentials. Export failure does
not change the task result.

## Linked Issues or Issue Description

**Subsystem affected**

Company settings, shared contracts, database, server, adapters, and
runner.

**Problem or motivation**

An operator cannot configure a company destination for native agent logs
and traces. Manual harness configuration is hard to apply across local
and remote execution.

**Proposed solution**

Add one company destination: Braintrust or a custom OTLP HTTP/protobuf
endpoint. Apply a transient snapshot when execution preparation starts.
Keep credentials out of API reads, task environment manifests, recovery
files, and command arguments. Replace a warm process when its export
settings change and preserve its conversation.

**Alternatives considered**

Multiple destinations can use a user-operated collector for fan-out.
This change does not add a collector, an inference proxy, or transcript
scraping.

**Roadmap alignment**

This extends company settings, secret management, and support for
multiple harnesses. The maintainer requested this implementation.
Searches for observability and Braintrust found no duplicate company
destination feature. Related infrastructure tracing work in #16236 has a
separate content-free contract.

## What Changed

- Add strict schemas, revision checks, encrypted secret storage,
activity records, and board-only settings routes.
- Add explicit synthetic logs and traces tests with a bounded HTTP
request and sanitized results.
- Supply native Codex configuration and Claude Code environment values
through local and remote launch paths.
- Preserve Codex login refresh through the existing managed credential
link. Retain unsaved drafts across background reads. Require complete
custom header re-entry when the endpoint origin changes.
- Separate process export compatibility from conversation identity.
Isolate generated Codex configuration and preserve resumable sessions,
including remote home refresh after export changes.
- Advance the immutable Pi/Copilot source attestations for shared
environment and sidecar code changes. Keep their provider payloads
unchanged and retain prior identities for decoding.
- Redact destination credentials throughout launch diagnostics and HTTP
logs.
- Add the production settings form, Storybook states and journey,
documentation, and feature/access map entries.

## Verification

- Real managed local Codex 0.160.0 and Claude Code 2.1.286 tasks
exported to Braintrust. API readback and the Braintrust UI showed the
test records. A real remote Daytona Codex task exported through the
legacy `exec` path.
- Live tests exercised content capture off, export disabled, warm
conversation reuse, and a destination that accepted connections but
never replied. Agent work succeeded and export requests stopped at the
configured three-second timeout. The UI connection test returned “Test
payload accepted”; the saved API key stayed masked after reload.
- All current-head CI test lanes, typechecks, packaging/build checks,
and required aggregates passed on
`71e994b2be9c8fb6d6e938a4ad7cf4c95fdafe31` ([CI
run](https://github.com/paperclipai/paperclip/actions/runs/39319194318)).
Greptile completed on that exact commit at 5/5, with zero unresolved
review threads. The additional optional Paperclip Review check remains
queued waiting for its assigned agent.
- Local workspace typecheck and build passed. Focused verification
included 239 combined runner tests, 789 API/native-session tests, 107
Codex home/ACP/sandbox-site tests, 204 feature/privacy tests, and the
affected Rust suites. Migration, token, map, Storybook catalog, and
Storybook build checks passed during acceptance. These checks ran at the
relevant implementation or merge boundary; the current-head CI is the
complete final gate.
- Managed AI credential projections now receive enabled and disabled
company export settings; genuine caller-owned Codex homes remain
untouched. Two regressions reproduced the skip before the repair. All
276 engine/lifecycle tests and adapter-utils typecheck pass afterward.
The launched TOML retains provider/MCP settings, credential continuity,
and redaction.
- Settings saves, removal, and the real company-deletion owner acquire
secret mutation ownership before database locks. PostgreSQL NOWAIT
probes cover all three paths; concurrent save/rotation/removal/deletion
requests settle correctly. The affected suites passed 137 tests,
followed by all 32 service/connection cases after expanded deletion
coverage. Server and Codex adapter typechecks pass.
- Codex source profiles use the effective CLI argument list. A spawned
fixture CLI reproduced both ignored-argument failures; all three
precedence/fallback cases now pass.
- Real tar staging reproduced remote conversation loss in both API-key
and subscription modes before the repair. Both now pass: changing
managed settings preserves sessions, archives, native indexes, and
refreshed subscription credentials. A corrupt upload preserves the prior
config and conversation.
- Preserved failure evidence: initial CI caught stale Pi/Copilot source
attestations, a missing test-harness helper, and packaging fixture/probe
mismatches; those were corrected and covered by focused checks.
Superseded heads had intermittent attachment-composer timeouts despite
successful uploads; [the original trace and screenshot remain
available](https://github.com/paperclipai/paperclip/actions/runs/39309701089/artifacts/12215109203).
The same attachment case passed on the final head: [25/25 tests in shard
3](https://github.com/paperclipai/paperclip/actions/runs/39319194318/job/118288637051).
- A connection-fault fixture also exposed a stale pooled socket after
its hang case; closing fixture responses isolated scenarios and the full
affected suite passed.
- The broad local test run was not clean: database resource failures,
timeouts, an older cached module graph, and a stale optional-resource
manifest assumption were recorded. Focused checks passed after the
documented fixes. This does not establish a clean full local pass.
- Native remote Codex, remote Claude, and the full ACPX Codex bridge
remain unqualified. The direct Codex resume test does not establish full
bridge acceptance.

## Risks

- Native exporters perform network requests from each execution
environment. A server connection test does not prove remote
reachability.
- Prompts, assistant responses, and tool content are enabled by default
when supported. Native caps and harness-specific controls still apply.
- Caller-owned Codex homes are unsupported for automatic configuration
and remain untouched.
- Native harnesses and their tool processes can inspect export
credentials. The settings form and documentation advise using
ingestion-scoped credentials. Retained headers remain bound to their
saved scheme, host, and port; changing origin requires fresh values or
removal.
- Migration 0357 adds a company-scoped row and secret reference. It is
safe to reapply. Secret removal and company deletion use the existing
secret lifecycle.
- Slow or unavailable destinations must not block task settlement.
Export settings take effect at the next execution preparation boundary.

## Model Used

OpenAI Codex, GPT-6, with reasoning, tool use, code execution, and
browser verification. The exact serving model ID and context window size
are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 15:36:04 -05:00
Nicky LeachandPaperclip 2e5bf12411 test(adapter-utils): retry HTTP/2 fixture port collisions (#16888)
## Thinking Path

> - Paperclip manages work for AI agents.
> - Sandbox agents use a callback bridge to reach the API.
> - Tests start the generated HTTP/2 gateway on an assigned loopback
port.
> - The test probe releases that port before the gateway binds it.
> - Another process can claim the port during that gap.
> - This PR retries that specific fixture startup collision and tests
its limits.

## Linked Issues or Issue Description

**What happened?**

The unchanged callback bridge test failed in #16605 because its selected
port was already in use. [CI job
118251110752](https://github.com/paperclipai/paperclip/actions/runs/39308303837/job/118251110752)
reports `EADDRINUSE` before the gateway READY frame. The same helper is
present on master `4d92589799`; no merged or open fix for this exact
failure was found.

**Expected behavior**

The fixture starts on a fresh port after a confirmed bind collision. It
stops after three attempts and preserves other startup failures.

**Steps to reproduce**

The new held-probe case keeps the selected socket open before the real
child starts. Before the correction, the original authorization test
fails with `EADDRINUSE`. The unchanged no-collision case passes.

**Additional context**

This is the separate scoped correction for #16605's unrelated CI
failure. It changes one test file.

## What Changed

- Retry only pre-READY gateway exits with code 1 and the specific
`EADDRINUSE` bind diagnostic.
- Wait for child close and fully drained stderr before classifying
startup. Kill failed attempts and preserve the original failure after
three collisions.
- Keep the real probe socket open to inject collisions without a timing
race.
- Verify successful recovery, bounded exhaustion, delayed stderr, and
immediate failure for unrelated startup errors. Accept successful starts
anywhere within the three-attempt limit. Preserve the original
authorization and header-stripping assertions.

## Verification

- Negative controls: the held-port authorization case fails with
`EADDRINUSE`, and retry exhaustion observes only one attempt before the
correction. The ordinary case passes.
- `pnpm exec vitest run
packages/adapter-utils/src/sandbox-callback-bridge.test.ts`: all 89
tests pass on the final head.
- `pnpm --filter @paperclipai/adapter-utils typecheck`: passes.
- Initial standard Greptile returned 4/5 for late stderr classification
and exact success-count assertions. Both are corrected. The final
real-pipe control reproduces missing diagnostics with the old exit
listener and passes with close-based readiness. An initial pause-only
control was not discriminating because Node resumes pipes on exit; the
final control holds that resume until after exit.
- Diff checks and the complete secrets/PII review pass.
- Full local repository tests and build were not run for this one-file
fixture change. Hosted CI and standard Greptile are pending.

## Risks

The fixture can still fail after three consecutive collisions. Other
startup failures remain failures. The generated gateway and its
assigned-port protocol are unchanged.

## Model Used

OpenAI Codex, GPT-6, with reasoning, repository inspection, code
execution, and testing. The exact deployment model ID and context window
are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [ ] All Paperclip CI gates are green
- [ ] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 12:49:25 -07:00
Nicky LeachandPaperclip 313fb265db feat(plugins): invalidate runtimes when connector access changes (#16605)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Runtime preparation depends on access and credential state as well
as tool definitions.
> - Grant, membership, secret, and endpoint changes need committed
invalidation.
> - Their writers must acquire locks before journal fanout can lock
agent rows.
> - This pull request adds access hooks with the corresponding
transaction guards.
> - Plugins can refresh preparation immediately while task-time
authorization remains authoritative.

## Linked Issues or Issue Description

**What happened?**

Grant changes, credential rotation and revocation, company access
changes, and connector endpoint configuration do not request runtime
synchronization. Journal fanout exposes lock inversions between
credential persistence, access cleanup, and connection assignment
writers.

**Expected behavior**

Committed access changes request runtime preparation without polling or
credential values in the journal. Agent-specific secret bindings and new
personal delegations affect their target agent. Company access changes
remain conservative. Provider bookkeeping does not create preparation
work.

**Steps to reproduce**

1. Change an audience, delegation, membership permission, referenced
credential, vault configuration, or endpoint instruction.
2. Expect a committed runtime event in the correct company and scope.
3. Run reconnect, credential refresh, SSH setup, or membership cleanup
concurrently with related writes.
4. Expect both operations to preserve access checks and finish without a
lock-order cycle.

**Additional context**

Final feature extraction from #16503. The earlier slices, #16604, and
the separate delivery-test correction #16871 are merged. This PR is now
the active change against master. The rebase preserves the merged
assignment and definition recipient rules, Unicode selector semantics,
and profile/reference transaction guards.

## What Changed

- Add migration 0356 for grants, audiences, delegation,
membership/permissions, secret bindings, referenced credentials and
vaults, and chat/email endpoint configuration.
- Keep events content-free. Ignore health, delivery, publication, Vercel
verification, and GitHub webhook bookkeeping while retaining credential
and repository-access changes.
- Target agent secret bindings and all personal delegation changes to
their old and new target agents. Coalesce delegation changes per
transaction.
- Lock existing grants before connections and credential persistence in
OAuth and cleanup writers.
- Reject superseded refresh leases before rotating stored credentials.
Ignore lease acquisition and release when access metadata is unchanged.
- Serialize audience replacement, validate membership, and preserve
unchanged audiences.
- Lock membership before permission-only saves and grant before Railway
SSH setup. Individual delegation revocation locks its grant and target.
Whole-grant and membership cleanup lock company recipients before
deleting scoped delegations.
- Lock grants and connection inputs before static-key reconnect writes.
Lock company agents before cascading secret deletion; use a nonblocking
secret lock and bounded retries to avoid a new cycle with credential
writers.
- Add PostgreSQL concurrency coverage for access writers and endpoint
publication/configuration behavior.
- Preserve the owner lock for plugin instance-secret removal; these
secrets cannot use ordinary bindings.
- Align Slack search refresh, callbacks, and disconnect with
grant-before-connection locking. Recheck newly discovered grants without
waiting before provider work.
- Retry complete membership transactions when a credential deletion
candidate is busy. Cover all four cleanup entry points and process
company access in ID order.
- Document final invalidation coverage and task-time authorization
boundaries.

## Verification

- Current head: `78aace55bef7f52bc5742b131e0b3961eb5c0f11`. All 1,061
tests across 23 affected suites pass. The named Slack authorization
integration scenario also passes; it exercises authorization, refresh,
disconnect, and rejection of a late callback. Server/database
typechecks, migration safety and numbering, five-snapshot retention,
feature maps, and diff checks pass. The complete PR diff was reviewed
for secrets and personal data before push. Final acceptance: [CI run
39308303837, attempt
2](https://github.com/paperclipai/paperclip/actions/runs/39308303837) is
green, with 55 successful checks and two optional Storybook skips. The
current-head Greptile reassessment returned **Apex 5/5** at 19:16 UTC on
2026-10-19. Its full summary reports no actionable issues. Security
passed, all threads are resolved, and GitHub reports no merge conflicts.
The reassessment was requested as a standard review after the fixes;
Greptile retained the Apex tier.
- On this head, [CI run
39308303837](https://github.com/paperclipai/paperclip/actions/runs/39308303837)
failed the unchanged adapter-utils HTTP/2 fixture with `EADDRINUSE`
before READY. Its closed probe left a port handoff race. That test and
its gateway are byte-identical on master. No upstream fix was found. The
deterministic fixture correction is isolated in #16888; no adapter test
changes are included here. The failed jobs recovered on retry without a
feature source change. The original failure remains documented here, and
#16888 carries the fixture correction separately. That retry
demonstrates recovery; the held-probe negative control establishes the
port handoff race.
- Rebased onto master `194fc11406`, including merged #16604 and #16871.
Replayed only the access-hook commit. Resolved OAuth, test, and
documentation conflicts while retaining both sets of tests. Migration
0356 preserves the merged assignment/definition recipient rules, Unicode
selector semantics, and profile/reference guards.
- Apex returned 3/5 on `0fb65bc27`. Negative controls reproduce its
Slack delegation and member-cleanup deadlocks (`40P01`) and unwanted
Vercel/GitHub bookkeeping events. Slack grant writers now take their
locks before the connection. A separate late-grant control reproduces
`40P01` without the post-lock recheck; the complete guard passes. All
four membership cleanup commands retry from a fresh transaction when the
credential is busy. Tests verify successful cleanup and no journal rows
from failed attempts. Credential IDs and repository-access changes still
notify runtimes.
- Earlier review corrections remain covered: static-key reconnect and
cascading secret removal each reproduce `40P01` without their guards.
Grant lease acquisition/release is ignored. Secret removal releases
agent locks when a credential writer is busy. Instance-secret removal
retains the owner lock and passes its public plugin API contention
regression. Delegation updates and revocations target old/new agents;
unrelated-peer, coalescing, unchanged-update, and rollback cases pass.
Three negative controls verify the required whole-grant and membership
cleanup guards after narrowing delegation scope.
- Preserve prior acceptance failures: the first rebased 20-suite run
passed 1,025/1,026; its only failure was a draft uninstall fixture
blocking a random peer. Blocking the assigned agent corrected that
assumption, and all 44 access/assignment tests passed. Later, all 1,044
tests across 21 suites, [CI run
39302185527](https://github.com/paperclipai/paperclip/actions/runs/39302185527),
standard Greptile 5/5, and security passed on `0fb65bc27`. That did not
clear the later Apex findings described above. Draft run 38975428081
failed a server shard; its cause was not re-investigated. A later green
run does not establish that earlier cause.
- Local fixture corrections are recorded separately from product
failures: an assignment filename filter initially matched no file; the
actual suite was included in full runs. A delegation fixture omitted its
required creator, and a guard run omitted a query import. The new
global-access cleanup fixture now uses its own user to avoid earlier
fixtures' memberships. All were corrected before publishing their final
iterations.
- Local checks target affected services and real PostgreSQL boundaries.
A full local build and repository-wide test run were not performed.
Hosted CI supplies broader verification. Provider responses in tests are
controlled; live provider behavior was not qualified.

## Risks

Migration 0356 adds triggers without changing table schema. Apply it
through the normal migration flow. Most access changes retain
synchronous company-wide invalidation. Company fanout takes O(eligible
company agents) locks and journal rows, without a fanout ceiling or
mutation quota. Agent secret bindings and individual delegation changes
retain narrower recipients. Events contain no credentials.

Physical removal of non-instance secrets takes ordered locks on all
company agents before cascading into bindings. This costs O(company
agents) locks even for an otherwise unreferenced secret. Instance
secrets cannot use ordinary bindings and retain their owner lock. A busy
secret lock releases the transaction guards and retries up to three
times. Continued contention returns a retryable conflict. Provider
deletion stays outside that transaction; a retry resumes removal of an
already disabled secret.

Membership cleanup uses nonblocking credential guards and retries the
full membership transaction. Slack search adds two grant queries, scoped
to the subject and connection. Its retries occur before provider work or
credential persistence. Each retry loop is limited to three attempts.
Invalidation requests preparation; task-time authorization and provider
session activation remain authoritative. Provider calls use fixtures; no
live provider qualification is claimed.

## Model Used

OpenAI Codex, GPT-6, with reasoning, repository inspection, code
execution, and testing. The exact deployment model ID and context window
are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 12:49:11 -07:00
DottaandPaperclip 06d4fe3121 perf(runner): preload essential Claude task tools (#16885)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - The Runner exposes assigned tools to Claude through an authenticated
MCP bridge.
> - Claude can defer these tools and search for them before a simple
task can finish.
> - Title and terminal tools are common requirements for a task turn.
> - This pull request marks those three tools for immediate loading by
Claude.
> - The remaining tools keep the SDK deferral policy and the existing
access checks.

## Linked Issues or Issue Description

Refs #15993, #15994, #15997.

**What existing behavior does this improve?**
Claude Runner tool discovery during task execution.

**Current behavior**
Claude can use ToolSearch to discover the mandatory title and terminal
tools before it answers a simple task.

**Proposed behavior**
Expose `set_task_title`, `paperclip_finish`, and `paperclip_block` in
the first Claude request through per-tool `anthropic/alwaysLoad`
metadata. Keep other tools deferred under the SDK policy.

**Reason and benefit**
Remove an avoidable tool discovery step without changing the model,
effort, or authorization. Repeated product measurements will check the
latency benefit.

## What Changed

- Add closed metadata for the three essential tools only in Claude
runtime hosts.
- Keep incoming metadata discarded and private tools hidden. Keep other
providers unchanged.
- Test real bridge catalogs and provider routing. Check the pinned
Claude SDK request against a loopback fixture with no paid calls.
- Advance the pending Copilot source binding because it attests the
shared bridge file. Preserve historical profile readers and
qualification limits.

## Verification

- Focused bridge, admission, profile, and effort controls: 185 passed,
one skipped. Three provider-routing cases pass.
- Runner TypeScript compilation passes.
- The production SDK fixture loads exactly three essential tools with
the change and zero in the controlled baseline. The document tool stays
deferred.
- Six real API-key tasks used Opus 5.5 / High in alternating order A B B
A A B. Median first assistant receipt was 22.021 s baseline vs 17.060 s
candidate (22.5% lower). Median total was 24.119 s vs 19.150 s (20.6%
lower). ToolSearch was 3/3 baseline vs 0/3 candidate. All six tasks
saved a title and accepted finish. A separate candidate follow-up
resumed the same provider session and finished without ToolSearch.
- Median startup was 4.786 s baseline vs 5.381 s candidate. This change
does not improve startup. Three samples per version give directional
evidence only.
- Estimated cost for the six tasks was $0.850900800. Candidate total was
$0.450341800 vs baseline $0.400559000; the first candidate wrote a new
cache prefix. These rate-card estimates are not invoices.
- The benchmark used source `5aed3c6a083cf8e6246815455abde3b29ecbbbac`.
Rebuilding both bundles at master-reconciled head
`d2da07259048c0a2bebd210c35cc0ebb3ff42c67` produced identical SHA-256
values. Baseline bundle SHA-256:
`10a92c373bba4fb630bf4fefeab953d850a77cf8258bc2e94711410a73a78ecd`.
Candidate:
`40348fc67a3b1ae5cc1f27f933f369981d31bcdf5d1bdc7b1797968ddfe53938`.
Baseline differs only by compiling the Claude preload selector as false.
Fresh task sessions avoid checkpoint changes.
- Full local runtime-host runs exposed credential lease collisions in
existing cases. A later complete host run passed 67 cases and timed out
in an existing admission-abort case; that case passes in isolation. All
failures are retained. Focused controls pass. Complete Runner suites,
repository typecheck, tests, browser checks, and build pass in cloud CI
on this head.

## Risks

- These three tool schemas add input to Claude requests. Measurements
must include token usage and cost.
- Copilot source identity changes because it includes the bridge source
hash. It remains pending qualification. Its catalog and executable
closure do not change.
- The test fixture proves request shape. It does not prove real-provider
latency or platform package qualification.

## Model Used

OpenAI Codex, GPT-6 family, with reasoning, tool use, and code
execution. The exact serving model ID and context window are not exposed
in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass (focused controls and
isolated cancellation check; broad local failures are retained above)
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 14:29:22 -05:00
DottaandPaperclip e6dcd1e8e9 feat: add Commentary to Audit with filters and shareable messages (#16884)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Agents can submit suggestions and complaints while they work.
> - Operators currently need database access to read those messages.
> - That makes it hard to find feedback from one agent or share a
specific message.
> - This pull request adds a standard Commentary tab in Audit.
> - Operators can filter messages, browse 50 at a time, and share links
to full message dialogs.

## Linked Issues or Issue Description

Refs #15367, which added feedback storage and agent submission. The
duplicate search found no open PR for a commentary reader.

**Subsystem affected**

Server, shared API contracts, and the board UI.

**Problem or motivation**

Agent suggestions and complaints are stored but have no board reader.
Operators must query the database to inspect feedback.

**Proposed solution**

Add Commentary to Audit without an experimental toggle. Show previews,
agent and message-type filters, text search, and 50-message pages.
Opening a row updates the URL. A copied URL opens the full message with
its agent, task, and run context.

**Alternatives considered**

Direct database queries remain useful for operators, but do not provide
a normal product workflow. An experimental setting would add setup to a
read-only audit page.

**Roadmap alignment**

This completes the operator view for the existing feedback feature. It
supports human oversight and does not change agent execution or task
ownership.

## What Changed

- Add company-scoped, board-only list and detail endpoints with audit
permission and source-task privacy checks.
- Return bounded previews and counts. Fetch full bodies only when a
message opens.
- Add the Commentary tab, search, filters, 50-row pagination, and
URL-based selection. Audit tab destinations work in both layouts, with a
classic sidebar entry for Commentary.
- Add production Storybook examples for populated, filtered, linked,
long, paginated, empty, loading, failed, denied, mobile, and light
states.
- Update API documentation and the feature and agent access maps.

## Verification

- Final head `abc4a251c14cfbfec007542214beec528f2b18bf`: 55 checks pass;
two conditional Storybook checks are skipped. The PR workflow is
successful. Greptile is 5/5 with all findings resolved.
- Focused database, HTTP, submission, OpenAPI, and UI regression tests
cover company isolation, task privacy, filter bounds, 50-row pagination,
and copied message links.
- Browser Storybook journeys cover row opening, direct links, combined
filters, search, and pagination. Storybook uses synthetic API fixtures;
database authorization is tested separately.
- Token gates, feature maps, and Storybook catalog validation pass.
- `pnpm -r typecheck`, `pnpm build`, and `pnpm build-storybook` pass on
the rebased branch. All 80 focused tests and all 37 Audit tests pass,
including the real App route table in both layouts, task
grant/revocation through HTTP, deleted-task privacy, and URL UI
regressions. The full suite passes in the parallel PR CI matrix. The
local serial full-suite run was stopped before completion after checking
the recorded 94-minute serial duration. Local focused tests, workspace
typecheck, production build, and final server/UI checks pass.
- The linked-message Storybook test initially asserted against the
loading dialog. It now waits for the message body; both direct-link and
row-open journeys pass.
- Native and legacy deleted-task privacy regressions failed before the
fix and pass afterward. The reader checks the run task binding after the
task foreign key clears.
- A rapid search-then-agent-filter browser regression reproduced the
search overwriting the selected agent. The pending search now restarts
when URL filters change. The same browser test passes with both filters
applied.
- CI found two existing AuditHub assertions that still expected five
tabs. They now assert the six-tab model and selected-company Commentary
rendering. All 37 Audit tests pass. All other test and build jobs passed
before this test-only correction.

- The [agent-chat attachment browser
test](https://github.com/paperclipai/paperclip/actions/runs/39307881171/job/118250189664)
timed out waiting for an attachment preview. The [same shard passed on
the prior
head](https://github.com/paperclipai/paperclip/actions/runs/39306658703/job/118245498343)
with identical application code; the intervening change only updates
AuditHub unit tests. The single retry passed on the same head. The
precise cause of the earlier failure remains unconfirmed.

## Risks

- Commentary may contain sensitive task context. The reader requires
board access and audit permission, and filters source-task visibility
before returning previews, counts, or full bodies.
- Text search scans stored message bodies. Pages are bounded and full
bodies are fetched on demand.
- Offset pagination can shift if new messages arrive while paging.
Ordering uses timestamp and ID for stable ties.
- No database migration or agent submission behavior changes are
required.

## Model Used

- OpenAI Codex, GPT-6 family, with reasoning, tool use, browser
interaction, and code execution. The exact backend model ID and
context-window size are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 14:21:13 -05:00
d747752496 fix(runner): record why an OpenCode turn fails when opencode serve stops (#16863)
When `opencode serve` stops during a turn, the OpenCode driver now fails the
active turn itself with a closed-vocabulary cause (server exit code or known
signal, allowlisted socket error code, HTTP status, or closed stream) instead
of leaving runnerd to close it with `error: null`. The proxy flushes stdout
before a fatal exit so the failed turn reaches runnerd, and the server records
OpenCode failed turns as `nativeTurnFailure` (live and persisted-recovery
paths) so the run-failure diagnostic names the cause. Provider text is never
copied. Run status, retries and recovery behaviour do not change.

Co-Authored-By: Paperclip Sentry triage <Paperclip-Paperclip@users.noreply.github.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-19 12:20:24 -07:00
DottaandPaperclip 8193abb936 feat(claude): default qualified macOS and Linux targets to Paperclip Runner (#15997)
## Thinking Path

> - Paperclip must run the selected agent on its selected host.
> - Claude needs verified packages for each supported target.
> - A Mac controller must select the correct Linux provider pack.
> - New defaults must follow package and execution evidence.
> - This PR adds Claude platform packaging and target-specific pack
selection.
> - Existing Codex Linux ARM64 behavior remains intact.

## Linked Issues or Issue Description

Refs #15683. This PR depends on #15993 and #15994. Related scope: #15422
and #15224.

## What Changed

- Reuse the merged four-target daemon producer/consumer matrix. Add
target-owned Linux provider packs and carry their immutable identities
through release assembly and vendoring.
- Reuse master’s landed pinned Claude SDK ARM64 executable admission and
retain package-integrity, architecture and no-follow admission.
- Select target-specific remote packs so Mac controllers can use Linux
hosts without a development pack override.
- Preserve read-only runtime context on SSH startup and resume without
accepting unverified old content.
- Check ordinary installed Claude readiness without injected package
authority. Retain Codex and Linux x64 consumer checks.
- Extend Claude automatic target selection for the remaining qualified
package targets. Retain unsupported-platform and external-override
behavior.
- Qualify managed Daytona snapshot names through provider IDs during
Claude Connect. Pin native acquisition to the measured ID. Preserve a
revocation marker after failed probes or target edits, and block native
acquisition until requalification instead of falling back to a mutable
name. Preserve immutable-image proof, company and account boundaries,
and Legacy acquisition.

## Verification

- Reconciled with master `9179d8dcc3e908c217fde4f63c9d08ccf8132eeb`
through the prerequisite stack, retaining the merged startup fix and
latest Codex Linux ARM64 behavior.
- [Four-target exact-source package
qualification](https://github.com/paperclipai/paperclip/actions/runs/39267321383)
passed on source `04e0202ca81387b17cbe7fd094a8338648356fe9`: all four
native builds, public-package assembly, Linux x64 verification and clean
installed consumers on Apple Silicon, Intel Mac and Linux ARM64. The
later master reconciliation adds shared OpenRouter attribution and
changes runtime source. This historical result keeps its original source
identity; [later
qualification](https://github.com/paperclipai/paperclip/actions/runs/39281100929)
passed at `dca62c7aeb4b45f0dd91a8e18d386a16a2658ef8`. It predates the
subsequent TypeScript startup fix.
- Fresh local product acceptance on integrated source
`b2c9fe43f9cd3bc5dd9d22552da0148845ba71a4` completed a useful file and
follow-up through native Claude/Opus 5.5, High effort and the API-key
connection. Both actual browser downloads were independently checked;
the revision preserves the original body and session continuity. Total
task estimates: $0.518432800. Ordinary web and API creation saved
defaults with the native experiment disabled.
- Local focused verification passed 993 startup/session tests, 243 UI
tests, 12 workflow security tests, direct server/UI TypeScript checks,
and token/palette gates before the last review changes. Initial
DB-backed snapshot pin/revocation coverage passed 18 cases; the final
serial route suites pass 122 credential/permission and 232
snapshot/environment cases after correcting a test hook timeout.
Current-head cloud suites pass.
- Preserved the failed pre-provider local fixture and its full pending
reservation. The successful fixture has no unpriced or pending usage.
Historical failed Cloud journeys, accounting holds, source identities
and subscription limitations remain in the dated plan.
- All Docker/Rust release production was performed in cloud CI. No local
Docker image was built. An inadvertently invoked local Rust prerequisite
was stopped.
- Current-head cloud CI is green. All three stack PRs have fresh
Greptile 5/5 reviews and zero unresolved review threads. Required
typecheck, test and build gates ran in cloud CI; Docker work stayed
remote. Earlier failed checks remain in their original runs.

- The final master merge preserves task-loading, permission,
skill-retention and OpenRouter changes. Pi uses a fresh combined profile
27, preserving both historical profile-24 declarations; Copilot remains
profile 22. Focused protocol checks passed 155 cases (one skipped), the
updated Pi attestation check passed 18 (one skipped), and 91
evaluation/catalog checks passed.

- Latest-application manual continuation passed in 37.942 seconds on
`695e5c005a85bddc8711d3fcddcaf6b7e1fb64d0`, with High effort, native
Opus 5.5, Anthropic API attribution, the same resumed Claude session, an
independently checked 635-byte file and persisted Done status. It uses
the earlier verified Mac daemon; the preceding-source package
qualification passed at `dca62c7aeb4b45f0dd91a8e18d386a16a2658ef8`. That
package run predates the small TypeScript startup fix and is not
relabeled as qualification for it.
- Upgrade limitation: changed compiled sidecar identity rejected old
durable launch state and recovery hit session-open bounds before
eventually resuming. That attempt was operator-cancelled and retained;
the successful manual continuation does not qualify seamless upgrades.

- Local latency profile, Opus 5.5/High unchanged: three alternating
real-ACP loopback samples per variant reduce median provider-ready time
from 5.081s to 4.034s. The matched real API task startup improves from
5.533s to 4.348s, but total reply time changes from 17.933s to 20.221s
because agent work varies. This establishes a startup saving of about
one second, not a consistent total-reply speedup. A real candidate
follow-up passed in 20.146s and resumed the same saved session. The
loopback fixture makes no external model requests; failed initial probes
remain retained.
- The startup change passes 107 focused runtime/effort/lease tests, 53
profile checks (one skipped), TypeScript checking and the
TypeScript-only runtime build. Native hire fixture checks pass 70 tests;
their first local run retained a socket-hangup failure and stale
OpenCode expectation, both accounted for before the passing rerun.
Broader required checks run in cloud CI.

## Risks

- **Experience needs improvement:** successful connection setup still
shows “Connection needs attention” because runtime checks are deferred.
Cold provider-pack upload took 122–126 seconds per run while the task
mainly showed “Thinking.” The tested Core-only preview excludes private
Cloud UI plugins; this is not full Cloud distribution or subscription
qualification. Desktop dark theme was tested; mobile and comprehensive
accessibility were not. The portable report validates, but gallery
interaction could not be inspected because host preview was queued.

- The optional supply-chain scan returned neutral/inconclusive because
GitHub Actions package coverage and infrastructure parsing are
unavailable. It is not counted as a successful supply-chain
qualification. Exact package, daemon and image integrity checks passed.
- A stale, missing or wrong-architecture pack must fail admission. It
must not change runner or target silently.
- Provider-pack source changes invalidate affected earlier execution
results. Existing unknown-cost and cleanup holds remain intact.
- Live subscription execution remains unverified under the API-key
qualification direction. Built-in authentication flows are retained.
ARM64 cloud-image production is deferred. Merge and production
deployment remain separate.

## Model Used

OpenAI Codex, GPT-6 family, with reasoning, repository tools, code
execution and browser testing. The exact serving model ID and
context-window size are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [ ] Focused local tests and final cloud verification pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 14:17:24 -05:00
DottaandPaperclip 45b67f1d93 feat: default new Apple Silicon Claude agents to Paperclip Runner (#15993)
## Thinking Path

> - Paperclip lets users choose an agent harness and account.
> - The server resolves the runner for new agents.
> - Claude still needs the same ordinary native-default journey as
Codex.
> - Existing agents must retain their runner, model and account.
> - This PR defaults new Apple Silicon Claude agents to Paperclip Runner
with Opus 5.5.
> - Users can connect and work without a runner override.

## Linked Issues or Issue Description

Refs #15683. This PR depends on #15994 and precedes #15997. Related
scope: #15422, #13978 and #15224.

## What Changed

- Resolve new Apple Silicon Claude agents to `paperclip_runner`,
`provider: acpx`, `acpxAgent: claude`. Keep explicit Legacy, models,
provider routing and saved execution.
- Use `claude-opus-5-5` for ordinary Claude defaults and retain explicit
overrides.
- Reuse existing API-key/subscription connections, credential storage
and checks. Generalize the shared Advanced runner control with Claude
branding.
- Carry configured effort into the shared v9 contract. Preserve
compatible permissions, instructions, skills, timeouts and session
behavior. Require Legacy for unsupported settings.
- Qualify a new immutable managed Claude target at explicit Connect
through the existing permission-gated probe. Use fresh scoped discovery
for test and hire. Discard stale results and require an explicit Connect
after settings change.
- Retain merged Codex onboarding recovery, auth preparation,
import/effort corrections and Grok Bot gates.
- Check the Claude first-task wizard's saved default directly. Update
configuration/runtime documentation and exact Opus 5.5 accounting.

- Align hire fixtures with the merged host-environment restriction.
Native agent-authenticated hires cannot inject host env settings; both
creation endpoints verify that no extra agent is saved.

## Verification

- Updated onto master `9179d8dcc3e908c217fde4f63c9d08ccf8132eeb` through
#15994. Native input v9 carries effort while preserving v7 home modes
and v8 Muse. Codex defaults remain unchanged.
- Focused local verification passed 285 server tests, 323 UI tests, 124
setup/registry tests, and two v9 permission-pin transport cases. Direct
server/UI TypeScript checks passed. An initial 30-second hook timeout
was resolved by serial verification with a longer hook budget: all 122
credential/permission cases and 232 snapshot/environment cases pass.
Direct server TypeScript checking also passes.
- Ordinary web creation with the experiment disabled saved native
Claude, Opus 5.5 and High effort without runner/model overrides. The
actual product task and follow-up both succeeded on integrated source
`b2c9fe43f9cd3bc5dd9d22552da0148845ba71a4` with the cloud-built daemon
from `04e0202ca81387b17cbe7fd094a8338648356fe9`. The final master
reconciliation also changes shared runtime source. Historical proof
retains its source identity; a final-source cloud qualification is
running before refreshing the preview daemon.
- Both actual browser downloads were checked: v1 has three sections/six
checkboxes (451 bytes); v2 preserves the original body and adds two
Rollback checks (612 bytes). The original attachment stayed
byte-identical. The follow-up records session resume and the same
provider session. Total estimated API usage: $0.518432800, with no
pending/unpriced usage in the successful fixture.
- Fixed the live-discovered setup incompatibility: native API-key
validation no longer depends on the global Legacy Claude CLI. The
existing provider endpoint verifies the key without a paid prompt;
subscription/custom routing probes remain intact.
- Fixed security review's native-hire credential redirection:
agent-supplied URLs, proxy/launch settings and other host environment
controls are rejected before inheritance. Native credential references
remain supported and partial edits use the saved harness. Added
create/hire/update regression coverage.
- Current-head cloud CI is green. All three stack PRs have fresh
Greptile 5/5 reviews and zero unresolved review threads. Required
typecheck, test and build gates ran in cloud CI; Docker work stayed
remote. Earlier failed checks remain in their original runs.
- Docker and native release builds ran in cloud infrastructure. An
inadvertent local Rust prerequisite was stopped; no local Docker build
was run.

- The final master merge preserves task-loading, permission,
skill-retention and OpenRouter changes. Pi uses a fresh combined profile
27, preserving both historical profile-24 declarations; Copilot remains
profile 22. Focused protocol checks passed 155 cases (one skipped), the
updated Pi attestation check passed 18 (one skipped), and 91
evaluation/catalog checks passed.

- Latest-application manual continuation passed in 37.942 seconds on
`695e5c005a85bddc8711d3fcddcaf6b7e1fb64d0`, with High effort, native
Opus 5.5, Anthropic API attribution, the same resumed Claude session, an
independently checked 635-byte file and persisted Done status. It uses
the earlier verified Mac daemon; the preceding-source package
qualification passed at `dca62c7aeb4b45f0dd91a8e18d386a16a2658ef8`. That
package run predates the small TypeScript startup fix and is not
relabeled as qualification for it.
- Upgrade limitation: changed compiled sidecar identity rejected old
durable launch state and recovery hit session-open bounds before
eventually resuming. That attempt was operator-cancelled and retained;
the successful manual continuation does not qualify seamless upgrades.

- Local latency profile, Opus 5.5/High unchanged: three alternating
real-ACP loopback samples per variant reduce median provider-ready time
from 5.081s to 4.034s. The matched real API task startup improves from
5.533s to 4.348s, but total reply time changes from 17.933s to 20.221s
because agent work varies. This establishes a startup saving of about
one second, not a consistent total-reply speedup. A real candidate
follow-up passed in 20.146s and resumed the same saved session. The
loopback fixture makes no external model requests; failed initial probes
remain retained.
- The startup change passes 107 focused runtime/effort/lease tests, 53
profile checks (one skipped), TypeScript checking and the
TypeScript-only runtime build. Native hire fixture checks pass 70 tests;
their first local run retained a socket-hangup failure and stale
OpenCode expectation, both accounted for before the passing rerun.
Broader required checks run in cloud CI.

## Risks

- Missing packages, authentication rejection, unsupported settings and
unavailable models must fail explicitly. Existing agents retain saved
execution; explicit runner changes use existing revision/session
invalidation.
- Subscription follow-up remains unverified; remaining live acceptance
uses API keys per human steering. Historical accounting holds and the
separate $50 ceiling remain intact.
- The subscription acceptance limit remains explicit for review. No
Claude database migration is introduced.

## Model Used

OpenAI Codex, GPT-6 family, with reasoning, repository tools, code
execution and browser testing. The exact serving model ID and
context-window size are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [ ] Focused local tests and final cloud verification pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 13:58:52 -05:00
DottaandPaperclip 95672307f4 feat(runner): carry acknowledged Claude effort through native resume (#15994)
## Thinking Path

> - Paperclip manages AI agents and their work.
> - The native runner must carry each supported agent setting.
> - Claude effort must reach its ACP session before a prompt and after
resume.
> - Installed Claude setup must find the owning server package without a
qualification override.
> - This PR adds those shared contracts and preserves historical
readers.
> - The Claude default change can then use the same runner path.

## Linked Issues or Issue Description

Refs #15683. This prerequisite follows the actual Codex squash
`adb69e8f09852c772d9901ae270e5b2d66e39c77`. Consumers: #15993 and
#15997. Related scope: #15422, #13978 and #15224.

## What Changed

- Add native-input v9 for Claude effort. Preserve v1–v8 readers,
including v7 explicit home modes, v8 Muse, Dot and Grok Bot.
- Preserve prepared task input and constraints through the newer
contracts, including completion-only continuation without wrapping
compact model input again.
- Carry effort through daemon/sidecar admission; require provider
acknowledgment before prompting and after resume.
- Find installed server package authority through the verified canonical
layout. Retain package-integrity, digest, architecture and no-follow
checks.
- Return Claude startup cancellation promptly while retaining unfinished
settings writes and the lifetime lease through cleanup. Preserve merged
Codex close/cleanup behavior.
- Retain both independently authored historical Pi profile-24
declarations. Combined master/Claude source attestations use Pi profile
27; pending Copilot remains profile 22. This does not expand either
provider's qualification boundary.

- Avoid a spare verified executable snapshot when Claude effort control
reuses its initialized provider. Preserve cold-control snapshot renewal
and acknowledged effort.

## Verification

- Reconciled with master `9179d8dcc3e908c217fde4f63c9d08ccf8132eeb`,
retaining its task-loading, progress, skill-retention, permission and
OpenRouter changes.
- Final focused protocol/provider checks passed 155 tests (one skipped),
the updated Pi attestation check passed 18 (one skipped), and 91
evaluation/catalog checks passed. Generated TypeScript/Rust profile
checks and Rust formatting pass. The integrated consumer's
TypeScript-only runtime build also passes.
- Earlier branch checks passed 369 protocol tests (one skipped), 72
catalog checks and TypeScript checks/build; their source identities
remain historical. No Rust compilation or Docker build is needed locally
for this proof.
- Current-head cloud CI is green. All three stack PRs have fresh
Greptile 5/5 reviews and zero unresolved review threads. Required
typecheck, test and build gates ran in cloud CI; Docker work stayed
remote. Earlier failed checks remain in their original runs.
- [Earlier four-target package
qualification](https://github.com/paperclipai/paperclip/actions/runs/39267321383)
passed on source `04e0202ca81387b17cbe7fd094a8338648356fe9`; it is not
relabeled as proof for the final merge. Existing failures and
unknown-cost holds remain preserved.
- Current-head cloud CI is green. All three stack PRs have fresh
Greptile 5/5 reviews and zero unresolved review threads. Required
typecheck, test and build gates ran in cloud CI; Docker work stayed
remote. Earlier failed checks remain in their original runs.

- Latest-application manual continuation passed in 37.942 seconds on
`695e5c005a85bddc8711d3fcddcaf6b7e1fb64d0`, with High effort, native
Opus 5.5, Anthropic API attribution, the same resumed Claude session, an
independently checked 635-byte file and persisted Done status. It uses
the earlier verified Mac daemon; the preceding-source package
qualification passed at `dca62c7aeb4b45f0dd91a8e18d386a16a2658ef8`. That
package run predates the small TypeScript startup fix and is not
relabeled as qualification for it.
- Upgrade limitation: changed compiled sidecar identity rejected old
durable launch state and recovery hit session-open bounds before
eventually resuming. That attempt was operator-cancelled and retained;
the successful manual continuation does not qualify seamless upgrades.

- Local latency profile, Opus 5.5/High unchanged: three alternating
real-ACP loopback samples per variant reduce median provider-ready time
from 5.081s to 4.034s. The matched real API task startup improves from
5.533s to 4.348s, but total reply time changes from 17.933s to 20.221s
because agent work varies. This establishes a startup saving of about
one second, not a consistent total-reply speedup. A real candidate
follow-up passed in 20.146s and resumed the same saved session. The
loopback fixture makes no external model requests; failed initial probes
remain retained.
- The startup change passes 107 focused runtime/effort/lease tests, 53
profile checks (one skipped), TypeScript checking and the
TypeScript-only runtime build. Native hire fixture checks pass 70 tests;
their first local run retained a socket-hangup failure and stale
OpenCode expectation, both accounted for before the passing rerun.
Broader required checks run in cloud CI.

## Risks

- Explicit Claude effort needs a daemon and sidecar that support input
v9. Historical readers stay available; downstream builders and
permission-pin transport checks must also use v9.
- Source-bound profile changes may require reopening older Pi/Copilot
sessions. Copilot remains pending and executable package closures remain
unchanged.
- This prerequisite changes shared runtime behavior; Claude default
selection remains in #15993/#15997. No database migration or Codex
default change is introduced.

## Model Used

OpenAI Codex, GPT-6 family, with reasoning, repository tools, code
execution and browser testing. The exact serving model ID and
context-window size are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 13:31:09 -05:00
Nicky LeachandPaperclip 194fc11406 feat(plugins): invalidate runtimes when tool definitions change (#16604)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Lifecycle plugins must refresh runtime preparation when tool
definitions change.
> - Standing assignments alone do not cover catalogs, profile entries,
or policies.
> - New journal hooks must preserve the order used by setup
finalization.
> - This pull request adds tool-definition invalidation and its required
writer guards.
> - It leaves credentials and provider access changes for the next
independent capability.

## Linked Issues or Issue Description

**What happened?**

Catalog, profile-entry, policy, gateway, and connection-configuration
changes do not request agent runtime synchronization. A new
profile-entry trigger also exposes a deletion/finalization deadlock if
the child row is changed before its parent is locked.

**Expected behavior**

Committed tool-definition changes advance runtime revisions without
polling. Bookkeeping does not. Entry changes and profile replacement use
a consistent parent/reference lock order and commit atomically.

**Steps to reproduce**

1. Change a catalog descriptor, profile entry, policy, or connection
configuration.
2. Expect committed runtime events for the affected agents.
3. Run profile-entry deletion concurrently with setup finalization while
both wait for an agent row.
4. Expect both operations to complete without PostgreSQL deadlock 40P01.

**Additional context**

Extracted from #16503. Catalog publication #16602 and standing
assignments #16603 are merged. This PR is rebased onto master and is the
active review. It addresses the original Apex profile-entry deletion
finding. Credential/access hooks #16605 remain a draft without review
requests.

## What Changed

- Add migration 0355 for application/connection configuration, catalog,
profile-entry, policy, and MCP gateway invalidation.
- Preserve transaction coalescing and ignore health bookkeeping and
trust-rule usage counters.
- Keep credential-only fields outside this migration's coverage.
- Preserve merged recipient scoping for bindings and installations.
Profile-entry edits resolve old/new standing profile bindings. Policy
edits resolve old/new agent selectors with their intersection/list
semantics.
- Lock old and new profile-entry references before parent profiles and
child mutations. Recheck the reference set under the parent lock, retry
changed snapshots up to three times, and merge unspecified fields from
the locked profile.
- Make entry add/edit/delete and profile replacement transactional,
including validation and profile reads on the reserved connection.
- Lock policy rows in ID order and change priorities in one statement so
scoped agent locks are ordered across the full set.
- Lock the managed profile before connection removal deletes its entries
in the same transaction.
- Update assignment tests whose old absence assertions are superseded by
expanded configuration coverage.
- Document the supported capability and the remaining credential/access
boundary.

## Verification

- Final head: `809fcb11794bfb12c545af0a2f96ab9bc2b570a2`. It is rebased
onto master with merged #16623. GitHub reports no merge conflicts. [CI
run
39293925136](https://github.com/paperclipai/paperclip/actions/runs/39293925136)
has 55 successful checks and two optional Storybook skips.
- Standard Greptile returned an independent 5/5. The final Apex review
returned 5/5 on this exact head at 17:47 UTC on 2026-10-19. Its summary
explicitly clears this PR for merge independently of draft #16605. The
security scan passed. All review threads are resolved.
- Two real-PostgreSQL negative controls reproduce `40P01` without the
old-reference guard or the concurrent-snapshot check. Both regression
tests pass with the final correction. Server typecheck, migration safety
and numbering, five-snapshot retention, journal history, feature maps,
and diff checks pass. The actual PR diff was scanned for secrets and
personal data before push.
- The final 15-suite local run passed 821/822 tests. The one failure was
in the unchanged runtime-delivery test: a startup callback changed its
global callback count during an independent transaction. The test-only
correction is isolated in #16871. That PR passes all 17 runtime-hook
tests, server types, hosted CI, and standard Greptile 5/5. Its
notification-disabled control fails at the independent event-delivery
assertion. No changes from #16871 are included here; this feature head
passes hosted CI independently.
- Earlier affected-suite runs passed 814 tests after rebase and 820
tests after recipient and whitespace corrections. Four affected suites
passed 514 tests before the second reference-contention regression was
added. Single-connection tests cover entry add, edit, delete, and
replacement. Validation and profile reads use the reserved transaction
connection.
- Review fixes have negative controls: the old code hangs with a
one-connection pool; parent-lock omissions deadlock entry deletion or
app removal against setup finalization; per-row policy reorder deadlocks
under contention; unscoped triggers journal unrelated peers; default SQL
trimming misses JavaScript whitespace. Corrected cases pass. Selector
tests cover all 25 ECMAScript whitespace characters. Recipient tests
cover repeated edits, old/new targets, ignored bindings, rollback,
coalescing, and company scope. The definition suite now has 28 cases.
- Earlier standard scores that depended on #16605 were not accepted as
independent clearance. The first Apex review returned 4/5 for
replacement versus application deletion. The final correction locks old
and new references, checks the reference set again under the parent
lock, and retries before any mutation. The final independent reviews
clear that correction.
- Preserve prior failures for acceptance: draft run 38975432017 had
failures whose causes were not re-investigated. Run 38990400765 exposed
the unrelated durable-resume watchdog race, fixed in merged #16623. In
run 39287657148, two jobs reported cancellation without a failed-test
summary; the cause remains unknown. Both passed on retry without source
changes. Initial local fixtures and SQL bindings also needed correction:
an internal helper name was replaced with public `archiveConnection`,
unchanged priorities were changed to exercise reorder, a driver
timestamp was bound as ISO text, and a superseded company-fanout
assertion was updated. These recovered checks do not establish a cause
for the unexplained CI failures.
- Local checks target the affected services and real database
boundaries. A full local build and repository-wide test run were not
performed. Hosted CI supplies the broader checks. Provider responses in
tests are controlled; live provider behavior was not qualified.

## Risks

Migration 0355 adds statement triggers without changing table schema.
Apply it through the normal migration flow. A tool-definition event can
advance a runtime revision without changing the bounded assignment
snapshot. Consumers still need authorized readers for definitions.
Credential-only changes, grants, secrets, and endpoints remain for the
access-hook migration. Profile replacement now rolls back as a unit if
any entry fails. Binding and install notifications retain scoped
recipients. Profile-entry changes use standing bindings, and policies
use old/new agent selectors. Unscoped policies, company-bound profiles,
and other conservative definition changes retain synchronous
transaction-atomic company-wide fanout: O(eligible company agents) locks
and journal storage, without a fanout ceiling or mutation quota. This
retains the accepted tradeoff from #16603 for company-wide changes.

## Model Used

OpenAI Codex, GPT-6, with reasoning, repository inspection, code
execution, and testing. The exact deployment model ID and context window
are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run local checks; results and the isolated test failure are
recorded above
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 10:56:08 -07:00
DottaandPaperclip 985d3b12b6 fix(runner): explain rejected task monitor arguments (#16868)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Agents use task monitors to resume work after a future check.
> - The runner rejects monitor arguments that fail the tool schema.
> - It returned a generic error with no field or repair guidance.
> - An agent could treat a repairable call as a scheduling outage and
block its task.
> - This pull request adds safe repair guidance and shows the nested
request shape.
> - Agents can correct the call and confirm a saved schedule before they
yield.

## Linked Issues or Issue Description

Refs: #15446, #16686.

**What happened?**

A rejected native `set_task_monitor` call returned `invalid_tool_call`
with only “Paperclip rejected this semantic tool call.” The agent could
not identify the invalid field. A retry could fail again and leave
unfinished work without a scheduled wake.

**Expected behavior**

Reject invalid arguments before any mutation. Give the provider bounded
schema locations and clear repair guidance. A corrected call must save a
monitor and allow one wake without duplicate effects.

**Steps to reproduce**

1. Call `set_task_monitor` with `idempotencyKey`, `nextCheckAt`, and
`notes` at the top level.
2. The schema rejects the call because scheduling fields belong inside
`monitor`.
3. Before this change, the provider received no guidance about the
required shape.

**Paperclip version or commit**

Reproduced against master `35c75b56d4` with a failing Rust regression.

**Deployment mode**

Source checkout. This affects the native runner tool bridge.

## What Changed

- Add monitor-specific repair guidance to the runner's existing safe
schema error path.
- Keep feedback within 512 bytes and omit submitted values and unknown
field names.
- Show the nested monitor request in the production tool description.
Refresh generated contracts and catalog identities.
- Test flat and nested invalid input, private value handling, and
unchanged authorization errors.
- Test rejection, correction with the same key, saved schedule and
audit, receipt replay, and one timer wake with real PostgreSQL and the
native tool authority.
- Update execution documentation and the task verification recipes.

## Verification

- Red/green: the Rust provider error regression failed on master because
monitor repair guidance was absent. It passed after the fix.
- Passed: 29 PostgreSQL monitor and scheduler integration tests. These
use the real tool authority and scheduler, with a no-op process agent
for wake delivery.
- Passed: the native Codex server vertical-slice test. It runs the
rebuilt Runner binary with a fake provider and checks durable results
and session resume.
- Passed: map structure checks, Rust formatting, and `git diff --check`.
- Passed locally: full repository `pnpm -r typecheck`, `pnpm build`, and
all 392 Rust library unit tests.
- Passed on commit `3b667ad24763c1828edd48f56ef7a10766aeb946`: [CI run
39290889768](https://github.com/paperclipai/paperclip/actions/runs/39290889768),
including all server, Runner, serialized, browser, typecheck, build, and
canary gates. Across the PR, 56 checks passed and four conditional
checks were skipped. No check remains pending or failed.
- Greptile: 5/5 on that exact commit. The check concluded success, with
no review comments or unresolved threads.
- The duplicate local `pnpm test:run` attempt did not complete. It was
stopped after the full CI suite passed; it is not counted as a local
full-suite pass.
- The first PostgreSQL attempt could not bind localhost inside the shell
sandbox. It passed with normal localhost access. The first broader Rust
attempt had 37 socket-permission failures and 355 passes; all 392 passed
with localhost access and no code change.
- Live model recovery was not run. Local execution policy did not
authorize an extra acceptance run through the signed-in provider
account. This PR does not include a deployment or recovery of an
existing task.

## Risks

- Error feedback must not reveal submitted values. Tests cover private
values, unknown keys, nested constraints, length bounds, and unchanged
generic authorization errors.
- This changes guidance only. It does not relax the schema, retry calls
automatically, or change scheduling authority.
- A new runner binary and refreshed provider contract must reach the
target instance before agents receive this guidance.

## Model Used

OpenAI Codex, GPT-6, with reasoning, tool use, and code execution. The
exact runtime suffix and context window size are not exposed in this
session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 12:37:28 -05:00
DottaandPaperclip 3e5a9f5afe perf(ui): load recent tasks with bounded summaries (#16851)
Replace passive recent-task detail reads with bounded, authorized summaries. Keep account isolation, stored history, task actions, and live recovery behavior.

Overlap access checks with shell settings and avoid duplicate session and health reads on the first healthy socket opening. Retain domain reconciliation.

Add focused coverage and local performance evidence. Isolate the existing cache capacity test from entry expiry on slow CI runners.

Co-Authored-By: Paperclip <noreply@paperclip.ing>
2026-10-19 12:13:28 -05:00
DottaandPaperclip 23b2ceb0d1 feat(connections): add unified Google Workspace connector (#15545)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Connected Apps supply governed tools to those agents.
> - Google services currently require separate connections or one broad
request.
> - Users need one account and control over which services it can
access.
> - A picker must change the OAuth request, not just the screen.
> - This pull request binds selected services to consent and tool
access.
> - The benefit is simpler setup without enabling unselected tools.

## Linked Issues or Issue Description

**Subsystem affected**

Connections catalog, OAuth grants, and the MCP tool gateway.

**Current behavior**

Google setup uses separate service profiles. A combined request alone
cannot express the user's choice before Google consent. Accumulated
Google grants can be broader than a new request.

**Proposed behavior**

Offer one Workspace connection. Let users choose Gmail, Drive (including
Docs, Sheets, and Slides), and Calendar. Start all three with read and
write access. Let users disable groups or choose read-only access. Do
not offer Chat, Contacts/directory, or cross-service Search in new
setup. Bind selected scopes to durable OAuth state. Cap effective tool
access to both the saved request and provider-reported consent.

**Reason and benefit**

Users can choose services without managing several accounts. Existing
company, identity, agent, and action-policy controls remain in force.

**Breaking changes**

No database migration. Existing service connections and grants remain
supported. New Workspace requests require the companion broker change in
https://github.com/paperclipai/paperclip-cloud/pull/823. Old brokers
reject narrowed requests safely.

Related work: #14740 reduced Google scopes; #14774 introduced the
earlier catalog hold. #15412 proposes a separate Gmail REST
implementation. This maintainer-requested change extends the existing
Connections and governed tool gateway paths. It does not replace them.

## What Changed

- Add one Workspace catalog entry and a namespaced action catalog.
Retain legacy definitions and saved accounts.
- Use the approved production service picker in Apps and task-hosted
setup. Keep dropdowns between names and toggles. Block empty selection.
- Derive exact scopes from a closed registry. Default selection requests
nine scopes. New requests exclude Chat, Contacts/directory, and Search
scopes.
- Bind selected scopes through managed and customer-owned OAuth state,
callback, claim redemption, and refresh.
- Cap accumulated Google grants to the saved selection. Recheck
grant-specific permission at discovery, listing, and dispatch, including
cached actions.
- Restore the current subject's saved request on reconnect. Block on
grant-load failure. Preserve draft selection on cancel and retry. Do not
create an account on picker cancellation.
- Preserve healthy services during partial outages, without combining
grants across identities. Keep writes from being automatically replayed.
- Preserve the original 21-scope legacy Workspace envelope contract as
individual profiles evolve.
- Add production-component Storybook stories, request validators,
consent regression tests, and rollout guidance. Integrate the stories
with the current feature catalog while preserving their IDs.

## Verification

- Integrated branch merges current master and has no merge conflicts.
- Full workspace build passed on the integrated checkout.
- Token gates passed. Storybook catalog structure check passed: 283
files and 2,750 stories.
- Final affected app suites: 914 passed. This includes 502
database-backed service/gateway tests and 412
UI/shared/validator/broker-handoff/governance tests. The production
picker tests cover defaults, identity-specific reconnect, and
failed-load recovery.
- Full workspace typecheck passed after adding required current-master
Storybook annotations. The final UI build also passed.
- The full repository suite is still running and includes the two
pre-fix retry assertions. Both were updated for the current gateway's
explicit-retry contract and pass in the clean 502-test database run. No
complete final-head full-suite pass is claimed.
- The initial local database startup failure came from missing
native-library symlinks in the fresh dependency install. The package's
postinstall repair fixed it; the clean database-backed run has no
skipped tests.
- Broker focused suite: 47 passed, including real signed session →
callback → claim redemption and wrong-scope rejection. Full broker suite
before the final test-only follow-up: 3,562 passed, 103 skipped.
- Real integrated-app walkthrough: Connectors → Workspace →
customer-owned app → service picker. Verified all three defaults,
empty-selection blocking, cancel/reopen with the selected read-only
access preserved, preserved form values, and zero saved connections
after cancel. Credentials were synthetic; no Google grant was made.
- Current-head CI and Greptile review remain pending. Previous-head
results are not treated as current.

## Risks

Ship the companion broker before app instances send narrowed requests.
Enable the intended Workspace client/profile separately on the target
broker. This pull request does not deploy a tenant app, start a fleet
rollout, alter Google Console, or upgrade the pinned reviewer stack.

The three-group picker is not proof of live provider access. Before
production, verify a real selected-service grant, reconnect, refresh,
allowed reads/writes, and denied unselected actions on the isolated
staging reviewer app. Google verification and preview enrollment remain
separate requirements.

Legacy service profiles stay compatible. New grant metadata keeps
provider scope evidence separate from requested scope evidence. Missing
or unsupported evidence fails closed. No scope union across user or
organization grants is allowed.

## Model Used

OpenAI Codex, GPT-5-based coding agent, with repository editing, code
execution, and browser tools. The exact serving model ID and
context-window size were not exposed.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have described the issue in-PR following the relevant issue
template
- [x] I have not referenced internal/instance-local Paperclip issues or
links
- [x] My branch name describes the change and contains no internal issue
ID
- [ ] I have run all final-head tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented risks above
- [ ] All Paperclip CI gates are green
- [ ] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 12:07:30 -05:00
DottaandPaperclip d5b92cc41b perf(ui): reduce task startup initialization and redundant reads (#16862)
## Thinking Path

> - Paperclip users open tasks to read saved work and reply.
> - Faster startup must preserve message positions and composer state.
> - Chrome CPU samples showed unused shared schemas and catalog indexes
being initialized before task content.
> - The shared package exports definitions and module-local data, with
no required import-time registrations.
> - Let the browser bundler discard unused shared modules.
> - Readiness marks also exposed a duplicate plan read even though full
task detail contains that plan.
> - Keep both improvements measurable through CPU profiles, gate
transitions and real browser acceptance.

## Linked Issues or Issue Description

Follow-up to #16849. Related layout work: #14758. Searches found no
overlapping plan-cache PR.

**What existing behavior does this improve?**

Task startup evaluates unused schemas and catalog indexes reached
through the shared package barrel. The task also waits for a second
plan-document request after full task detail arrives, even when that
response already includes the plan or an explicit absent-plan value.
Profiling showed that removing the request alone gave a small and
variable total gain; unused initialization was the larger cold-load
opportunity.

**Subsystem affected**

Board task loading, shared-package bundling metadata, plan-query
caching, and local issue-detail profiling.

**Proposed behavior**

Discard unused shared modules during browser bundling. Fill an unused
plan query when a full task response arrives. List-only snapshots keep
their normal plan fetch. Keep the existing coordinated reveal.

## What Changed

- Declare the shared package side-effect free so the bundler can drop
unused module initialization. Used schemas and catalog data still
initialize normally.
- Seed an absent plan query at the successful full-task HTTP response
boundary. Use a 30-second plan-query freshness window. List cache merges
do not update this plan cache, and a later detail response never
overwrites an existing plan query.
- Preserve document-scope invalidation for plan creation, edits and
deletion.
- Add opt-in Chrome CPU profiles and readiness transitions to the
existing performance harness. Diagnostic runs use one sample per
scenario/profile and are labelled separately from latency benchmarks.
- Record only fixed gate names and readiness booleans in local browser
marks. Reset the gate effects on task changes so fully cached navigation
is profiled too.

## Verification

- Production UI build, UI typecheck and token design gates passed.
- 258 focused unit tests passed. The final freshness follow-up passed 14
tests, including query eviction followed by a list refresh, preserving a
separately fetched newer plan, missing projection, task isolation, and
document-event refresh/deletion.
- Two focused reuse tests fail with the original HTTP cache function and
pass with the fix. The original production browser case makes redundant
plan reads and fails.
- All 13 final browser cases passed serially: eight layout scenarios,
four plan-present/absent and direct/list startup cases, and a
cached-task switch that records every gate. The cached-switch case
failed before the identity dependencies were added.
- One earlier concurrent browser run failed a properties-resize
reading-anchor assertion. Two isolated repeats and the final serial
suite passed. This outlier is retained in the local logs; it was not
treated as a reason to change the unchanged scroll owner speculatively.
- Actual CPU samples and readiness artifacts were captured on a
disposable local production preview. This is browser timing data, not
exported telemetry.
- Audited 247 non-test shared modules for required import-time
registration. The four top-level loops construct exported local catalog
data. No required registration or side-effect-only shared imports were
found.
- A compiled browser-library contract accepted valid task input,
rejected an empty title, retained all seven agent statuses, and retained
GitHub metadata plus 1,576 catalog entries. All 13 browser scenarios
passed against the initialization candidate too.
- Plan reuse alone did not establish a reliable total gain: a final
local run was 4,356 ms cold and 1,116 ms warm on Fast 4G/4x CPU.
- The next five-sample run with unused shared initialization removed
measured **3,298 ms cold (24% faster)** and 1,079 ms warm. Median issue
API server time was 35 versus 39 ms. First contentful paint fell from
2,808 to 1,648 ms. JavaScript before content fell from 1,722 to 1,670
KiB; CPU initialization mattered more than byte size.
- Final alternating comparison: five samples per variant for both cold
and warm navigation, same persisted task and Fast 4G/4x CPU settings,
fresh browser per sample, order alternated between variants. **Cold
content paint: 4,588 → 3,688 ms (20% faster). Warm: 996 → 1,030 ms (+35
ms).** No CPU profiler was active. The final initialization commit is
the only source difference between these two builds.
- These local measurements do not establish deployed staging latency or
a speedup across every profile. Unthrottled timings varied with API
latency.
- Actual UI walkthrough on the final bundle: read the saved plan and
conversation, submit one unassigned reply, refresh, navigate to Projects
and Back, and inspect the new-task dialog. The reply persisted exactly
once, confirmed independently through the comments API. No paid agent
was woken.
- Final head `a7043c474d`: Greptile 5/5, all review threads resolved,
and all 56 checks passed, including full typecheck, build, unit and E2E
suites.


## Risks

Bundlers can discard unreferenced shared modules. Future required
registrations or global initialization must be declared in the package
side-effects metadata. Current module-local catalog construction remains
when its exports are used.

Merged list snapshots can retain old plan fields while receiving a new
task-cache timestamp. This change seeds only from a new full HTTP
response, rather than inferring plan freshness from those merged
snapshots. Existing plan-query state is never overwritten. List-only,
stale, invalidated, or incomplete data still uses the normal plan read.
Existing document invalidations refresh the query. No API, database,
permission or reveal-policy changes.

## Model Used

OpenAI Codex, GPT-6, with reasoning, repository tools, code execution
and browser verification. A more precise runtime model identifier and
context-window size are unavailable.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 12:03:53 -05:00
DottaandPaperclip 35c75b56d4 fix(pi): credit Paperclip for default legacy OpenRouter requests (#16864)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Legacy adapters can use host credentials and provider settings.
> - OpenRouter assigns app credit from the final request headers.
> - The first attribution change covered managed connections and
explicit provider configs.
> - Legacy Pi with only an API key bypassed those config changes.
> - This pull request applies attribution at Pi's request boundary.
> - The benefit is Paperclip credit without replacing the user's Pi
home.

## Linked Issues or Issue Description

Follow-up to #16850. A search of related OpenRouter PRs and issues found
no duplicate fix for this path.

**What happened?**

A legacy `pi_local` agent with `OPENROUTER_API_KEY` and no
`PAPERCLIP_PI_PROVIDERS` could send requests without Paperclip
attribution. Existing Pi home configs could also retain the previous
harness title.

**Expected behavior**

Paperclip receives credit for OpenRouter requests from its legacy Pi
adapter. The adapter preserves credentials, routing, model settings, and
other providers.

**Steps to reproduce**

1. Configure a legacy Pi agent with an OpenRouter model and API key.
2. Leave `PAPERCLIP_PI_PROVIDERS` unset.
3. Start a run and inspect its outgoing headers or OpenRouter generation
record.

**Paperclip version or commit**

Reproduced after #16850, on master commit
`9179d8dcc3e908c217fde4f63c9d08ccf8132eeb`.

## What Changed

- Load a temporary attribution extension for every legacy Pi run,
including remote targets and retries.
- Apply headers after credential and model-header resolution on Pi 0.74
and at provider dispatch on Pi 1.0.
- Check the actual endpoint. Cover custom aliases and regional
OpenRouter hosts. Preserve other endpoints, credentials, unrelated
headers, and explicit visibility preferences.
- Keep the Pi home, auth file, settings, and model catalog in place.
Remove the temporary extension after the run.
- Prevent repeated wrapping when Pi recomposes a provider after a
registry refresh. Add regression tests and update the connector
playbook.

## Verification

- Final head `902399468a9033d12e3ff6ab30c8463daef50bad`: Greptile
**5/5**, with no actionable comments. CI is waiting for runner
assignment.
- Complete legacy Pi adapter suite: **124 tests passed across 12
files**, including extension, runtime-config, and remote execution
coverage. The initial focused subset passed 30 tests.
- `pnpm -r typecheck` and `pnpm build` passed. After the lifecycle
guard, all 124 Pi tests and the Pi package typecheck passed again. Full
`pnpm test:run` is in progress.
- Actual Pi 0.74 outgoing-request comparison with dummy credentials: the
baseline sent no attribution headers. The patched request sent all four
Paperclip headers and retained the same credential. The transport
returned an intentional 401 after capture; this check does not claim
successful inference.
- Final-head Pi 0.74 request-capture matrix: **8/8 passed**. Cases cover
bare keys, host aliases, per-model overrides, EU/US endpoints, a
repointed built-in provider, an unrelated provider, and an HTTP
endpoint. Credentials, custom routing headers, and visibility
preferences survived. These captures used dummy credentials and
intentional 401 responses.
- Live request through the actual legacy adapter with Pi 0.74: response
`legacy attribution verified.`; generation
`gen-1792424885-G3THa6DdJXmAL3C841DI`; OpenRouter app ID **3118063**;
cost **$0.0002268**.
- Live request through the actual legacy adapter with the Pi 1.0 bundled
CLI: response `legacy attribution verified.`; generation
`gen-1792425530-LlpIbfBFyjs6XRP5l5PV` on final head
`902399468a9033d12e3ff6ab30c8463daef50bad`; OpenRouter app ID
**3118063**; cost **$0.0002391**. Its usage record became available on a
later read.
- Both live runs preserved the existing `models.json`, `settings.json`,
and `auth.json` byte for byte. Pi 0.74 also retained the custom
`X-Route` header while replacing the conflicting harness title.
- Built-package smoke passed. `npm pack --dry-run --ignore-scripts`
includes `dist/server/openrouter-extension.js`, and the compiled helper
produced a working self-contained extension. The pack check used a
temporary npm cache because the default cache was not writable.
- Remote asset delivery is covered through the SSH execution test
boundary. No live remote sandbox was used.
- Initial capture attempts produced no requests because the test left
stdin open. A separate source-checkout live attempt lacked the
TypeScript loader and did not reach the provider. Correcting the test
setup produced the evidence above. Pi 1.0's bundled transport bypassed
the global-fetch capture shim; its acceptance evidence is the successful
live request and provider-side app ID.

## Risks

- The extension depends on Pi 0.74's request-auth registry and Pi 1.0's
provider API. Harness upgrades require a fresh request capture or live
credit check.
- Missing extension delivery stops remote startup rather than silently
losing attribution.
- A private gateway that replaces headers and an externally managed
harness remain outside this adapter's control. Public listing metadata
still belongs to OpenRouter.
- No database, API, credential ownership, or telemetry contract changes
are required.

## Model Used

OpenAI GPT-6 through Codex, with reasoning, repository editing, shell
execution, and live API verification. The exact runtime model identifier
and context-window size are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass — the focused suites above;
the full suite is still running
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [ ] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 11:55:52 -05:00
DottaandPaperclip 9179d8dcc3 fix: credit Paperclip for managed OpenRouter requests (#16850)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - AI connections choose credentials and routes independently of the
agent harness.
> - OpenRouter assigns app credit from the final request headers.
> - Harness defaults can assign Paperclip work to the underlying
harness.
> - This pull request applies one public Paperclip identity to managed
OpenRouter requests.
> - The benefit is consistent app credit across supported harnesses and
internal model calls.

## Linked Issues or Issue Description

**What existing behavior does this improve?**

App attribution for existing OpenRouter connections and explicit
provider configurations.

**Current behavior**

Requests can omit attribution or carry the harness identity. Paperclip
does not receive consistent credit in OpenRouter rankings.

**Proposed behavior**

Use `https://paperclip.ing`, the title `Paperclip`, and the coding
categories `cloud-agent,programming-app` for managed requests to
OpenRouter. Keep credentials, routing, and unrelated providers intact.

**Reason and benefit**

The provider URL identifies the app across personal and shared API keys.
A search of public issues and pull requests found no duplicate
attribution work. This improves existing AI connections and does not add
a separate roadmap feature.

## What Changed

- Add a shared attribution policy and a parity-checked copy for the
standalone Runner.
- Apply it to managed Codex, Claude, OpenCode, and Hermes connections,
plus native Pi and explicit legacy provider configs.
- Preserve attribution across Codex config filtering, Claude environment
filtering, OpenCode proxy requests, and model-level overrides.
- Attribute direct fast-response and decision-model requests, including
custom connections to the OpenRouter endpoint.
- Add positive and negative regression tests and provider attribution
requirements to the connector playbook.
- Advance native Pi to profile 24, preserving historical identities and
binding the attribution source in its declaration and release checks.

## Verification

- Final head `6df282d2a58c2698e41127443903d6fc85b4b72f`: all CI/status
checks passed or were intentionally skipped; Greptile is **5/5**, with
zero unresolved review threads. [Final CI
run](https://github.com/paperclipai/paperclip/actions/runs/39274938069).
- Focused server/shared/config suites: 132 tests passed before the final
edge-case additions. Expanded adapter suites pass 48 tests; the final
OpenCode merge passes 15 tests; global/EU/US endpoint and policy-parity
suites pass 26 tests.
- Focused Runner suites: 85 tests passed, including model overrides and
recovery/config boundaries. Profile installation/environment/config
tests subsequently passed 72 tests (one optional distribution test
skipped); historical decoding passed 11 tests and updated recovery
coverage passed 27 tests. The Rust profile admission test and all five
native Pi launch/recovery tests passed.
- All 114 managed AI connection tests pass together. They include
custom-header preservation for legacy and native Claude runs, both
OpenRouter and other gateways, inherited headers, and unresolved secret
references.
- Actual requests from installed Codex 0.160.0, Claude Code 2.1.245,
OpenCode 1.18.34, Pi 0.74.0 and 1.0.0, and the managed Hermes runtime
carried all four Paperclip headers. A local endpoint used dummy
credentials and returned an intentional 401 after capture. Codex and
Claude retry requests retained attribution. This proves outgoing header
precedence; it is not a successful model-inference test. The first
Claude capture had an argument-separation error and sent no request;
correcting the command produced the captured requests.
- A live request through `fastResponseModel` completed with `attribution
verified`. OpenRouter recorded generation
`gen-1792420273-Ez1GUTCc7YuZ1FJMCGob` under app ID `3118063`, at a cost
of $0.00000375. The public app record maps that ID to
`https://paperclip.ing/`.
- Full `pnpm -r typecheck` and `pnpm build` passed, including a repeat
after the review fixes. The final server build stamp records commit
`6df282d2a58c2698e41127443903d6fc85b4b72f`. `pnpm check:token-gates`
passed.
- CI first caught the stale Pi source attestation; it is now a new
immutable profile. Greptile caught custom-header loss, now fixed and
covered by the complete managed-connection suite. The next CI run caught
the missing Docker allowlist entry for profile 24; the allowlist and
release smoke pins are now synchronized. Local Docker verification
cannot run because its daemon socket is absent; The exact Docker context
check passed in CI on the final head.
- The initial local `pnpm test:run` did **not** pass. It ran across
source/build edits, reported chat/tool-access collection failures, three
workspace-runtime failures, two new managed-header failures, one Dot
Runner readiness failure, and two native-session-resume failures, and
was interrupted after the final-head CI server coverage passed. Its
secrets suite also reported 91 cases skipped. The isolated tool-access
suite passed all 428 tests, and the complete managed-connection suite
passed all 114 tests. These retries establish recovery, not the cause of
the original local failures; no claim of a successful full local run is
made. Final acceptance uses immutable final-head CI plus the focused
local and live checks above.
- Final-head CI encountered one unchanged UI assertion in
`FileViewerSheet.copy.test.tsx` (missing “Copied link” feedback after
clipboard completion). That shard passed on the earlier head with
identical UI code, and all six clipboard tests passed locally. A timing
race around the asynchronous React update is suspected but not
conclusively established. The single CI retry passed, with no
product/test code changed for it. The earlier failure remains part of
this verification record.

## Risks

- Native Pi profile 24 requires a fresh provider session when
encountering a profile 23 identity; recovery tests cover that boundary.
- Harness upgrades can change header precedence. The playbook requires
actual request capture when changing provider paths.
- Externally managed agents, unmanaged harness settings, and gateways
that replace headers need separate qualification. This change does not
intercept arbitrary model calls made by task scripts.
- The existing OpenRouter entry for the Paperclip URL still displays an
old title, “PrettyFly Opus Testing,” and no categories on the final
public-page recheck. The live request received credit under that URL's
app ID. Public title propagation and leaderboard placement remain
controlled by OpenRouter.
- Global, EU, and US OpenRouter hosts are recognized explicitly; other
subdomains are not treated as OpenRouter. No database migration,
credential ownership change, or Paperclip telemetry event is involved.
Attribution contains public product constants only.

## Model Used

OpenAI GPT-6 through Codex, with reasoning, repository editing, shell
execution, web research, and live API verification. The exact deployment
identifier and context-window size are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass — the focused suites listed
above; the unsuccessful full local attempt is explicitly recorded, with
full final-head coverage supplied by CI
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 10:28:53 -05:00
DottaandPaperclip 56e09cd19f docs: add native Runner integration playbook (#16846)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Native Runner connects those agents to harnesses through provider
drivers.
> - Adding a harness crosses protocol, setup, lifecycle, packaging, and
product boundaries.
> - Existing guidance does not provide one complete procedure for this
work.
> - This pull request adds a native Runner skill, detailed playbook, and
working templates.
> - Contributors can use them to define a release, implement the
integration, and verify the delivered result.

## Linked Issues or Issue Description

**Issue type**

Missing documentation.

**Where is the issue?**

Native Runner contribution guidance in `doc/DEVELOPING.md` and
`packages/paperclip-runner/README.md`.

**What's wrong?**

Contributors must reconstruct the requirements, protocol mapping, normal
setup, lifecycle rules, packaging, and acceptance process when they add
a harness. The legacy direct-adapter recipe covers a different execution
path.

**Suggested fix**

Add a self-contained native Runner procedure. Include capability
research, a finite release contract, implementation boundaries,
reproducible tests, normal installation, and release evidence. State
each lesson directly so contributors need no private chats, tasks, or
evidence archives. The duplicate search found no existing playbook PR.

## What Changed

- Add `create-runner-adapter` for new native Runner harness
integrations.
- Add a detailed playbook based on the Pi, Cursor, and Copilot
integration lessons.
- Cover model and instruction admission, connection setup, rich events,
durable interactions, recovery, cancellation, packaging, and Product E2E
acceptance.
- Add templates for scope, capabilities, attempts, failures, jobs, and
release handoff.
- Link the procedure from the development guide and Runner README.
- Keep legacy adapters as a compatibility boundary.

## Verification

- `git diff origin/master --check` passed.
- `node scripts/validate-doc-links.mjs` passed from
`packages/paperclip-runner` and checked 53 documentation files.
- All 71 Markdown links in the new reusable files resolve to repository
paths or public provider documentation.
- Skill YAML, naming, description, and scaffold checks passed.
- A private-reference audit passed for the reusable skill, playbook, and
templates.
- The legacy direct-adapter skill matches the base version.
- Full local runtime checks were attempted with pnpm 9.15.4. `pnpm -r
typecheck` stopped because Node type definitions are missing. `pnpm
test:run` and `pnpm build` stopped because `cli/node_modules/tsx` is
missing. This checkout has no installed dependencies. These commands did
not establish runtime test or build results.
- Full remote CI passed on commit
`88b4fc4832d95807da1f5e48029a183b3dc62b6c`: build, typecheck, general
and serialized server tests, Runner checks, browser tests, and the
canary dry run. [CI
run](https://github.com/paperclipai/paperclip/actions/runs/39262297681).
- All 55 applicable checks passed. The two Storybook checks were skipped
for this change.
- Greptile gave the current commit 5/5. There are no review comments or
unresolved threads.

## Risks

Low risk. The procedure can drift as the Runner contracts and test entry
points change. It records its source baseline and tells contributors to
inspect current declarations. Historical lessons describe failure
patterns; they do not certify current binaries.

## Model Used

OpenAI Codex with `gpt-6-astra` and `gpt-6.1-sol`, both using xhigh
reasoning. Context-window sizes were not exposed. The models used
repository search, terminal tools, and file edits.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used, including available version and
capability details
- [x] I have checked ROADMAP.md and confirmed this documentation does
not duplicate planned core work
- [x] I have searched GitHub for duplicate or related PRs
- [x] I have described the issue in this PR using the documentation
issue template fields
- [x] I have not referenced internal or instance-local Paperclip issues
or links
- [x] My branch name describes the change and contains no internal
ticket or instance details
- [x] I have run the relevant local documentation checks; they pass.
Blocked runtime checks are recorded above
- [x] I have considered tests for this documentation-only change and
validated its links and skill metadata
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented the risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before merge

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 08:50:44 -05:00
DottaandPaperclip 98ca6ff7c5 perf: reuse verified provider files during sandbox startup (#16493)
Build provider-pack transport layers once, reuse verified image files in private directories, and upload only missing layers. Preserve archive integrity checks and directory fallback on unsupported hosts.

Verified with 44 focused tests, all 48 main CI jobs, cloud Docker Runner checks, and Greptile 5/5 on the merged head.

Co-Authored-By: Paperclip <noreply@paperclip.ing>
2026-10-19 08:45:09 -05:00
DottaandPaperclip f3cd3f4ea8 fix(runner): require confirmed exit before remote replacement (#16835)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Remote runs need one runner to own their process identity and
listener.
> - A health request can fail while that runner continues to work.
> - The active monitor treated a failed request as a process exit.
> - Recovery could then launch another runner against the occupied
listener.
> - This pull request retries health reads and requires proof of exit
before replacement.
> - A brief outage can recover on the same runner without replaying
agent work.

## Linked Issues or Issue Description

Refs: #16341 adds remote recovery diagnostics. Refs: #16686 retries
verification when restoring a saved remote session. This change applies
the shared probe policy to active process supervision.

**What happened?**

The active remote monitor settled its completion promise after a
timed-out or rejected health request. The transport treated that result
as an exit and started process recovery. An existing runner could still
own the listener. Replacement then failed with
`runner_ingress_bind_conflict` until the reconnect deadline expired.
Missing or changed ownership markers also did not prove that the old
process had exited.

**Expected behavior**

Retry transient read failures on the same runner. Require a matching
ownership marker and proof of process exit before replacement. Preserve
uncertainty when identity or liveness cannot be verified.

**Steps to reproduce**

1. Start a remote runner and leave its listener alive.
2. Make one process-health request time out or reject.
3. Observe completion and the restart decision. Before this change, the
monitor settles while the process is alive, and the restart wrapper
permits another launch.

**Paperclip version or commit**

The defect was reproduced on master at `6e89919631`. The patch is based
on current master at `c6a0cf4bce`.

## What Changed

- Reuse the bounded read-only recovery probe for active supervision.
Retry up to three reads within 30 seconds.
- Check the saved process generation when available. Accept only the
specific process-not-running receipt as exit proof.
- Add an exit-confirmation contract to remote process handles. Require
it for restart and shutdown completion. Preserve the cause of
supervision errors.
- Test transient failures, exhausted retries, conflicting identities,
real listening processes, and an authenticated runner with a fake
provider. Keep confirmed-exit replacement covered.
- Document the recovery policy and coverage limits in the execution
contract and maps.

## Verification

- Red: the timeout and transport-error regressions failed before the
patch because completion settled while the runner was alive. The
restart-guard regression also failed because replacement was allowed.
- Green: 14 server supervision cases passed, including a real listening
process. All 120 shared control-plane tests passed. Focused Runner tests
passed for authenticated live-runner fault injection and confirmed-exit
replacement.
- Review regression: a replacement-health test first failed because its
error cause was lost. It passed after preserving the cause and detail.
The four affected transport cases and Runner typecheck then passed.
- `node scripts/check-maps.mjs` passed for 35 areas and 176 capability
IDs.
- `pnpm -r typecheck` and `pnpm build` passed locally. The sequential
local full-suite run was stopped before completion; no local full-suite
pass is claimed. Final commit `bcc1b1d339` passed the complete CI
matrix: 55 checks passed and two optional Storybook checks were skipped.
Greptile is 5/5 with no unresolved conversations. The PR has no merge
conflicts.
- The first real-listener attempt could not bind inside the execution
sandbox. The same test passed with local socket access. The first
package-test invocation used the root configuration and selected no
tests; the package configuration ran all selected tests.
- CI attempt 1: nine test jobs were cancelled together at 12:54:59 UTC.
Their test steps report cancellation. The build and uninterrupted jobs
passed. The interrupted jobs were retried once. That retry exposed one
confirmed-exit message assertion failure in the Runner shard; the other
jobs passed. The compatibility correction preserves the prior message.
The failing case and four recovery cases then passed locally. The
complete CI matrix passed after that correction.
- No live sandbox restoration, deployment, or historical task recovery
is claimed.

## Risks

- A persistent outage now ends supervision with explicit exit
uncertainty. It cannot authorize a competing process. Existing ownership
and workspace recovery checks remain required.
- Health reads can take up to 30 seconds before reporting an unavailable
runner. Retries are read-only and bounded.
- Local launchers keep their existing completion contract. No database
migration or public API change is required.

## Model Used

OpenAI GPT-6 through Codex, with reasoning, tool use, and code
execution. The exact serving snapshot and context-window size are not
exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 08:19:37 -05:00
DottaandPaperclip 9077748894 Remove the Pipelines experiment and preserve its data (#16834)
## Thinking Path

> - Paperclip manages AI agents and their work.
> - Pipelines was an unused experiment with its own UI, API, CLI, and
automation.
> - Keeping it leaves unsupported product surfaces and extra task-detail
queries.
> - Removing the experiment must preserve data that users already saved.
> - This pull request removes the feature and keeps its database schema
and migration history.
> - Cases and Routines remain available as separate features.

## Linked Issues or Issue Description

**What existing behavior does this improve?**

Remove the unused Pipelines experiment across the application.

**Current behavior**

The experiment includes pipeline boards, stage settings, case
automation, review queues, learnings, permissions, and CLI commands.
Task detail also queries pipeline links.

**Proposed behavior**

Remove all these product surfaces and their implementation. Preserve
existing tables, records, and documents. Ignore the retired boolean in
older managed configurations so upgrades still start.

**Breaking changes**

Pipeline URLs, API endpoints, CLI commands, and `pipelines:write` are
removed. Task detail no longer includes the old `linkedCases` field. The
independent Cases API remains available. No database migration or
cleanup is included.

Related feature work: #7907, #9110, #10905, #11375, #13004, #14671,
#16133. Related issues: #9663, #10310, #10312. This removal supersedes
the feature; it does not implement those pending enhancements or delete
their saved data.

## What Changed

- Remove Pipeline UI pages, navigation, gates, clients, query keys,
helpers, and unused design tokens.
- Remove Pipeline REST routes, services, automation dispatch,
task-detail queries, and OpenAPI discovery.
- Remove the CLI commands, shared contracts, experimental flag, catalog
entry, and permission defaults.
- Remove feature-specific tests, tutorials, smoke scripts, maps, and
Storybook examples.
- Preserve database schema, migration history, and the reserved document
key used by old records.
- Keep Cases routes independent and cover obsolete stored and managed
settings.

## Verification

- Passed: `pnpm build` and `pnpm -r typecheck`.
- Passed: targeted settings, managed configuration, sidebar, settings
UI, routing, and feature-catalog tests. A first sidebar run caught a
shared Workspaces icon import; the import was restored and the sidebar
rerun passed.
- Passed: 40 tests covering Cases routes, OpenAPI discovery, retained
Pipeline table constraints, and schema snapshot drift.
- Passed: token gates, map validation, generated API metadata check,
Storybook catalog validation, and 28 map/catalog tests.
- Passed: isolated local browser verification of navigation and
Experimental settings with Pipelines absent; Cases and Routines still
open normally. Live GET/POST requests to retired Pipeline endpoints
return 404, and the retired setting is absent. CLI help has no Pipeline
commands.
- Passed: 22 access-service and agent-default-grant tests after
restoring unrelated permission assertions flagged in review.
- Local full run: `pnpm test:run` reported one failure in the unchanged
workspace-runtime port-allocation test. That test passed in an isolated
rerun. The long local run was stopped after full CI passed; it is not
reported as a complete local pass.
- Passed: all 56 checks on `def9181f3a4491d95fca1d38e9739f5b821aae3e` (2
conditional checks skipped), including build, typecheck, test shards,
and browser suites. Eleven interrupted CI jobs reported “The operation
was canceled”; their one-time retry passed. [CI
run](https://github.com/paperclipai/paperclip/actions/runs/39255211006).
- Greptile: 5/5 on the final commit, with the only review finding fixed
and resolved.
- Sandbox socket restrictions affected the first build/API test
attempts. The same commands ran with local sockets available.

## Risks

- Existing Pipeline clients must stop using the removed endpoints and
commands.
- Existing data remains in the database and backups, but the removed UI
no longer displays it.
- Historical boolean `enablePipelines` values are ignored. They cannot
restore the feature.
- Cases and Routines must retain their separate behavior. Targeted route
tests cover this boundary.

## Model Used

OpenAI Codex, GPT-6, with repository inspection, editing, shell
execution, and browser verification. The exact deployed model ID and
context-window size are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-19 08:09:46 -05:00
DottaandPaperclip 3858d2341d fix(recovery): default saved-monitor waits and keep task recovery quiet (#16686)
## Thinking Path

> - Paperclip manages AI agents and their work.
> - A task must keep a durable path to its next action.
> - A provider can save a task monitor, then fail to yield because it
omits internal continuation fields.
> - An interrupted provider-pack check can then be reported as permanent
artifact incompatibility.
> - The task asks its user to certify recovered workspace files, even
though this is an operator responsibility.
> - This pull request derives the saved monitor continuation, bounds
verification retries, and removes that task form.
> - Normal recovery stays quiet. Unresolved holds retain inspection and
the existing safety checks.

## Linked Issues or Issue Description

**What happened?**

A yielded completion without `continuation` is rejected even after the
provider saves an eligible monitor on the task. Repeated attempts cannot
finish. Remote verification also treats timeouts and missing exit status
as artifact incompatibility. The task recovery notice exposes raw
diagnostics and asks the task user to certify infrastructure files.

**Expected behavior**

Use current persisted task state to fill routine continuation fields.
Retry interrupted verification reads within a fixed bound. Keep normal
recovery in the working state. Show a compact notice only when work
cannot safely continue.

**Steps to reproduce**

1. Save an eligible monitor on the active task.
2. Call `paperclip_finish` with `reportedWorkDisposition: "yielded"` and
omit `continuation`.
3. Return a timed-out remote provider-pack command with empty stderr
during recovery. Inspect the resulting task notice.

**Paperclip version or commit**

Source baseline: `aaeff418cf` (master integrated with its current task
visibility and saved-source reconstruction rules).

Related changes: #15824, #16104, #16451, #16493, #16690. This fix
complements saved-result recovery and verified pack reuse. It does not
replace their workspace ownership checks.

## What Changed

- Allow omitted or null continuation at the provider input boundary.
Read current authorized task context and fill a monitor continuation
only for the bound run and an eligible saved monitor. Keep accepted
results strict. Apply this to Codex, OpenCode, both direct and
production-sidecar ACPX paths, and external drivers. Reserve the
semantic call identity during the saved-context read and reject
cancellation or a changed run/turn.
- Bind the shared completion change and continuation helper in a new
Copilot v21 source declaration. Preserve v20 history and its decoder
support. Qualification stays pending.
- Expose the eligible continuation in task context. Completion admission
still checks persisted monitor state. No schedule is created or renewed
by the default.
- Retry read-only provider verification at most twice per command. Hold
exhausted reads with a distinct verification-unavailable cause.
Reattachment cannot renew the read budget through an unchanged
provider-attempt counter. Keep completed verification failures and wrong
versions incompatible.
- Remove the task file-certification form. Hide the notice only for a
matching durable recovery path without an unknown-action replay hold.
Keep missed retries, unsafe outcomes, and unresolved file holds visible.
- Add production-component stories for automatic recovery, blocked and
expired holds, reader access, persisted repair decisions, source
reconstruction, queued continuation, and mobile. Preserve master’s
guarded saved-source reconstruction choice after confirmed source
destruction. Update the execution contract and access maps.

## Verification

- Completion, helper, Codex, OpenCode, ACPX, and profile regressions
pass. After the sidecar review fix, 271 tests across the production
sidecar and three provider suites pass, plus 72 helper/profile tests.
The real sidecar MCP bridge tests cover saved-monitor acceptance,
no-monitor refusal, cancellation, duplicate call identity, and
raw-versus-forwarded semantic receipt hashes. The OpenCode tests also
cover eligible-monitor acceptance and refusal without one.
- The fresh full native executor suite passes all 743 tests. Four
profile, installation-integrity, and ACPX driver suites pass all 168
tests. The earlier CI fingerprint failure required a new immutable
source declaration; its follow-up Docker failure required the matching
context allowlist entry. Both fixes are verified locally. Targeted
server monitor, tool authority, and provider verification suites pass.
The probe tests include a real timed-out subprocess, an unrelated
responsive timer, transport errors, and completed integrity rejections.
- All 90 tests in the merged task notice, reconstruction choice,
recovery display, and lineage suites pass. They cover reader access,
live/missed/mismatched recovery, unknown outcomes, saved messages, retry
refusal, and removal of the file form. Both review findings have
failing-baseline/passing-treatment regressions: identical polling across
retry expiry, and a failed refresh after cached running activity.
- Browser walkthrough passed for automatic recovery, unresolved details,
a 390px mobile story, and the merged saved-source reconstruction and
queued states. The reconstruction control starts disabled and normal
automatic recovery shows only Working. The stories use production
components and fixture API data. They do not prove live cloud recovery.
- Token gates, map checks, and Storybook catalog generation pass. The
exact Docker context integrity command passes locally after adding the
new build declaration to its allowlist.
- Workspace typecheck and build pass on the final source, including the
versioned identity update. The final server and UI guards pass their
focused tests, typechecks, builds, and token gates. The final standalone
Storybook builds. The saved-monitor default retains master’s stricter
child-task visibility filter. Re-review caught an additional
production-sidecar validator before forwarding; the fix now defaults at
that boundary and has passing regression controls. After preserving
master’s new reconstruction capability, 68 targeted reconstruction,
tool-authority, and provider-verification server tests pass. The
current-master integration at `2a80050a0d` has a fresh 5/5 review with
zero unresolved threads. Its complete CI matrix, including Runner tests,
is the merge acceptance record.
- On the final master integration, local typecheck, build, and all 90
recovery UI tests pass. A concurrent runner run hit five 5-second
sidecar startup timeouts; an isolated sidecar run passed 86 tests and
timed out in the unrelated unsupported-bootstrap case. Those local
deadline failures remain recorded; the canonical CI Runner lanes use
their normal deadlines and pass. The unsharded local full-suite attempt
did not complete. It spanned source edits; the fresh native executor run
above passes. An unrelated workspace fixture timed out once and then
failed to reserve 32 contiguous ports on this host. Its unchanged-base
control and CI server suite pass. Full-suite acceptance uses the fresh
latest-head CI matrix; this PR does not claim a passing unsharded local
run.

## Risks

The default applies only to an eligible persisted monitor. An explicit
invalid continuation still fails validation. The added read occurs only
when a yielded report omits its continuation. Admission rechecks current
state after that read.

An interrupted verification command can add one extra 30-second probe.
Completed rejections stay closed. These probes do not change the pack,
launch provider work, or replay external tools. Two inconclusive reads
hold the original run. They do not schedule another reattachment with an
unchanged provider-attempt counter.

This PR’s pending Copilot v21 declaration binds the changed shared
contract, resolver, direct driver, and production sidecar sources. The
previous v20 declaration is immutable and remains decodable, but launch
requires the new exact identity. Qualification remains pending.

Task users lose the file-certification form. Board-authorized
source-only repair remains available through the resolution API with the
original evidence and stop-receipt requirements. This branch does not
deploy or recover historical held runs.

> This is a bug fix and UI polish within existing recovery behavior.
ROADMAP.md was checked.

## Model Used

OpenAI Codex, `gpt-6.1-sol`, xhigh reasoning, with tool use and code
execution. The host does not expose the context-window limit.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass (changed-area suites; the
full local run limitation is recorded above)
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-18 21:43:15 -05:00
DottaandPaperclip 023f4a5d0c fix: preserve repository cache negotiation refs (#16687)
## Thinking Path

> - Paperclip manages agent work and its execution environments.
> - A fresh repository task needs an independent checkout before its
runner can start.
> - The object cache from #16487 should reduce repeated network
transfer.
> - The cache kept Git objects but dropped remote-tracking refs during
its bare clone.
> - Git needs those tips to negotiate which objects it already has.
> - This pull request preserves the tips in a versioned mirror cache and
records explicit cache outcomes.
> - The benefit is less repeated transfer and clearer evidence when a
cache does not help.

## Linked Issues or Issue Description

Refs #16487 and #16454. No duplicate cache-negotiation fix was found in
the public PR search.

**What happened?**

A valid object cache could make a fresh clone slower. A controlled
staging probe took 45.87 seconds and received 184.39 MB even though the
reference already held the objects. An earlier probe took 52.33 seconds.
An uncached clone took 20.94 seconds.

`git clone --bare` copied the pristine checkout's objects, local
branches, and tags, but omitted its remote-tracking refs. The source had
about 1,200 remote branches. Git could not use the missing tips to
negotiate those objects.

**Expected behavior**

Keep the pristine reference's negotiation tips. Each task must still
authenticate online, use the current remote refs, and end with
independent Git objects.

**Steps to reproduce**

1. Clone a repository with many remote branches into a fresh checkout.
2. Publish a reference with `git clone --bare --no-hardlinks` from that
checkout.
3. Clone the remote with `--reference-if-able` and `--dissociate`.
4. Compare with a reference that retains the remote-tracking tips. Use
Git Trace2 and count received pack bytes.

**Paperclip version or commit**

The staging runtime was `27ab902d3db2770ada79c9f42a9c06e1d346f34b`, with
Git 2.47.3. The cache implementation was unchanged from #16487.

**Deployment mode**

Docker on a persistent application volume. The probe used the
application file owner and the public Paperclip repository. It did not
start agent tasks or alter the application cache.

## What Changed

- Publish pristine object caches with `--mirror` to retain
remote-tracking tips.
- Put cache format version 2 in the key and receipt. The first checkout
builds a new generation. Existing generations stay under the current
storage limits.
- Keep the existing online authentication, current remote refs,
credential and company isolation, independent objects, quotas, and
fallback behavior.
- Add closed Honeycomb cache outcomes and a boolean that states whether
a reference was supplied to clone.
- Document that a lookup hit or supplied reference does not prove Git
avoided transfer.

## Verification

- Controlled staging component experiment: a disposable reference copy
held exactly the same 210,057 objects as the original. It added 1,187
advertised branch tips whose commits were already in those objects.
- Before: 45.87 seconds and 184.39 MB received, one sample in this
comparison.
- After: 12.20 and 14.58 seconds; median 13.39 seconds. Received pack
sizes were 1.99 and 1.95 MB.
- All comparison clones used the same current remote HEAD and ended
without an alternates file.
- The remaining repack took 9.72–9.81 seconds. Checkout file writing
took 0.86–0.96 seconds.
- The staging experiment restored tips on a disposable cache copy. It
did not deploy this patch or measure complete agent latency.
- Confirmed both staging scratch locations were empty afterward. The
original cache timestamps stayed unchanged. The temporary operator SSH
key was revoked and its local files removed.
- TypeScript 5.9.3 transpilation reported zero syntax diagnostics across
the four changed TypeScript files. `git diff --check` passed.
- The new negotiation regression fails with the old `--bare` publisher
and passes with the mirror publisher.
- Focused Vitest suites: 26 tests passed across repository-object-cache
and execution-preparation-timing. These cover independent objects,
current refs, unavailable/revoked remotes, scope separation, invalid
storage, tracing isolation, and endpoint-off behavior.
- The first full focused run passed 24 tests but failed its existing
localhost HTTP fixture because the sandbox denied `listen` on
`127.0.0.1`. The rerun with local loopback permission passed all 26
tests.
- Server semantic typechecking passed with `tsc -p server/tsconfig.json
--noEmit` after building the required workspace declarations. Initial
attempts lacked generated dependency outputs; the completed dependency
build and rerun passed.
- A full application build was not run locally. CI passed: 55 checks
passed and two optional checks were skipped. Greptile is 5/5 on the
current head, with both findings resolved.

## Risks

- Version 2 causes one cold cache rebuild. Old cache generations retain
their disk usage, and the existing quota can prevent publication.
- A cache still needs a full repack to produce an independent task
checkout. This PR does not remove that cost.
- The component experiment establishes the negotiation effect on
staging. It does not establish an end-to-end agent speedup or the
under-30-second goal.
- The new trace fields remain behind the existing OTLP gate. Their
values are closed enums or a boolean. They export no refs, paths, URLs,
cache keys, credentials, or error text.

## Model Used

OpenAI Codex, GPT-6 family, with code and tool use. The exact serving
model ID and context window are not exposed in this session.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-18 21:28:20 -05:00
aaeff418cf fix(acpx): add a positive control to stalled-tool permission evidence (#16769)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - The ACPX engine runs Claude agents. A watchdog ends a turn when a
pending tool call gets no update for 30 minutes.
> - #16688 added a field to stalled runs. The field records if the
stalled call's permission request reached Paperclip.
> - Recent stalled runs show `acpStalledToolPermissionRequested: false`.
We can read this as "the call stopped before its permission request".
That reading is correct only if calls of the same kind usually send a
request.
> - We have no data that shows if finished calls of that kind sent
requests. Thus we cannot tell if the missing request is a real signal.
> - This pull request records a positive control: the number of finished
calls of the stalled call's kind, and how many of them sent a permission
request.
> - The benefit: the next stall event tells us if the missing request
locates the stall, or if it gives no information.

## Linked Issues or Issue Description

Refs #16688

**What happened?**
Runs stop with the stalled-tool watchdog error. The diagnostics show
that the stalled call sent no permission request. The diagnostics do not
show if finished calls of the same kind sent requests.

**Expected behavior**
The stalled-run diagnostics contain enough data to show if a missing
permission request is a real signal.

**Steps to reproduce**
A pending tool call gets no ACP update for 30 minutes. The watchdog ends
the turn. The run result contains the stalled-tool fields.

## What Changed

- `packages/adapter-utils/src/acpx-engine/execute.ts`: when the watchdog
fires, count the finished calls of the stalled call's kind, and count
how many of them sent a permission request. Write the counts to the run
result as `acpSettledSameKindToolCount` and
`acpSettledSameKindToolPermissionRequestedCount`.
- `server/src/services/run-failure-diagnostics.ts`: allow the two new
fields as non-negative safe integers. Other values are dropped.
- `doc/observability.md`: explain how to read the two fields with the
existing permission-request field.
- Tests: extend the existing stalled-tool tests in `execute.test.ts` and
`run-failure-diagnostics.test.ts`.

## Verification

- `pnpm exec vitest run src/acpx-engine/execute.test.ts` in
`packages/adapter-utils`: 244/244 pass.
- `pnpm exec vitest run
src/services/__tests__/run-failure-diagnostics.test.ts` in `server`:
115/115 pass.
- Mutation check: remove the kind filter, or count every finished call
as "requested". Each mutation makes the stalled-tool test fail.
- `tsc --noEmit` passes in `packages/adapter-utils` and in `server`.
Note: the full `server` `typecheck` script did not run locally, because
the runner vendor build step failed in this sandbox. I ran `tsc
--noEmit` directly.

## Risks

- Low risk. The change only adds two counts to the run result after the
watchdog fires. It does not change the decision to stop the turn, or any
permission decision.
- The fields hold only counts. They contain no tool titles, inputs, or
identifiers. This is the run-log and run-result path. It is not
Telemetry. The fields reach Sentry through the existing allowlist in
`run-failure-diagnostics.ts`.

## Model Used

- Claude Opus 5.5 (`claude-opus-5-5`), Anthropic, used through Claude
Code with tool use (shell, file edits, test runs).

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [ ] All Paperclip CI gates are green
- [ ] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

🤖 Generated with [Claude Code](https://claude.com/claude-code)

---------

Co-authored-by: devinfoley <139239+devinfoley@users.noreply.github.com>
Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-18 13:59:16 -07:00
Devin FoleyandPaperclip 10d92eb468 fix(daytona): clear idle guard after verified sandbox cleanup (#16760)
Replace the lifetime provider-use guard with scoped allocation and pending-request evidence. Fence cleanup observations against overlapping work, retain timed-out raw requests, and wait for completed remote deletion before permitting idle sleep.

Verified with 436 Daytona tests, package and workspace typecheck/build, full CI, and Greptile Apex 5/5 on the reviewed head. Four deletion-boundary regressions and two concurrency regressions fail on the earlier implementation and pass with the fixes. Live-provider and local full-suite limits are documented in the PR.

Co-Authored-By: Paperclip <noreply@paperclip.ing>
2026-10-18 13:56:20 -07:00
DottaandPaperclip bfadb66556 fix(daytona): retain already archived workspaces on stop (#16710)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Stop-only recovery must keep unfinished remote workspace files safe.
> - Daytona can archive a stopped sandbox while those files remain in
object storage.
> - The stop handler sent another Stop request for that archived source.
> - Daytona rejected that request, so recovery could not record its
required receipt.
> - This change accepts the freshly confirmed archived state after
retention is verified.
> - Recovery can proceed while the source stays cold and its files
remain available.

## Linked Issues or Issue Description

Refs: #16583, #16700.

**What happened?**

Stop-only cleanup rejected a retained workspace after Daytona archived
it. The live provider returned `DaytonaValidationError` for Stop while
its state was `archived` and auto-delete was already disabled. The host
correctly kept the recovery gate closed.

**Expected behavior**

Confirm the exact source and its retention policy. Treat an archived
source as having no running process. Record the stop-only receipt
without starting or deleting the source.

**Steps to reproduce**

1. Keep an unfinished native workspace with stop-and-retain intent.
2. Let its stopped Daytona sandbox become archived.
3. Request stop-only cleanup.
4. Observe the rejected Stop request and missing receipt.

## What Changed

- Accept `archived` after a fresh provider read confirms that
auto-delete is disabled.
- Stop the source if that fresh read instead shows it has resumed.
- Add regression cases for confirmed retention, unconfirmed retention,
and a resumed cached handle.
- Update the recovery runbook and capability map.

## Verification

- The new baseline fixture failed on the old handler: 1 failed, 2
passed.
- Daytona provider suites: 417 passed, 6 skipped.
- Full workspace `pnpm -r typecheck`: passed.
- Full workspace `pnpm build`: passed on `fc8b1c1bb8`.
- Maps and Git whitespace checks: passed.
- The live provider rejection was reproduced on the exact retained
source. No model turn, file change or delete was performed. The fixed
source handler was then run against that same archived allocation with
the declared SDK version. It returned the stopped-process receipt while
the provider stayed archived with auto-delete disabled. No process was
started. All 58 exact-head CI checks passed; independent review is 5/5.
A full local run is also in progress on a separate frozen checkout of
this revision; it is not reported as complete.
- [Daytona lifecycle
documentation](https://www.daytona.io/docs/en/sandboxes/) confirms that
archive follows Stop and preserves the filesystem in object storage.

## Risks

- An archived source grants a generic stopped-process receipt. Its
physical provider state stays archived.
- Retention confirmation remains required. A stale archived handle that
has resumed still requires Stop.
- The host still checks the original allocation, ownership, stop receipt
and file-recovery evidence before continuation.

## Model Used

OpenAI Codex, GPT-6 family, with reasoning, tool use and code execution.
The session does not expose an exact backend model ID or context-window
size.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-18 02:50:49 -05:00
DottaandPaperclip 6bec153410 fix(runtime): retain cancelled workspaces before reconstruction (#16700)
## Thinking Path

> - Paperclip is the open source app people use to manage AI agents for
work.
> - Native runs must preserve files when Stop ends a turn before its
result is saved.
> - The cancellation path could skip file retention and leave a prepared
remote workspace active.
> - An older controller could also admit an extra run while an earlier
lost-source hold was unresolved.
> - Rejecting every later run then prevented recovery even after that
extra run was stopped and its files were reconciled.
> - This change retains cancelled workspaces and records the exact proof
for a safely reconciled intervening cancellation.
> - Recovery can proceed without changing cancelled history, replaying
actions, or weakening execution gates.

## Linked Issues or Issue Description

Refs: #16583, #16690, #16696.

**What happened?**

Stop could acknowledge a native turn without recording its unsaved file
obligation. Reconstruction also rejected a later cancelled run after its
exact environment and files had been reconciled. The task could remain
inactive with an `in_progress` status, which the reconstruction endpoint
rejected.

**Expected behavior**

Retain unsaved files after Stop. Permit a board operator to reconstruct
from saved sources only after each intervening cancellation has a
confirmed stop and a file-only repair record. Preserve the original
failed export and the cancelled run.

**Steps to reproduce**

1. Prepare a native workspace and cancel the turn before a structured
result exists.
2. Inspect its file retention and remote lease state.
3. For a task with an older destroyed export, reconcile the later
cancelled run's exact files and unperformed actions.
4. Request reconstruction from verified same-task attachments.

## What Changed

- Pin prepared native files before cancellation settlement. Defer
teardown if pinning fails. Use the existing stop-only cleanup worker.
- Repair active warm and ephemeral sources, plus stopping and
confirmed-stopped historical cancellations in bounded startup and
periodic batches. Preserve the existing exact-source checks. Bound
row-lock waits and advance past a busy source.
- Accept only same-owner native run-only cancellations with no result or
current coordinator, confirmed stopped leases, and board file-only
repair with `not_performed` action outcomes.
- Save hashes of each intervening repair and recheck them at queue claim
and final dispatch. Reject changed evidence or another later run.
- Expose saved-source reconstruction in the issue API for inactive
`blocked` and `in_progress` tasks, and hide it when an execution or
checkout owner exists. Permit the same inactive source at submission.
Keep the source, owner, version, attachment, budget, pause and retry
checks.
- Update the shared evidence type, recovery runbook and capability maps.
Add an optional cancelled-native no-action confirmation to file
recovery, resetting evidence when its source changes. No migration, new
endpoint, permission or dependency.

## Verification

- The new fixture fails on the original validator with
`workspace_reconstruction_stale` after valid cancelled-run file repair.
- Focused source and Stop retention tests: 94 passed before the final
contention case. The subsequent three-suite run passed 123 tests,
including real PostgreSQL lock contention and public
startup/API/final-dispatch paths. The final narrow-query rerun passed
all 123 tests. Review correction: all 143 tests passed across four
suites, including real lock contention through the teardown boundary and
stopping/stopped allocations.
- Six broader cancellation, executor, heartbeat and restart suites: 831
passed, 9 existing skips.
- Final correction: all 145 backend tests and all 36 recovery UI tests
passed. Real contention covers both warm reusable and ephemeral sources.
Optional no-action confirmation defaults to uncertified, and changing
source clears evidence. Workspace `pnpm -r typecheck` and token gates
passed on these sources.
- Maps, module boundaries and Git whitespace checks: passed. Full `pnpm
build` passed on the final `4e8c0e73ac` revision as well as the prior
reviewed heads. A full local run of the preceding fix completed with
21,724 passes, 109 skips and three failures in webhook body limits, a
status-card timeout, and a port-allocation fixture. All three suites
then passed unchanged in an isolated rerun (209 tests). The full local
run remains recorded as failed; the final head's full CI passed (55
completed checks, no failures). A fresh full local run is also in
progress on the frozen reviewed head.
- Preserved failures: the first attempt lacked a built plugin SDK; after
building prerequisites, the regression reached the expected validator
rejection. Treatment tests caught the file-only action's deliberately
null continuation owner. A real lock test then caught the database
driver's wrapped timeout error. Both defects were corrected and
retested. Independent review then found a teardown race after a failed
retention write. A second review found active warm sources excluded by
the historical policy filter; the regression reproduced both warm
failures before correcting the query. Its real-row-lock fixture
reproduced the failure; the fixed release guard and historical
stopping/stopped cases pass. No checks were weakened.
- A pre-deployment walkthrough caught the issue API still hiding
reconstruction for an inactive `in_progress` task. The status/capability
baseline reproduced three failures, including inappropriate capability
flags for execution/checkout owners. The fix uses the same
inactive-state requirements as submission; its positive fixture reads
the assembled issue API before reconstructing. All 117 tests in those
three recovery suites pass, and all 28 heartbeat-recovery tests pass
separately. Full workspace typecheck passed again. Full build passed
with the exact `4e8c0e73ac` stamp; latest-head independent review is 5/5
with no open findings. All 55 latest-head checks completed with no
failures.
- Live tenant acceptance remains pending. No successful reconstruction,
export or warm-process proof is claimed by these local tests.

## Risks

- Stop retains unfinished work, so storage remains until file recovery
and explicit cleanup complete.
- Reconstruction remains held for unknown or performed external actions,
foreign owners, live or rebound environments, accepted results, changed
evidence, and unrelated later runs.
- The sweep examines at most five candidates per pass. It uses a fair
cursor and bounded transaction waits. It performs no provider call and
starts no new turn.
- Intervening verification reads only the needed JSON fields. The source
transaction still serializes recovery for the same task.

## Model Used

OpenAI Codex, GPT-6 family, with reasoning, tool use and code execution.
The session does not expose an exact backend model ID or context-window
size.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have searched GitHub for duplicate or related PRs and linked
them above
- [x] I have either (a) linked existing issues with `Fixes: #` / `Closes
#` / `Refs #` OR (b) described the issue in-PR following the relevant
issue template
- [x] I have not referenced internal/instance-local Paperclip issues or
links (only public GitHub `#NNN` / `github.com/paperclipai/paperclip`
URLs)
- [x] My branch name describes the change (e.g. `docs/...`, `fix/...`)
and contains no internal Paperclip ticket id or instance-derived details
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] All Paperclip CI gates are green
- [x] Greptile is 5/5 with no open P2s, recommendations, or follow-ups
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Paperclip <noreply@paperclip.ing>
2026-10-18 01:33:11 -05:00