fix(harness): migrate legacy cursor install-state into profile sync - #469
Closed
solomonneas wants to merge 1 commit into
Closed
fix(harness): migrate legacy cursor install-state into profile sync#469solomonneas wants to merge 1 commit into
solomonneas wants to merge 1 commit into
Conversation
`brigade harness install cursor` (legacy, v1) and `brigade harness sync --target cursor` (profile layer, schema v2) share ~/.cursor/brigade/install-state.json with incompatible schemas, and each refused the other's state with no recovery path. The profile layer now detects a legacy version-1 state and deliberately adopts its attestations into the v2 ownership model before syncing, so a later uninstall still removes exactly what was installed. The legacy installer now names the recovery step (`brigade harness uninstall --target cursor --scope user`) when it hits a v2 state, and still fails closed without writing. Closes #468 Co-authored-by: Kimi <noreply@moonshot.cn>
|
Important Review skippedAuto reviews are limited based on label configuration. 🏷️ Required labels (at least one) (1)
Please check the settings in the CodeRabbit UI or the ⚙️ Run configurationConfiguration used: Repository: escoffier-labs/coderabbit/.coderabbit.yaml Review profile: CHILL Plan: Pro Plus Run ID: You can disable this status message by setting the Use the checkbox below for a quick retry:
✨ Finishing Touches🧪 Generate unit tests (beta)
Comment |
Collaborator
Author
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Closes #468.
brigade harness install cursor --scope user(legacy,cursor_user_cmd.py, schema v1) andbrigade harness sync --target cursor --scope user(profile layer,harness_profile_cmd.py, schema v2) share~/.cursor/brigade/install-state.jsonwith incompatible schemas. Each refused the other's state as a conflict with no recovery path — a deadlock whose only manual escape (rmthe state file) also destroys the ownership attestations uninstall needs.Root-cause fix (option 1 from the issue): the legacy installer is already documented as superseded by sync, so the profile layer now detects a legacy version-1 state and deliberately migrates it:
harness_profile_cmd.load_profile_statedetects{"version": 1, ...}on the cursor harness and adopts every legacy attestation into the v2 ownership model — instruction digest, generated plugin/hook artifacts, thehooks.json#sessionStartentry fingerprint, skill files, and MCP projections (the legacy digest prefix isstable_hash-compatible, so unedited live entries still attest). Adoption is in-memory and read-only until a sync--writepersists the migrated state; the result payload reports"migration": {"from": "legacy-install-v1", ...}.brigade/mcp.jsoncatalog and legacy-only skill files are removed through the standard removed-profile/removed-registry paths, and nothing user-owned is clobbered.harness install cursorafter a profile sync now fails closed with a conflict that names the recovery step — runbrigade harness uninstall --target cursor --scope userfrom the owning surface first — instead of a bareunsupported ownership state version: 2.No other harnesses' behavior changes (migration is gated on
harness == "cursor"and the legacy v1 shape; non-cursor and malformed states keep the existing fail-closed error).Tests
test_cursor_legacy_install_migrates_into_profile_sync: legacy install → profile sync migrates cleanly (rule survives byte-for-byte, attestations carried), a second sync is a no-op, andharness uninstall --scope userremoves exactly the artifacts — originally-legacy and newly-synced alike.test_cursor_profile_sync_then_legacy_install_names_recovery: profile sync → legacy install gives the recovery-named conflict, writes nothing, and leaves the v2 state untouched.test_load_state_migrates_legacy_cursor_install_state_read_only/test_load_state_rejects_non_dict_legacy_cursor_sections: unit coverage for the adoption mapping, read-only guarantee, and fail-closed edges.All tests drive a temp HOME/
tmp_path; the real~/.cursoris never touched.Verification (brigade-wired)
Receipts:
.brigade/work/verify-runs/20260724-002316-work-verify-322e6a/and.brigade/work/verify-runs/20260724-002456-work-verify-019210/.