Files
PaperClipAI/maps/feature-map
DottaandPaperclip 24067a16b5 fix(workspaces): classify restricted shared repository admission (#16895)
## Thinking Path

> - Paperclip manages agents, their tasks, and their saved work.
> - Workspace preparation must check access before an agent starts.
> - A shared project checkout can contain another task's private
worktree.
> - The access guard correctly rejects a run that cannot read that work.
> - The isolated-source path reports this as a configuration blocker
after #16545.
> - Shared project repository admission missed that classification and
returned a generic setup failure.
> - This change uses the same blocker at that boundary so recovery names
the required workspace repair.

## Linked Issues or Issue Description

Refs #16545 and #16095. The open retained-reader repair in #16832
addresses deleted identities, a separate condition.

**What happened?**

A task reused a shared project workspace. Another worktree in that
checkout retained a private task that the run could not read. Repository
admission rejected access before provider startup. The run reported
`setup_failed`, and recovery showed a generic no-live-execution notice.

**Expected behavior**

Keep the access denial. Report `configuration_incomplete` with reason
`workspace_source_restricted`. Preserve the workspace and files. Give
the owner the existing workspace repair action. Do not queue an
automatic failure retry or report this expected blocker as an unexpected
Sentry failure.

**Steps to reproduce**

1. Bind a task to a shared project checkout.
2. Add a private task worktree beneath that checkout.
3. Continue the shared task as an agent that cannot read the private
task.
4. Inspect the run result and recovery action.

**Version and deployment**

Reproduced in the full heartbeat service from source revision
`06d4fe3121`, with PostgreSQL and real Git worktrees on macOS. The
provider never starts. The regression also covers the existing
Git-worktree path.

## What Changed

- Apply the existing restricted-source classifier to task repository
admission.
- Extend the heartbeat regression to shared project workspaces.
- Assert one run and one recovery action, no provider start, no
unexpected Sentry report, and preserved binding and files.
- Update the workspace documentation and both capability maps.

## Verification

- Red: the shared project regression returned `setup_failed`; the
Git-worktree control passed.
- Green: the same two cases pass after the change.
- `node scripts/check-maps.mjs` and `git diff --check` passed.
- Current head `e26cdd45da76c6edaa1622856f9c69e9f48b81fb`: 55 successful
checks, one neutral check, two skipped Storybook checks. Greptile 5/5,
no review threads, mergeable.
- All 337 tests passed across `heartbeat-workspace-branch-containment`,
`heartbeat/workspace-preparation`, `run-failure-report`, and
`recovery/stranded-notice`.
- `pnpm -r typecheck` and `pnpm build` passed. All full current-head CI
suites passed in [run
39315969013](https://github.com/paperclipai/paperclip/actions/runs/39315969013).
The duplicate local full Vitest run was stopped after 11 minutes when CI
completed; it has no local full-suite completion claim. The 337 affected
local tests completed successfully.
- Running-app acceptance at `e26cdd45da76c6edaa1622856f9c69e9f48b81fb`:
a synthetic private Git worktree caused the shared task to stop with the
visible Workspace source restricted notice and no process start. The
normal workspace API selected a separate task directory. Resolving the
recovery action resumed the same assignee. A real process fixture
completed, the output persisted after reload, and both source files
remained intact. Checkout and execution locks cleared. There were no
automatic failure retries.
- The first recovered process wrote its report to the command cwd. This
was a fixture output-path mistake. The corrected fixture reads the
selected workspace from the authenticated API before writing. One
explicit additional admission verified that output. The record retains
both successful process runs and the earlier configuration-blocked run.
This is local process-adapter acceptance, not live Codex/provider
qualification.
- Staging diagnosis confirmed a retained private source and failure
before provider startup. The original task has not been recovered. The
deployed UI hides its workspace selector, and no authenticated
task-write API is available in this session. No live Codex recovery is
claimed.

## Risks

The same exact 403 denial is now a configuration blocker during shared
repository admission. Other failures retain their original type. Access
policy, cloning, credentials, provider execution, and workspace contents
do not change. An existing task still requires a permitted workspace
repair before it can run.

## Model Used

OpenAI GPT-6 through Codex, with reasoning, code execution, and browser
tools. 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
- [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:03:16 -05:00
..

Paperclip feature map

Start here when reproducing a user-facing bug, verifying a change, or deciding which surfaces a fix must cover. Each recipe describes what a person can do, where they can do it, the expected result, and the evidence needed to verify it. Product behavior is still governed by the implementation spec.

The sibling agent access map records APIs, agent entry points and permission boundaries for the same capability IDs. Follow the shared map contract when maintaining either map.

Browse features

Open the published Storybook guide for the assembled feature and capability index. The Markdown recipes in this directory are the authored source. Each has a same-named agent-access companion.

Run node scripts/storybook-catalog.mjs to generate local navigation in maps/generated/feature-map.md, maps/generated/agent-access-map.md, and the Storybook guide. A new recipe is discovered automatically; do not register it in this README or maintain counts here.

Before driving a journey

  1. Use this checkout's isolated test drive for manual product checks. It creates a temporary instance and prints its URL and data directory. Do not guess that a server on port 3100 belongs to you.
  2. Record the commit, URL, company, login role, relevant experimental settings, adapter, runtime mode, and live versus simulated dependencies. Use disposable tasks and provider resources. A fresh test drive creates a company and CEO, but no task or first run.
  3. Use the current navigation and company prefix. Paths in recipes omit that prefix. Record whether the streamlined or production shell is selected; Agent Chat, chat connectors, and the combined Inbox/Tasks view have separate gates. A hidden surface is an unmet prerequisite, not a successful test.
  4. Run the smallest relevant test first. Vitest commands below run from the repository root after installing dependencies. Playwright recipes use their named configuration and its isolated environment, not an unrelated running instance. Reserve expensive runner/provider tests for the behavior at issue.
  5. Exercise the actual user action, inspect its result, reload, and verify the persisted state or continuation. Use read-only API checks to corroborate UI evidence; creating state through the API does not prove the creation UI.

For agent-driven acceptance work, start with the Paperclip verification skill for an isolated launch, ownership/readiness checks, browser driving, evidence, and cleanup. It uses this directory as its feature map. The existing dev-workspace run/verify skill and evaluation skill describe runtime ownership and evidence handling. Reuse them; this map introduces no environment launcher, credentials, scheduled job, or second test framework.

Evidence contract

Report each entry point as passed, failed, blocked (with its missing prerequisite), or not run. Include the feature filename and entry-point ID, commit/environment, user action, expected and observed result, command/exit code, and evidence links. Screenshots or traces should show both the action and the discriminating result. Include task/run/request IDs when relevant, without secrets.

A fix is verified across its affected surfaces only when each has evidence or an explicit reason it does not apply. Shared code alone does not prove parity. Keep product regressions visible; do not change the recipe to bless a failure. For Paperclip-assigned work, attach evidence through the artifact workflow.

Inventory and remaining depth

The generated maps/generated/coverage.json lists the current non-test TSX page modules and the recipes that directly reference each one. An unreferenced module is a documentation candidate, not proof that its feature is absent or untested. Remaining workflow limits live in each recipe. Inventory and example associations describe documentation scope, not runtime health.

Maintaining the reference

The map documents user journeys. It does not execute them automatically; generated inventories record documentation scope rather than live test health.

When maintaining a recipe, compare its entry points and expected results with the current source. Check that linked tests still exercise the stated behavior and that local references still exist. Keep the same-named agent access companion and stable sub-feature IDs aligned when behavior or access changes. Source-only access inventory remains distinct from live verification. Run node scripts/check-maps.mjs after map edits for structural/reference checks; follow the shared contract for the source and behavioral checks it cannot perform.

Each recipe starts with a small frontmatter navigation record, then an H1:

---
navigation: {"section":"Tasks and conversations","sectionOrder":20,"order":10}
---

The H1 supplies the feature title, and the first paragraph supplies its summary. Orders are local to the section; leave gaps for additions. Equal orders use the stable filename as a tie-breaker. Keep a section's name/order consistent across its recipes. A new feature or capability needs only its recipe and companion.

Optional ### Storybook verification guidance lives inside the recipe's Gotchas section. Each level-four heading contains a backtick-quoted capability key and has Scope (ui, cli, or browser), Storybook, Production, and Sources fields. These are verification instructions and intentional scope limits, not run results or a required story for every API. The generated gap report combines this guidance with current story associations.

After frontmatter, each recipe starts with an H1 and a user-visible description, then exactly:

  1. Sub-features — stable backticked IDs and observable behavior/states.
  2. How to get to it (user POV) — one H3 backticked entry-point ID per surface.
  3. Driving it with — starts with Preconditions:; repeat each entry-point H3, with Automated: and Manual: paragraphs. Name test scope and gaps honestly.
  4. Gotchas — misleading look-alikes, feature gates, and invalid evidence.

New or updated entries follow Poteto's feature-map examples. Existing entries with a Driving it heading can adopt the named harness when their recipes are updated. The original format was inspired by Omnigent's feature map. Paperclip's recipes and checks follow its own task model and test infrastructure.