Files
CC-Switch/src/components/ui/sonner.tsx
T
Dex Miller e7badb1a24 Feat/provider individual config (#663)
* refactor(ui): simplify UpdateBadge to minimal dot indicator

* feat(provider): add individual test and proxy config for providers

Add support for provider-specific model test and proxy configurations:

- Add ProviderTestConfig and ProviderProxyConfig types in Rust and TypeScript
- Create ProviderAdvancedConfig component with collapsible panels
- Update stream_check service to merge provider config with global config
- Proxy config UI follows global proxy style (single URL input)

Provider-level configs stored in meta field, no database schema changes needed.

* feat(ui): add failover toggle and improve proxy controls

- Add FailoverToggle component with slide animation
- Simplify ProxyToggle style to match FailoverToggle
- Add usage statistics button when proxy is active
- Fix i18n parameter passing for failover messages
- Add missing failover translation keys (inQueue, addQueue, priority)
- Replace AboutSection icon with app logo

* fix(proxy): support system proxy fallback and provider-level proxy config

- Remove no_proxy() calls in http_client.rs to allow system proxy fallback
- Add get_for_provider() to build HTTP client with provider-specific proxy
- Update forwarder.rs and stream_check.rs to use provider proxy config
- Fix EditProviderDialog.tsx to include provider.meta in useMemo deps
- Add useEffect in ProviderAdvancedConfig.tsx to sync expand state

Fixes #636
Fixes #583

* fix(ui): sync toast theme with app setting

* feat(settings): add log config management

Fixes #612
Fixes #514

* fix(proxy): increase request body size limit to 200MB

Fixes #666

* docs(proxy): update timeout config descriptions and defaults

Fixes #612

* fix(proxy): filter x-goog-api-key header to prevent duplication

* fix(proxy): prevent proxy recursion when system proxy points to localhost

Detect if HTTP_PROXY, HTTPS_PROXY, or ALL_PROXY environment variables
point to loopback addresses (localhost, 127.0.0.1), and bypass system
proxy in such cases to avoid infinite request loops.

* fix(i18n): add providerAdvanced i18n keys and fix failover toast parameter

- Add providerAdvanced.* i18n keys to en.json, zh.json, and ja.json
- Fix failover toggleFailed toast to pass detail parameter
- Remove Chinese fallback text from UI for English/Japanese users

* fix(tray): restore tray-provider events and enable Auto failover properly

- Emit provider-switched event on tray provider click (backward compatibility)
- Auto button now: starts proxy, takes over live config, enables failover

* fix(log): enable dynamic log level and single file mode

- Initialize log at Trace level for dynamic adjustment
- Change rotation strategy to KeepSome(1) for single file
- Set max file size to 1GB
- Delete old log file on startup for clean start

* fix(tray): fix clippy uninlined format args warning

Use inline format arguments: {app_type_str} instead of {}

* fix(provider): allow typing :// in endpoint URL inputs

Change input type from "url" to "text" to prevent browser
URL validation from blocking :// input.

Closes #681

* fix(stream-check): use Gemini native streaming API format

- Change endpoint from OpenAI-compatible to native streamGenerateContent
- Add alt=sse parameter for SSE format response
- Use x-goog-api-key header instead of Bearer token
- Convert request body to Gemini contents/parts format

* feat(proxy): add request logging for debugging

Add debug logs for outgoing requests including URL and body content
with byte size, matching the existing response logging format.

* fix(log): prevent usize underflow in KeepSome rotation strategy

KeepSome(n) internally computes n-2, so n=1 causes underflow.
Use KeepSome(2) as the minimum safe value.
2026-01-20 21:02:44 +08:00

32 lines
1.0 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { Toaster as SonnerToaster } from "sonner";
import { useTheme } from "@/components/theme-provider";
export function Toaster() {
const { theme } = useTheme();
// 将应用主题映射到 Sonner 的主题
// 如果是 "system"Sonner 会自己处理
const sonnerTheme = theme === "system" ? "system" : theme;
return (
<SonnerToaster
position="top-center"
richColors
theme={sonnerTheme}
toastOptions={{
duration: 2000,
classNames: {
toast:
"group rounded-md border bg-background text-foreground shadow-lg",
title: "text-sm font-semibold",
description: "text-sm text-muted-foreground",
closeButton:
"absolute right-2 top-2 rounded-full p-1 text-muted-foreground transition-colors hover:bg-muted hover:text-foreground",
actionButton:
"rounded-md bg-primary px-3 py-1 text-xs font-medium text-primary-foreground transition-colors hover:bg-primary/90",
},
}}
/>
);
}