agent: lumotia-rebrand — fix Codex cross-model review blockers
Some checks failed
check / cargo check (macos-latest) (push) Has been cancelled
check / cargo check (ubuntu-22.04) (push) Has been cancelled
check / cargo check (windows-latest) (push) Has been cancelled
check / svelte build + lint (push) Has been cancelled

Codex independent review found 11 blockers post-cascade. All addressed.

CRITICAL (data-loss / crash):

10. crates/core/src/paths.rs — migrate_legacy_data_dir_inner used
    fs::rename which fails with EXDEV when source + target are on
    different filesystems (encrypted-home, bind mounts, separate
    $XDG_DATA_HOME partition). Combined with the Phase 5 QC fix that
    made migration errors fatal, this would crash on first launch
    for any user whose data dir spans filesystems. Added
    rename_or_copy_tree() that falls back to copy_dir_recursive +
    remove_dir_all on CrossesDevices / errno 18 (EXDEV). Symlinks
    preserved verbatim. Same fallback applied to magnotia.db ->
    lumotia.db inside the dir.

11. Added 4 unit tests: copy_dir_recursive preserves nested
    structure, rename_or_copy_tree same-filesystem happy path,
    is_cross_device classifies CrossesDevices kind + raw errno 18.

Doc residuals (blockers 1-9):

1. crates/cloud-providers/Cargo.toml — "Wyrdnote pending rebrand"
   description.
2. crates/cloud-providers/src/provider.rs — module docs + test
   fixture Wyrdnote refs.
3. crates/transcription/src/orchestrator.rs — module docs + test
   fixture Wyrdnote refs.
4. docs/roadmap/2026-05-10-pkm-phase-tooling-shortlist.md — phase
   name + outputs/wyrdnote path refs.
5. docs/architecture-map/04-llm-formatting-mcp/llm-tests.md —
   MAGNOTIA_LLM_TEST_MODEL env var.
6. .../cloud-providers-stubs.md — MAGNOTIA_API_KEY_*.
7. docs/architecture-map/03-audio-transcription/tests-and-fixtures.md
   — MAGNOTIA_WHISPER_*.
8. docs/gpu-tuning/plan.md — MAGNOTIA_BENCH_RUN.
9. docs/superpowers/specs/2026-05-09-battery-gpu-aware-thread-tuning-
   design.md + corresponding plan — MAGNOTIA_POWER_STATE_OVERRIDE,
   MAGNOTIA_INFERENCE_THREADS.

cargo test --workspace: 343 pass / 0 fail (up from 339; +4 EXDEV
fallback tests).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-05-13 13:39:21 +01:00
parent f093d18a5e
commit 2491c7a7dd
11 changed files with 235 additions and 70 deletions

View File

@@ -45,7 +45,7 @@ That is the entire public surface. Anything else is an implementation detail of
`store_api_key(provider, key)` (`crates/cloud-providers/src/keystore.rs:15`):
- Acquires the global `Mutex<HashMap<String, String>>` (`api_key_store` static, `:37`).
- Inserts under the key `provider_env_key(provider)` which formats as `MAGNOTIA_API_KEY_{PROVIDER_UPPERCASED}`.
- Inserts under the key `provider_env_key(provider)` which formats as `LUMOTIA_API_KEY_{PROVIDER_UPPERCASED}`.
- Returns nothing — last-write-wins.
`retrieve_api_key(provider)` (`crates/cloud-providers/src/keystore.rs:27`):
@@ -54,7 +54,7 @@ That is the entire public surface. Anything else is an implementation detail of
- Falls back to `std::env::var(env_key)` if not present in memory.
- Returns `Option<String>`.
The fallback is the why behind the `MAGNOTIA_API_KEY_<PROVIDER>` naming convention: an operator can inject a key via the environment without going through the in-memory store, which is useful for headless / CI runs.
The fallback is the why behind the `LUMOTIA_API_KEY_<PROVIDER>` naming convention: an operator can inject a key via the environment without going through the in-memory store, which is useful for headless / CI runs.
### Documented TODO
@@ -90,7 +90,7 @@ Today:
```
caller (currently no in-tree caller)
→ store_api_key(provider, key)
→ api_key_store().lock().insert("MAGNOTIA_API_KEY_{PROVIDER}", key)
→ api_key_store().lock().insert("LUMOTIA_API_KEY_{PROVIDER}", key)
→ retrieve_api_key(provider)
→ check in-memory map
→ fall back to std::env::var
@@ -113,7 +113,7 @@ The formatting pipeline does not need to change to consume cloud-transcribed seg
- **Empty crate is intentional.** Removing it would be premature; the workspace shape and the BYOK plan are both implied by its presence. But anyone doing slice analysis ("what does this crate do?") needs to know it does almost nothing today.
- **API keys vanish on restart.** The TODO is explicit. Until `keyring` integration lands, every cloud-provider feature using these helpers will need to re-prompt the user on every startup or break for headless deployments. Acceptable for a stub; not acceptable for a shipped feature.
- **Env-var fallback is `MAGNOTIA_API_KEY_<PROVIDER>`.** Provider names are uppercased in the env-key construction. A provider name with hyphens or underscores will produce a slightly weird-looking env var; not broken, but worth knowing. `provider = "open-ai"` becomes `MAGNOTIA_API_KEY_OPEN-AI`.
- **Env-var fallback is `LUMOTIA_API_KEY_<PROVIDER>`.** Provider names are uppercased in the env-key construction. A provider name with hyphens or underscores will produce a slightly weird-looking env var; not broken, but worth knowing. `provider = "open-ai"` becomes `LUMOTIA_API_KEY_OPEN-AI`.
- **No threading concerns beyond the mutex.** `Mutex<HashMap>` is fine here because keys are written rarely and read on the path of a network call that dwarfs any contention. The previous note in the doc-comment about "undefined behaviour of mutating process environment variables from arbitrary threads" refers to a discarded design that used `std::env::set_var` — that approach is unsound under the modern Rust memory model. The current in-memory map is the safe replacement.
- **`lumotia-core` dependency is declared but not currently used in this file.** It is reserved for when the providers themselves arrive (they will likely consume `Segment` and tuning helpers).
- **Security of the in-memory map is process-lifetime only.** A core dump or a memory-inspection attack reveals the keys. The `keyring`-backed replacement will inherit OS-level protections; until then the threat model is "user trusts their own machine".