Skip to content

feat(tui/screens): add Engram data-directory management render functions#488

Closed
tonyblu331 wants to merge 6 commits into
Gentleman-Programming:mainfrom
tonyblu331:feat/engram-data-dir-screens-v2
Closed

feat(tui/screens): add Engram data-directory management render functions#488
tonyblu331 wants to merge 6 commits into
Gentleman-Programming:mainfrom
tonyblu331:feat/engram-data-dir-screens-v2

Conversation

@tonyblu331
Copy link
Copy Markdown
Contributor

@tonyblu331 tonyblu331 commented May 9, 2026

Summary Adds four headless render functions for the Engram data-directory feature (issue #346, PR D1 of D1+D2): - RenderEngramDataDir — location picker for the management flow (Welcome → "Manage Engram directory") - RenderEngramDataDirInstall — install-time picker (Keep / Move to… / Start fresh) - RenderEngramDataDirConfirm — destructive-op confirmation with snapshot-ID reminder - RenderEngramDataDirResult — success/error result screen All four are pure string renderers with no Bubbletea dependency, following the pattern of backups.go / upgrade.go. Covered by 10 unit tests. ## Changes | File | Type | Lines | |------|------|-------| | internal/tui/screens/engram_datadir.go | New | +157 | | internal/tui/screens/engram_datadir_test.go | New | +125 | | Total | | +282 / budget: 400 ✅ | ## Test plan - [x] go test ./internal/tui/screens/... — all 10 new Engram tests pass - [x] go build ./... — clean build - [x] Full repo go test ./... — ✅ Pass — CI run - [x] E2E cd e2e && ./docker-test.sh (ubuntu / arch / fedora) — ✅ Pass — same workflow ## PR Chain — Closes #346 | # | PR | Lines | |---|----|-------| | A | #465 | 152 ✅ | | B1 | #484 | 340 ✅ | | B2 | #485 | 171 ✅ | | B3 | #486 | 370 ✅ | | C | #487 | 33 ✅ | | D1 | this PR | 282 ✅ | | D2 | #489 | 340 ✅ | --- ## CI status (GitHub Actions) — latest (ci: trigger unit and e2e workflows) Checks: https://github.com/Gentleman-Programming/gentle-ai/pull/488/checks Unit + E2E workflow: https://github.com/Gentleman-Programming/gentle-ai/actions/runs/25600337966 | Gate | Status | |------|--------| | Unit Tests (go test ./...) | ✅ Pass | | E2E (ubuntu) | ✅ Pass | | E2E (arch) | ✅ Pass | | E2E (fedora) | ✅ Pass | | Issue reference (Closes #346) + status:approved | ✅ Pass | | PR cognitive load vs main | ⚠️ Fails while stack is open (full diff vs main); this slice ≤400 lines ✅ | | Exactly one type:* label | ⚠️ Maintainer applies | bash go test ./... cd e2e && ./docker-test.sh 🤖 Generated with Claude Code


Chain Context (SDD - stacked PRs targeting main)

Field Value
Chain Engram data-directory (#346)
Strategy Stacked branches; each PR opens vs main - upstream typically has no intermediate GitHub base branches, so merge #465 .. #489 in order; branch ancestry carries predecessor commits.
Tracker PR none (feature-branch tracker not used).
This PR #488
Base Gentleman-Programming/gentle-ai main
Cognitive load (GitHub vs main) +1307/-25 = 1332 changed lines
CI budget (400-line gate) EXCEEDS 400 vs main (additions + deletions). CI requires maintainer-applied size:exception, OR retarget this PR to the previous branch once those bases exist upstream so GitHub shows only the slice diff.

The Summary / Changes tables above describe the scoped review unit for this numbered PR. GitHub diff vs main is cumulative while every PR still targets main, so totals grow down-chain even though each PR narrative stays slice-focused.

Merge-order diagram

main -> PR #465 -> PR #484 -> PR #485 -> PR #486 -> PR #487 -> [THIS] PR #488 -> PR #489

Autonomy

  • Single numbered deliverable (Summary).
  • Line totals above match GitHub Files changed aggregation vs main for this PR head.

@tonyblu331
Copy link
Copy Markdown
Contributor Author

👋 Maintainer request: could you please add the `type:feature` label?

Also a note on the size check: this PR is part of a 7-PR chain (A → B1 → B2 → B3 → C → D1 → D2). Because all PRs target `main`, the cognitive-load check counts accumulated diff until each predecessor merges. The per-PR line counts are:

PR Own lines
A #465 152 ✅
B1 #484 340 ✅
B2 #485 171 ✅
B3 #486 370 ✅
C #487 33 ✅
D1 #488 282 ✅
D2 #489 340 ✅

Each PR's check will turn green as soon as its predecessor merges. All seven are independently within the 400-line budget.

tonyblu331 added 6 commits May 9, 2026 19:06
Adds internal/storage package with:
- FormatBytes: human-readable sizes using 1024-based units (B/KiB/MiB/GiB)
- AvailableBytes: platform-gated disk space check (syscall.Statfs on Unix,
  GetDiskFreeSpaceExW on Windows)

No Engram coupling. Used by the upcoming data-directory domain layer.
…r helpers

Introduces the foundational types and location-discovery layer for
Engram data-directory management (issue Gentleman-Programming#346, PR B1 of B1+B2+B3):

- DataDirRef: future-proof path type with Resolve(homeDir), DefaultDir, DBPath helpers
- SuggestLocations: ordered candidate list with deduplication and free-space labels
- Platform-specific volume discovery (Statfs on Unix, GetDiskFreeSpaceEx on Windows)
- FormatDirLine / FormatSpaceWarning presenter helpers (no Bubbletea dep)

10 unit tests cover all location and label behaviours.
Depends on PR A (feat/storage-utils).
Adds the copy primitive for Engram data-directory operations (issue Gentleman-Programming#346,
PR B2 of B1+B2+B3):

- CopyDB(src, dst string) error: writes to a .tmp sibling then os.Rename
  for atomicity; uses io.Copy which activates sendfile/splice on Linux and
  macOS automatically — no manual buffer needed
- Size verification before rename catches truncated writes
- Deferred os.Remove on the tmp file is cancelled only on successful rename
- 5 unit tests cover happy path, idempotency, missing source, and dir creation

Depends on PR B1 (feat/engram-domain-types).
…ions

Completes the engram domain layer for data-directory management (issue Gentleman-Programming#346,
PR B3 of B1+B2+B3):

- DataDirService.CopyTo / MoveTo / Delete: snapshot-guarded operations that
  call backup.Snapshotter.Create before touching data; return snapshot ID
- DiskSpaceOK: pre-flight check before CopyTo/MoveTo
- InjectWithOptions: backward-compatible extension of Inject that accepts
  InjectOptions{DataDir} to include ENGRAM_DATA_DIR in MCP env config;
  existing Inject() delegates to InjectWithOptions with zero options unchanged
- 6 service unit tests + inject backward-compat coverage

Depends on PR B2 (feat/engram-domain-copy).
…e, and TUI model

Adds EngramDataDirOp string enum (keep/copy/move/delete/fresh) and
EngramDataDir string field to Selection for install-time data dir choice.
Persists EngramDataDir in state.json (engram_data_dir) and pre-loads it
into the TUI Model before the first render so management screens have it
available without a separate state read.
Add four headless render functions for the Engram data-directory feature:
- RenderEngramDataDir: location picker (management flow from Welcome)
- RenderEngramDataDirInstall: install-time picker (Keep/Move/Fresh)
- RenderEngramDataDirConfirm: destructive-op confirmation with snapshot reminder
- RenderEngramDataDirResult: success/error result screen

Includes 10 unit tests covering all render paths (no Bubbletea dependency).
Depends on PR C (feat/engram-data-dir-state).
@tonyblu331 tonyblu331 force-pushed the feat/engram-data-dir-screens-v2 branch from 32d189c to dae6de5 Compare May 9, 2026 12:08
@tonyblu331
Copy link
Copy Markdown
Contributor Author

Superseded by the ≤400 LOC chain (no \size:exception).

This draft exceeded the 400-line review budget vs \main.

@tonyblu331 tonyblu331 closed this May 9, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

First-class Engram data-directory selection and migration in install/TUI flows

1 participant