Repository navigation
Dev Migration Assistant 1.0.0 — back up and restore the real local state of your projects (Claude Code sessions, Git working trees and worktrees, project-local config) between Macs.
Install
Download Dev Migration Assistant-1.0.0-arm64.dmg below, open it and drag the app to Applications. macOS 13+ on Apple Silicon.
The build is ad-hoc signed but not notarized, so on first launch use right-click → Open and confirm. Verify the download against SHA256SUMS.txt if you like:
shasum -a 256 -c SHA256SUMS.txtWhat it does
Pick your projects on the old Mac, review exactly what will be captured, and write one encrypted .devbackup file (Argon2id + chunked AES-256-GCM). On the new Mac, open it, map each project to its new path, approve the restore plan, and the app writes only where you approved — then reports what it did and what still needs your attention.
Credentials are never captured. No Keychain items, no OAuth tokens, no MCP server secrets. Sign in again on the new Mac; the restore report tells you where.
Everything runs locally: no account, no server, no telemetry, no cloud upload.
Verification for this build
pnpm verifyand the Playwright E2E suite green on the tagged commit (650 unit + renderer tests, 77 integration tests, 10 E2E).- Every mitigation in the threat model names a passing test — 114 citations, checked mechanically, and a test now fails the build if an unvalidated one reappears.
- The packaged app's Electron fuses are read back in CI and must match ADR-0007:
RunAsNode,EnableNodeOptionsEnvironmentVariableandEnableNodeCliInspectArgumentsdisabled;OnlyLoadAppFromAsarandEnableEmbeddedAsarIntegrityValidationenabled.
Known limitations
No password recovery, no compression, no incremental backups, macOS/Apple Silicon only. The full list is in docs/KNOWN_LIMITATIONS.md.
Next up is 1.1 — Rehydrate: turning "files restored" into "development environment ready" (detect the tools, check what needs signing in again, and walk you through it).
First stable release. Everything the app was built for now ships and is covered by the security gate in
docs/security/THREAT_MODEL.md §5: project scan, encrypted .devbackup
(Argon2id + chunked AES-256-GCM), restore plan with collisions and preflight, safe path remapping, and the
macOS desktop app with a sandboxed renderer, zod-validated IPC, packaged-build fuses and a startup sweep of
leftover staging directories. From 1.0.0 the app version follows SemVer strictly and every 1.x release
keeps opening containers written by any earlier 1.x. Builds are ad-hoc signed but not notarized — see the
install notes in the README.
Added
- Every backup now records a capability snapshot (
manifest.capabilities): developer tools with
version, resolved path and install method, the search path used, and the Claude Code versions that
wrote the transcripts. Names and paths only — never credentials, env values or account details. - Diagnostics lists the developer tools it found (version, path, install method) and the directories
it searches.
Changed
- The app resolves a deterministic search path (launchd
PATH+/etc/paths(.d)+ the well-known
user tool directories that exist) instead of relying on the environment it was launched with. A
Finder-launched build previously reportedclaude,gh,brew,nodeandpnpmas not
installed when they lived in~/.local/binor/opt/homebrew/bin. No login shell is spawned. - The remediation catalogue moved to
@devmig/core(Remediationtype in@devmig/model); the
nvm installsuggestion (a shell function) becamebrew install node@<major>, and the invalid
brew install npmbecamebrew install node.
Security
- MCP server definitions in
~/.claude.jsonwhoseargsorurlcarry a secret-looking value
(e.g.API_KEY=…inline) now make the corresponding artifact sensitive and opt-in; previously
they were included as safe. session-env/scripts (hook-generated per-session environment files, which hooks may fill with
secrets) are no longer backed up or restored; they are listed as ephemeral and Claude Code
regenerates them.- Git remote URLs are stored without embedded credentials — in the manifest and in the Git provider's
repository.json— and are restored without them (https://user:token@…→https://…); sign in again
through your credential helper on the destination.