Bring-your-own keys for cloud providers (OpenAI-compatible)

Settings -> Providers takes keys for OpenAI, Anthropic (their official
OpenAI-compatibility layer), DeepSeek, Groq, OpenRouter and any custom
OpenAI-compatible endpoint. One adapter (lib/openai-compat) covers
listing, streaming chat, JSON generation and vision, and every model
flow can run on a provider: the chat picker lists each enabled
provider's models (labelled, remembered), and a "Study generation"
choice moves decks, homework, grading and attachment transcription onto
a provider model.

Keys stay in this browser exactly like the Ollama one
(freezmo.providers.v1): never stored server-side, never in a backup or
the sync payload, forwarded only with the request that needs them. The
provider test asserts the key reaches the provider while the routing
header stays on the app side.

New suite tests/providers-test.mjs (13 checks) stubs both protocols:
model listing, chat streaming, study generation and the Settings flow.
Privacy policy updated (en+cs). Contrast 0 findings, axe clean, mobile
126/126, chat 102/102, wizard 95/95, bubbles 34/34, regression 44/44,
i18n 13/13, native 33/33. Version 0.4.7, SW -> freezmo-v72.
This commit is contained in:
Martin Dvořák 2026-10-14 06:29:39 +00:00
commit 4372423167
28 changed files with 1538 additions and 150 deletions

View file

@ -1411,6 +1411,18 @@ Things I chose while building, with the reasoning:
pre-blurred wallpaper — the scene is clearly visible through the glass, and the
pixel-contrast scan still passes.
81. **Bring-your-own keys for cloud providers.** Besides the server's Ollama, Settings → Providers takes
keys for OpenAI, Anthropic (their official OpenAI-compatibility layer), DeepSeek, Groq, OpenRouter
and any custom OpenAI-compatible endpoint. One adapter (`lib/openai-compat`) covers them all —
model listing, streaming chat, JSON generation and vision — and every model flow can run on a
provider: the chat picker lists each enabled provider's models (labelled, remembered across
visits), and a "Study generation" choice moves decks, homework, grading and attachment
transcription onto a provider model. Keys stay in this browser exactly like the Ollama one
(`freezmo.providers.v1`): never stored server-side, never in a backup or the sync payload, only
forwarded with the request that needs them — the provider test asserts the key reaches the
provider and that the app keeps the routing header to itself. The suite (`tests/providers-test`,
13 checks) covers listing, chat, generation and the Settings flow against a two-protocol stub.
80. **Chat UI pass: glass chrome, one composer panel, friendlier chips.** The chat header was a flat
blue strip and the composer area floated on the wallpaper; both are glass surfaces now (the
composer is one flat frosted panel behind input + chips + note). The disclaimer is plain