feat(providers): add OpenRouter System One lane and New badge

OpenRouter serves TypeSafe Jev at POST /api/v1/systemone with the same
request/response shape, so it plugs into systemoneConfig directly with
model typesafe/jev-1.13. Mark the System One media kind isNew and
render a New badge on the sidebar kind item and the Media Providers
accordion when any visible kind is new.

Co-Authored-By: Claude Code <noreply@anthropic.com>
This commit is contained in:
decolua
2026-09-22 14:42:02 +07:00
parent 20014b3104
commit f84c667d42
3 changed files with 14 additions and 2 deletions

View File

@@ -43,8 +43,14 @@ export default {
{ id: "google/veo-3.1", name: "Veo 3.1 (via OpenRouter)", params: ["duration","aspect_ratio","resolution"], kind: "video" },
{ id: "openai/sora-2-pro", name: "Sora 2 Pro (via OpenRouter)", params: ["duration","aspect_ratio","resolution"], kind: "video" },
{ id: "bytedance/seedance-2.0", name: "Seedance 2.0 (via OpenRouter)", params: ["duration","aspect_ratio","resolution"], kind: "video" },
{ id: "typesafe/jev-1.13", name: "Jev 1.13", kind: "systemone" },
],
serviceKinds: ["llm","embedding","tts","imageToText","video"],
serviceKinds: ["llm","embedding","tts","imageToText","video","systemone"],
// System One decision API (TypeSafe-compatible): https://openrouter.ai/docs/guides/community/typesafe-sdk
systemoneConfig: {
baseUrl: "https://openrouter.ai/api/v1/systemone",
headers: {"HTTP-Referer":"https://endpoint-proxy.local","X-Title":"Endpoint Proxy"},
},
ttsConfig: {
baseUrl: "https://openrouter.ai/api/v1/chat/completions",
defaultModel: "openai/gpt-4o-mini-tts",

View File

@@ -200,6 +200,9 @@ export default function Sidebar({ onClose }) {
>
<span className="material-symbols-outlined text-[18px]">perm_media</span>
<span className="text-[13px] font-medium flex-1 text-left">Media Providers</span>
{MEDIA_PROVIDER_KINDS.some((k) => VISIBLE_MEDIA_KINDS.includes(k.id) && k.isNew) && (
<span className="text-[9px] font-bold uppercase text-primary bg-primary/10 px-1.5 py-0.5 rounded">New</span>
)}
<span className="material-symbols-outlined text-[14px] transition-transform" style={{ transform: mediaOpen ? "rotate(180deg)" : "rotate(0deg)" }}>
expand_more
</span>
@@ -220,6 +223,9 @@ export default function Sidebar({ onClose }) {
>
<span className="material-symbols-outlined text-[16px]">{kind.icon}</span>
<span className="text-sm">{kind.label}</span>
{kind.isNew && (
<span className="text-[9px] font-bold uppercase text-primary bg-primary/10 px-1.5 py-0.5 rounded">New</span>
)}
</Link>
))}
<Link

View File

@@ -79,7 +79,7 @@ export const MEDIA_PROVIDER_KINDS = [
{ id: "webFetch", label: "Web Fetch", icon: "language", endpoint: { method: "POST", path: "/v1/web/fetch" } },
{ id: "video", label: "Video", icon: "movie", endpoint: { method: "POST", path: "/v1/videos/generations" } },
{ id: "music", label: "Music", icon: "music_note", endpoint: { method: "POST", path: "/v1/audio/music" } },
{ id: "systemone", label: "System One", icon: "psychology", endpoint: { method: "POST", path: "/v1/systemone" } },
{ id: "systemone", label: "System One", icon: "psychology", endpoint: { method: "POST", path: "/v1/systemone" }, isNew: true },
];
export const OPENAI_COMPATIBLE_PREFIX = "openai-compatible-";