Skip to content

feat(git): add recoverable branch switching - #1836

Merged
FresnelR27 merged 2 commits into
developfrom
dev/branch-switch-recovery
Sep 15, 2026
Merged

FresnelR27 merged 2 commits into
developfrom
dev/branch-switch-recovery

Conversation

@Harry19081

@Harry19081 Harry19081 commented Sep 15, 2026 •

Copy link
Copy Markdown
Member

Problem

Switching branches only asked about uncommitted work after checkout failed, so compatible edits could move without a choice. The native stash/discard modal offered no Bring option, and optimistic branch updates could show the wrong branch after a partial failure. Positional stash indices and fire-and-forget editor saves also made recovery unreliable.

Solution

  • Replace the native switch modal with the existing shared Modal and SelectionGrid using vertical, showRadio, and visible title/description rows for Leave and Bring.
  • Route existing-branch selection, branch creation, detached checkout, ActionSystem and composer actions through one coordinator that prepares before mutating and publishes actual HEAD.
  • Add a backend-owned, revalidated save/checkout/apply operation with an OS lock per common Git directory. Preserve staged, unstaged and nonignored new files using UUID metadata, immutable snapshot OIDs and recovery refs.
  • Expose saved-work discovery, bounded diff previews and explicit restore in Source Control; preserve earlier snapshots and partially applied recovery copies.
  • Await text/diff editor saves, check disk content, block known active writers and unsupported/unsafe Git states, and translate the new UI in all 13 supported locales. Background refreshes explicitly handle promise rejection without widening lint baselines.

Potential risks

  • Additive HTTP endpoints and JSON journals introduce a new recovery workflow. No database migration is required. fs2 is added as an explicit dependency for OS locking at a version already present in Cargo.lock. App rollback leaves Git stashes and refs/orgii/branch-switch/<UUID> recovery refs usable; do not delete them during rollback.
  • The lock coordinates new switch/restore operations. External Git clients and legacy mutation routes remain independent; the active-task check uses the known ORGII roster rather than an exclusive writer lease. External writers still require coordination.
  • Recovery copies are retained until deliberate cleanup and consume disk. Partially applied operations are not automatically replayed. Journal recovery is tested with interrupted-phase fixtures, not abrupt process-kill testing.
  • Native Windows behavior, real Tauri light/dark and constrained-viewport layout, keyboard/focus behavior, and CPU/RSS measurements are unverified. Computer control was not authorized, so native screenshots/recordings were not captured. DOM tests exercise real shared components but are not visual evidence.

Verification

Checks ran in an isolated worktree based on develop; unrelated staged work was excluded. The latest target branch was fetched and the PR remains mergeable.

  • pnpm exec tsgo --noEmit --pretty false — passed the full project check. The earlier shared-checkout type errors are absent in this isolated branch.
  • Frontend command below — 71 tests passed, covering the coordinator, API serialization/read sharing, real Modal/SelectionGrid behavior, banner lifecycle, editor saves, buffer recovery and existing cache behavior.
  • cd src-tauri && cargo test -p git_api --lib commands::branch_switch — 25 passed using real temporary Git repositories, including Leave/Bring, index preservation, conflicts, collisions, detached/remote targets, worktree locking, stale preparation, journal recovery, pagination and symlinks.
  • cd src-tauri && cargo test -p git --lib util:: — 3 passed, including timeout kill/reap and draining output larger than pipe capacity.
  • Commit hooks ran without bypass: lint-staged (ESLint and Prettier), full TypeScript checking and cargo clippy --lib --message-format=short -p git -p git_api.
  • git diff --check and scoped source/diff review — passed. Confirmed the PR contains only branch-switch code, localization, tests and audit notes; no new raw action controls, sensitive content or unrelated generated changes.
  • Native UI, production application build and performance measurements were not run; limitations are listed above.
pnpm exec vitest run --config config/vitest.config.ts \
  src/api/http/git/branchSwitch.test.ts \
  src/components/GitDialogs/CheckoutConflictDialog/index.test.ts \
  src/components/GitDialogs/SavedChangesDialog/SavedChangesBanner.test.ts \
  src/services/git/operations/__tests__/guardedCheckout.test.ts \
  src/services/git/operations/__tests__/guardedCheckoutRecoveryFallbacks.test.ts \
  src/services/git/operations/__tests__/branchSwitchEditors.test.ts \
  src/services/git/operations/__tests__/branchSwitchWorkspace.test.ts \
  src/store/workstation/codeEditor/gitDiffEditDrafts.branchSwitch.test.ts \
  src/modules/WorkStation/CodeEditor/hooks/fileContent/__tests__/cache.test.ts

CI correction verification

  • pnpm check:i18n-keys — passed: no missing keys, locale gaps, or placeholder mismatches; no new unused keys.
  • NODE_OPTIONS=--max-old-space-size=6144 pnpm check:typed-lint — passed: 1,099 existing findings, zero new or increased findings. Baselines unchanged.
  • node scripts/ci/run-unit-tests.mjs < /tmp/orgii-pr1836-unit-paths — passed using the NUL-delimited PR diff plus the correction paths: 653 test files, 4,766 tests passed, one skipped.
  • pnpm test:typed-lint and pnpm test:i18n-keys — passed: 6 and 27 tooling tests respectively.
  • pnpm exec eslint --max-warnings 0 src/components/GitDialogs/SavedChangesDialog/index.tsx src/components/GitDialogs/SavedChangesDialog/SavedChangesBanner.tsx — passed.
  • Corrective commit hooks passed lint-staged and the staged-file TypeScript gate; no Rust files changed.

Audit

UI audit: 0 fix, 8 keep with reason, 0 abstract. All ten architecture layers reviewed. Automated lifecycle checks pass; the performance verdict remains blocked for unrun native measurements.

@FresnelR27
FresnelR27 merged commit 44323d0 into develop Sep 15, 2026
16 of 17 checks passed
@Harry19081 Harry19081 added enhancement New feature or request dev-tooling Developer tooling, build, CI, tests, diagnostics, or release labels Sep 16, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

dev-tooling Developer tooling, build, CI, tests, diagnostics, or release enhancement New feature or request

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants