v1.7.2-beta.2
Pre-release
Pre-release
Claude Code router-settings tab lands with the model_aliases + web_search RouterConfigYaml extensions, a /v1/messages Verify probe, OpenAI Codex OAuth device-code login, and agent-profile defense-in-depth hardening.
Backend.AI GO v1.7.2-beta.2
14 commits since v1.7.2-beta.1. (13210 lines added, 397 lines deleted)
New Features
- Claude Code router-settings tab in Settings → API. Four cards (Endpoint, Quick Setup, Model Aliases, Web Search) compose the new tab between Providers and Mesh. The tab is fully wired through
RouterConfigYamlextensions so continuum-router can rewrite hard-codedclaude-haiku-4-5-20251001/claude-sonnet-4-6/claude-opus-4-7model names to locally served models and (optionally) inject Serper / Brave / Exa search results into agent prompts (,,, epic). RouterConfigYamlextended withmodel_aliases(ModelAliasesConfig) andweb_search(WebSearchConfig) fields, both optional andskip_serializing_if = "Option::is_none"so existing configs round-trip unchanged.ModelAliasesConfigmaps size-class slots (haiku,sonnet,opus,reasoning,default) plus anexactHashMap.WebSearchConfigmirrors the continuum-routerweb_searchschema (provider, api_key, timeout, result caps, inject policy) and includes a customDebugimpl that redactsapi_key. DTO-validation tests pin the wire shape against the router spec .routerSettingsStoreextended with TypeScript mirrors of the Claude Code router fields. Four new Zustand actions —setModelAlias,setExactAliasEntry,updateWebSearch,applyClaudeCodeDefaults— manage the optionalmodel_aliasesandweb_searchsub-trees with tombstone semantics (drops the parent key when the last field is cleared). Two selector hooks:useModelAliases,useWebSearch.ActiveTabunion extended with"claude-code".ClaudeCodeEndpointCardships with read-onlyANTHROPIC_BASE_URL(derived frombind_addressviaderiveAnthropicBaseUrl),ANTHROPIC_API_KEY(password input with reveal toggle), andANTHROPIC_MODEL(Select populated from loaded models andmodel_aliases.default). "Copy as export" and "Copy as .env" buttons land the three env-vars as shell-ready snippets. A Verify button issues a/v1/messagesprobe through the canonical API adapter;router::service::verify_anthropic_endpoint(shared by both Tauri command and REST handler) classifies outcomes intoconnection_refused,timeout,auth,model_not_found,schema_mismatch, orotherso the UI renders a localized hint .- OpenAI ChatGPT (Codex OAuth) provider with device-code login flow.
CodexOAuthLoginDialogruns the device-code dance;codexOAuthServiceis the transport-agnostic shim forstart/poll/cancel/revoke. Per-provider token store is written to<app_data_dir>/router/auth/<id>.json. Full Tauri + REST parity on the four Codex OAuth commands . - Locale fan-out for the Claude Code Settings tab across
en,ko,ja,zh-CN,zh-TW,es— 28 keys undersettings.apiSettings.claudeCode.*cover Endpoint, Quick Setup, Model Aliases, and Web Search cards plus inline help text and error messages. Alocale-parity.test.ts(16 cases) enforces structural parity. User docs shipped atdocs/en/api-server/claude-code.mdanddocs/ko/api-server/claude-code.md. - Interim notice that web search API keys entered in the Claude Code → Web Search card are stored separately from those in the Providers panel. Rendered below the
api_keyinput inWebSearchCard.tsxwithclaude-code-section__hintstyling and a corresponding!!! note "Storage separation"admonition in both English and Korean docs. Both surfaces cross-reference (the planned consolidation fix) .
Improvements
router::servicemodule is the single source of truth forrouter_config.yamlread/write logic.read_router_config_from_file,save_router_config_preserving_backends, andreset_router_config_to_defaultare called by both the Tauri command and the REST handler so validation, backend-list preservation, and 0o600 permission enforcement live in exactly one place.ServiceErrordiscriminatesValidationfromIo/Serdeso the REST handler maps validation failures to 400 without duplicating that decision in the transport layer .- Quick Setup card writes haiku/sonnet/opus/default slots in a single fan-out and immediately persists. Model Aliases card surfaces per-slot
<Select>rows for primary aliases plus an advanced reveal forreasoningandexactmappings using theCorsOriginsEditorvisual pattern. Web Search card exposes provider dropdown, maskedapi_keywith explicit reveal toggle, and eight advanced tuning fields. A card-level Save bar withHotReloadBadgeconfirmation sits below the cards; Save is gated ongetWebSearchValidationKeyso web_search enabled without an api_key blocks persistence . - All interactive elements in the new Claude Code tab use
src/components/common/primitives (no raw<button>,<select>, or<input type="checkbox">); two pure helpers inutils.ts—getWebSearchValidationKeyandbuildClaudeCodeModelOptions— are the single source of truth for the blocking rule and option construction; both are unit-tested. 10 component tests, 2 regression tests inApiSettingsPage.test.tsx, and 10 new util tests .
Bug Fixes
cargo test --test api_paritywas failing onmainbecause five transport pairs were missing fromPARITY_MAPPINGS: the four Codex OAuth commands/endpoints (start_codex_oauth_login,poll_codex_oauth_login,cancel_codex_oauth_login,revoke_codex_oauth_tokens) and the verify-probe pair (verify_anthropic_endpoint/POST /router/verify-anthropic-endpoint). Both transports already existed and shared their service function; only the parity manifest was missing the rows .cargo test --test security_regressionwas also failing onmainfrom the same omission. The four codex-oauth REST routes were absent fromROUTE_MANIFESTinmanagement_api/route_scope.rs— added withsettings_writescope (mirrors the surrounding/providers/*mutation routes).oauth.rsadded toHANDLER_FILES_WITHOUT_EXPLICIT_SCOPE_ALLOWLIST(, follow-up).router::service::tests::backends_are_preserved_across_savesno longer fails to compile after the continuum-router v1.6.2 bump introducedBackendConfig::auth: Option<BackendAuthConfig>; the test fixture now setsauth: Nonelike every other field ( drive-by).- Delete action hidden for built-in agent profiles in
AgentProfileCard(marketplace grid), matching the existing gate inAgentProfileEditor.store::createnow unconditionally stripsis_builtin = falseso a caller cannot promote a newly created profile to built-in status . store::updatepreservesis_builtinfrom disk, preventing a REST/Tauri caller from unmarking a canonical built-in profile and bypassing the delete-protection guard. Forcingfalseinupdatewould allowPUT {canonical-builtin-id}withis_builtin: falsefollowed by a successfulDELETEbecause theBuiltinCannotBeDeletedguard is a conjunction ofprofile.is_builtin && is_canonical_builtin_id(id).
CI/CD Improvements
None.
Technical Details
- Single source of truth between Tauri commands and REST endpoints for all new transports:
router::service::verify_anthropic_endpoint,router::service::{read_router_config_from_file, save_router_config_preserving_backends, reset_router_config_to_default}, and the fourproviders::oauth::codex::*service functions. Both transports are thin wrappers per.claude/rules/api-parity.md. ?tab=claude-codedeep-link works via thevalidTabsallowlist already extended in.
Dependencies
- Update
continuum-routerto v1.6.2 (picks upBackendConfig::auth: Option<BackendAuthConfig>).
Breaking Changes
None.
Known Issues
- Web search API keys entered in Claude Code → Web Search are stored separately from those in the Providers panel; consolidation is tracked in.
Security
agent_profilestore::updatedefense-in-depth hardening (three changes, defaulting to Option A from the issue): (1)Self::validate_id(id)?is now the first statement ofupdate, mirroringgetanddeleteand rejecting path-traversal / null-byte / overlong IDs before any disk access; (2) the redundant upfrontpath.existscheck is removed in favour of usingread_profile_fileas both the existence probe and the source-of-truth read foris_builtin(any I/ONotFoundis mapped toAgentProfileError::NotFound(id)); (3) a newAgentProfileError::BuiltinCannotBeModifiedvariant blocks content mutation on canonical built-in templates (UUID v5 IDs fromtemplates::get_builtin_templates). Without this guard a direct REST/Tauri caller could rewrite "Code Assistant"'ssystem_prompt(prompt-injection vector), elevateenabled_tools, or swappreferred_model_id. The new error maps to HTTP 400 inmanagement_api/handlers/agent_profiles.rs, matching the existingBuiltinCannotBeDeletedmapping .- Four SSRF defenses on the verify endpoint: scheme allowlist (
http/httpsonly), cloud-metadata host block (169.254.169.254/ GCP / Azure / Alibaba + full169.254.0.0/16link-local range), 64 KiB response body cap, andapi_keyscrub on allerror_detailsurfaces — REST callers supplying a cloud-metadata URL receive a 400 . - Claude Code settings hardening — `` reviews and locks down the new Claude Code tab surfaces (defense-in-depth on the
api_keyhandling and validation paths added in /).