Skip to content

SQLR-70 — Desktop playground: in-app Settings for Anthropic API key#146

Merged
joaoh82 merged 1 commit into
mainfrom
sqlr-70-desktop-settings
May 30, 2026
Merged

SQLR-70 — Desktop playground: in-app Settings for Anthropic API key#146
joaoh82 merged 1 commit into
mainfrom
sqlr-70-desktop-settings

Conversation

@joaoh82

@joaoh82 joaoh82 commented May 30, 2026

Copy link
Copy Markdown
Owner

What & why

The SQL playground (sqlrite-desktop) read its ask config exclusively from SQLRITE_LLM_API_KEY in the environment. Launched from Finder / the Dock — which don't inherit a shell's env — the Ask… button just errored. This ports the in-app settings pattern we shipped for the journal example app (SQLR-41 / #145) into the playground, so a user can paste a key in a ⚙ dialog and it persists across restarts. Env var still works as a fallback for existing dev workflows.

Changes

Rust (desktop/src-tauri/)

  • src/settings.rs (new) — AskSettings persisted as JSON to $APP_DATA/com.sqlrite.desktop/settings.json; scrubbed AskSettingsDto (has_api_key: bool — the raw key never crosses to the webview); three-valued AskSettingsUpdate; build_ask_config() (prefers saved key, falls back to SQLRITE_LLM_API_KEY); settings_path(). 5 unit tests.
  • src/main.rsAppState gains settings_path (resolved from app_data_dir() in setup); ask_sql builds config from saved settings instead of AskConfig::from_env(); new get_ask_settings / update_ask_settings commands registered.

Frontend (desktop/src/)

  • lib/SettingsPanel.svelte (new) — gear-modal, rewritten in the playground's plain-CSS idiom (the playground uses global app.css vars, not Tailwind like the journal). Password field, model, max-tokens, "Clear saved key", status line, Esc-to-close, security note.
  • lib/api.ts (new) — getAskSettings / updateAskSettings wrappers with null→absent normalisation.
  • App.svelte — ⚙ header button mounts the panel. app.css.settings-button rule.

desktop/README.md (new) — "Configuring ask" section + security note (no README existed).

Deviations from the journal port

  • build_ask_config is unconditional — the desktop crate has no ask feature gate and always builds the engine with ask on (matching the existing unconditional ask_sql). So all 5 tests always run.
  • tempdir() in tests uses a process-wide AtomicU64 counter instead of subsec_nanos() — the journal's version has a latent parallel-run collision that surfaced here (fixed; see follow-up).

Test plan — all green locally

  • npm install + npm run build (vite) + npm run check (svelte-check: 0 errors/warnings)
  • cargo test -p sqlrite-desktop5/5 pass, stable across 3 runs
  • cargo build -p sqlrite-desktop --all-targets, cargo fmt --check, cargo clippy → new code has 0 warnings (remaining clippy hits are pre-existing)

Not verified: live end-to-end LLM call (needs a real key + network) and the literal Finder-launch scenario (headless run). Both are covered indirectly by unit tests + the binary compiling against the embedded dist/.

Follow-up

The journal app's examples/desktop-journal/src-tauri/src/settings.rs has the identical flaky tempdir() — worth a small ticket to port this fix back.

🤖 Generated with Claude Code

The SQL playground (`sqlrite-desktop`) read its `ask` config exclusively
from `SQLRITE_LLM_API_KEY`. Launched from Finder/the Dock — which don't
inherit a shell's env — the Ask… button just errored. Port the in-app
settings pattern from the journal example (SQLR-41, #145) so the key can
be pasted in a ⚙ dialog and persists across restarts.

- settings.rs: AskSettings (JSON at $APP_DATA/com.sqlrite.desktop/
  settings.json), scrubbed AskSettingsDto (has_api_key bool — the raw
  key never crosses to the webview), three-valued AskSettingsUpdate,
  build_ask_config (saved key, env var fallback). 5 unit tests.
- main.rs: AppState gains settings_path; ask_sql builds config from
  saved settings instead of from_env; add get_ask_settings /
  update_ask_settings commands.
- SettingsPanel.svelte (plain-CSS, matches the playground) + ⚙ header
  button + lib/api.ts wrappers.
- README: Configuring `ask` + security note.

Deviation from the journal port: build_ask_config is unconditional (the
desktop crate has no `ask` feature gate) and tempdir() in tests uses an
atomic counter, not subsec-nanos, to avoid a parallel-run collision.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@vercel

vercel Bot commented May 30, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
rust-sqlite Ready Ready Preview, Comment May 30, 2026 10:44pm

Request Review

@joaoh82 joaoh82 merged commit ed83464 into main May 30, 2026
18 of 19 checks passed
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.

1 participant