mirror of
https://github.com/paperclipai/paperclip.git
synced 2026-11-09 16:02:36 +01:00
## Thinking Path > - Paperclip is the open source app people use to manage AI agents for work. > - Durable workspace migration must preserve archived files and saved recovery data. > - An archived Git workspace can contain ignored recovery receipts and bundles in its encrypted restore point. > - The importer reconstructs a private repository from a verified source before it applies that restore point. > - Reconstruction omitted the source repository's local ignore rules. The restored files then changed classification, and the exact restore-point check failed. > - This pull request copies the verified local ignore rules into the private repository before restoration. > - The source stays unchanged, and the original restore-point integrity checks still apply. ## Linked Issues or Issue Description **What happened?** An archived workspace with saved files under an ignored recovery directory failed migration with `restored_contents_mismatch`. The task commit and staged index matched. The ignored files were restored, but the private repository treated them as untracked work because its `info/exclude` rules were missing. **Expected behavior** Reconstruction from an existing verified source must preserve its local ignore policy. Saved ignored files must survive migration and a cold object-store restore with their original classification. Import must not follow a symlink to an unrelated ignore file or edit the source repository. **Steps to reproduce** 1. Exclude a recovery directory in the managed source repository's `info/exclude` file. 2. Save staged edits, unstaged edits, an ignored recovery receipt, and an ignored binary bundle in an encrypted restore point. 3. Archive and remove the task worktree. 4. Import the archived workspace. Before this change, restore-point validation fails because the reconstructed repository lacks the local exclusion rule. **Paperclip version or commit** Reproduced on master at `879140cbbd`. **Deployment mode** Cloud workspace migration with a retained verified Git source, PostgreSQL, and encrypted durable object storage. The tests use real disposable PostgreSQL, Git repositories, and encrypted filesystem-backed object storage. Related migration work: #18826, #19138, and #19396. No duplicate open fix was found. ## What Changed - Copy the verified source's `info/exclude` file into the private reconstructed repository before applying its restore point. - Bound the read to one MiB. Reject symlinked, non-regular, hard-linked, or changing source files. - Keep the original source bytes unchanged. - Add regressions that check staged and unstaged edits, ignored recovery files, cold restore, and rejection of a symlinked ignore file. - Document the reconstruction behavior. ## Verification - Before the repair, the saved-ignored-files regression fails with `restored_contents_mismatch`. - After the repair, both focused cases pass. - At rebased head `81a0b1c041`, all 206 tests across migration, snapshot storage, archive, and migration concurrency suites pass. The merged interrupted-upload and nested-source approval regressions remain intact. - Server package typecheck passes. - Full repository typecheck and build pass at the rebased head. The full local test suite is running. The prior local full-test run was interrupted for rebase, and is not a passing result. - Initial CI hit a 15-second timeout in unchanged `activity-routes.test.ts`; the exact case passed in a focused local run. The browser shard lost its self-hosted runner, as confirmed by its check annotation; GitHub did not retain its full log. Those failures remain recorded. An unchanged retry was superseded by the required conflict rebase. At exact head `81a0b1c041`, all 53 CI checks and both required aggregate gates pass; Greptile is 5/5. The full local suite remains in progress, so no local full-suite PASS is claimed. A second automated review noted the existing nested-checkout counterpart. This PR fixes root reconstruction. The nested linked-checkout repair and its saved-ignored-files/cold-restore regression are implemented in #19409, which is required before the migration rollout uses nested imports. This PR leaves that sibling recovery path unchanged. The two identical scope warnings are addressed through that linked repair. ## Risks The copy applies only when an archived Git restore-point source is still present and verified. It changes only the private reconstruction directory. Missing sources retain the existing restoration path. Unsafe or unstable local ignore files block import and retain the original migration obligation. No database migration or saved format changes are included. ## Model Used OpenAI GPT-6 in Codex, with code editing, tool use, and test execution. 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 - [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>