waygate-open 1.6.16 → 1.6.18

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1 @@
1
+ .landing,.landing *,.landing :before,.landing :after{box-sizing:border-box}html.relay-landing{scroll-behavior:smooth;-webkit-text-size-adjust:100%}@media (prefers-reduced-motion:reduce){html.relay-landing{scroll-behavior:auto}}.landing{background:var(--bg-page);color:var(--text-secondary);font-family:var(--font-body);font-size:var(--fs-body);line-height:var(--lh-body);-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale;margin:0;overflow-x:hidden}.landing h1,.landing h2,.landing h3,.landing h4{font-family:var(--font-display);color:var(--text-primary);margin:0;font-weight:700}.landing p{margin:0}.landing a{color:inherit;text-decoration:none}.landing button{font:inherit;color:inherit}.landing code,.landing kbd{font-family:var(--font-mono);font-size:.92em}html.relay-landing ::-webkit-scrollbar{width:10px;height:10px}html.relay-landing ::-webkit-scrollbar-track{background:0 0}html.relay-landing ::-webkit-scrollbar-thumb{background:color-mix(in srgb, var(--iris) 22%, transparent);background-clip:content-box;border:2px solid #0000;border-radius:6px}.landing ::-webkit-scrollbar-thumb:hover{background:color-mix(in srgb, var(--iris) 38%, transparent);background-clip:content-box}.landing .shell{z-index:1;position:relative}.landing .wrap{width:100%;max-width:var(--maxw);padding-inline:var(--gutter);margin:0 auto}.landing .nav{z-index:40;align-items:center;gap:var(--space-6);padding:18px var(--gutter);transition:background var(--d-panel) var(--ease-out), border-color var(--d-panel) var(--ease-out), backdrop-filter var(--d-panel) var(--ease-out), padding var(--d-panel) var(--ease-out);border-bottom:1px solid #0000;display:flex;position:fixed;top:0;left:0;right:0}.landing .nav.stuck{background:color-mix(in srgb, var(--bg-page) 72%, transparent);border-bottom-color:var(--border-subtle);-webkit-backdrop-filter:blur(16px)saturate(140%);padding-block:12px}.landing .nav .brand{align-items:center;gap:11px;display:flex}.landing .nav .brand b{font-family:var(--font-display);letter-spacing:var(--track-tight);color:var(--text-primary);font-size:15px;font-weight:700}.landing .nav .brand span{font-family:var(--font-mono);letter-spacing:var(--track-eyebrow);color:var(--text-ghost);text-transform:uppercase;font-size:9.5px}.landing .nav-links{align-items:center;gap:26px;margin-left:auto;display:flex}.landing .nav-links a{color:var(--text-muted);transition:color var(--d-hover) var(--ease-out);font-size:13px;position:relative}.landing .nav-links a:hover{color:var(--text-primary)}.landing .nav-links a:after{content:"";background:var(--gradient-brand);transform-origin:0;height:1px;transition:transform var(--d-panel) var(--ease-out);position:absolute;bottom:-5px;left:0;right:0;transform:scaleX(0)}.landing .nav-links a:hover:after{transform:scaleX(1)}.landing .nav-menu-toggle,.landing .mobile-nav{display:none}@media (max-width:860px){.landing .nav-links{display:none}.landing .nav-menu-toggle{border:1px solid var(--border-subtle);border-radius:var(--radius-sm);background:color-mix(in srgb, var(--bg-surface) 66%, transparent);width:36px;height:36px;color:var(--text-secondary);cursor:pointer;justify-content:center;align-items:center;padding:0;display:inline-flex}.landing .nav-menu-toggle:hover{color:var(--text-primary);border-color:var(--border-strong)}.landing .nav-menu-toggle:focus-visible{color:var(--brand-400);box-shadow:0 0 0 3px var(--brand-tint);outline:none}.landing .mobile-nav{top:calc(100% + 8px);left:var(--gutter);right:var(--gutter);border:1px solid var(--border-default);border-radius:var(--radius-md);background:color-mix(in srgb, var(--bg-elevated) 94%, transparent);box-shadow:var(--shadow-float);-webkit-backdrop-filter:blur(16px)saturate(140%);backdrop-filter:blur(16px)saturate(140%);gap:4px;padding:8px;display:grid;position:absolute}.landing .mobile-nav[aria-hidden=true]{display:none}.landing .mobile-nav a{border-radius:var(--radius-sm);color:var(--text-secondary);padding:11px 12px;font-size:13px}.landing .mobile-nav a:hover,.landing .mobile-nav a:focus-visible{color:var(--text-primary);background:var(--brand-tint);outline:none}}.landing .display-1{font-size:var(--fs-display-1);line-height:var(--lh-display);letter-spacing:var(--track-display);font-weight:700}.landing .display-2{font-size:var(--fs-display-2);letter-spacing:var(--track-display);font-weight:700;line-height:1.14}.landing .display-3{font-size:var(--fs-display-3);line-height:var(--lh-title);letter-spacing:var(--track-tight);font-weight:600}.landing .lead{font-size:var(--fs-lead);color:var(--text-muted);max-width:62ch;line-height:1.7}.landing .eyebrow{font-family:var(--font-mono);font-size:var(--fs-micro);letter-spacing:var(--track-eyebrow);text-transform:uppercase;color:var(--c,var(--accent-cyan));align-items:center;gap:12px;display:inline-flex}.landing .eyebrow:before{content:"";opacity:.5;background:currentColor;width:26px;height:1px}.landing .eyebrow .idx{color:var(--text-ghost)}.landing .mono{font-family:var(--font-mono)}.landing .dim{color:var(--text-ghost)}.landing .btn{border-radius:var(--radius-md);cursor:pointer;white-space:nowrap;height:44px;transition:transform var(--d-tap) var(--ease-out), box-shadow var(--d-hover) var(--ease-out), border-color var(--d-hover) var(--ease-out), background var(--d-hover) var(--ease-out);border:1px solid #0000;align-items:center;gap:9px;padding:0 22px;font-size:14px;font-weight:500;display:inline-flex}.landing .btn:active{transform:translateY(1px)}.landing .btn-primary{background:var(--brand-500);color:#fff;box-shadow:0 8px 26px -8px color-mix(in srgb, var(--brand-500) 70%, transparent)}.landing .btn-primary:hover{background:var(--brand-hover);box-shadow:0 12px 34px -8px color-mix(in srgb, var(--brand-500) 90%, transparent)}.landing .btn-ghost{background:var(--wash-3);color:var(--text-secondary);border-color:var(--border-default)}.landing .btn-ghost:hover{border-color:var(--border-strong);color:var(--text-primary);background:var(--wash-6)}.landing .btn-sm{height:34px;padding:0 15px;font-size:12.5px}.landing .glass{background:var(--glass-bg);border:1px solid var(--glass-border);border-radius:var(--radius-xl);-webkit-backdrop-filter:blur(var(--glass-blur)) saturate(150%);box-shadow:var(--shadow-float);position:relative;overflow:hidden}.landing .glass:before{content:"";pointer-events:none;background:var(--edge-light);position:absolute;inset:0}.landing .glass-soft{background:var(--glass-bg-soft);-webkit-backdrop-filter:blur(calc(var(--glass-blur) * .6));box-shadow:none}.landing .section{padding-block:clamp(62px,8.4vh,122px);position:relative}.landing .section:before,.landing .strip:before{content:"";z-index:-1;pointer-events:none;background:linear-gradient(180deg, transparent 0%, color-mix(in srgb, var(--bg-band) 84%, transparent) 6%, color-mix(in srgb, var(--bg-band) 88%, transparent) 50%, color-mix(in srgb, var(--bg-band) 84%, transparent) 94%, transparent 100%);position:absolute;inset:0}.landing .sec-head{gap:var(--space-6) var(--space-8);margin-bottom:var(--space-8);grid-template-columns:minmax(0,7fr) minmax(0,5fr);align-items:end;display:grid}.landing .sec-head .lead{padding-bottom:6px}@media (max-width:900px){.landing .sec-head{grid-template-columns:1fr;align-items:start}}.landing .rule{background:var(--border-subtle);border:0;height:1px;margin:0}.landing .reveal{opacity:0;transition:opacity .9s var(--ease-out), transform .9s var(--ease-out);transition-delay:calc(var(--i,0) * 80ms);transform:translateY(22px)}.landing .reveal.in{opacity:1;transform:none}@media (prefers-reduced-motion:reduce){.landing .reveal{opacity:1!important;transform:none!important}}.landing .rail{z-index:30;flex-direction:column;align-items:center;gap:9px;display:flex;position:fixed;top:50%;right:22px;transform:translateY(-50%)}.landing .rail i{background:var(--border-default);transform-origin:50% 0;width:1px;height:26px;display:block}.landing .rail i.on{background:var(--gradient-brand);box-shadow:0 0 12px 1px color-mix(in srgb, var(--brand-500) 60%, transparent)}@media (max-width:1180px){.landing .rail{display:none}}.landing .code{background:var(--bg-code);border:1px solid var(--border-subtle);border-radius:var(--radius-lg);font-family:var(--font-mono);color:var(--text-tertiary);white-space:pre;padding:18px 20px;font-size:12.5px;line-height:1.9;position:relative;overflow-x:auto;-webkit-mask-image:none}.landing .code .c{color:var(--text-faint)}.landing .code .k{color:var(--accent-cyan)}.landing .code .s{color:var(--signal-live)}.landing .code .v{color:var(--brand-400)}.landing .code .fn{color:var(--text-primary);font-weight:500}.landing .footer{z-index:1;border-top:1px solid var(--border-subtle);background:var(--bg-band);color:var(--text-ghost);padding-block:40px;font-size:12.5px;position:relative}.landing .footer .row{flex-wrap:wrap;align-items:center;gap:14px 28px;display:flex}.landing .footer .row .sp{margin-left:auto}.landing .grid-2{gap:var(--space-5);grid-template-columns:repeat(2,minmax(0,1fr));display:grid}.landing .grid-3{gap:var(--space-5);grid-template-columns:repeat(3,minmax(0,1fr));display:grid}.landing .grid-4{gap:var(--space-5);grid-template-columns:repeat(4,minmax(0,1fr));display:grid}@media (max-width:1100px){.landing .grid-3,.landing .grid-4{grid-template-columns:repeat(2,minmax(0,1fr))}}@media (max-width:720px){.landing .grid-2,.landing .grid-3,.landing .grid-4{grid-template-columns:1fr}}.landing .card{background:var(--bg-surface-grad);border:1px solid var(--border-subtle);border-radius:var(--radius-lg);position:relative}.landing .card-2{background:var(--bg-surface-2-grad)}.landing .dot{background:currentColor;border-radius:50%;flex:0 0 7px;width:7px;height:7px;display:inline-block;box-shadow:0 0 10px 1px}.landing .dot-live{animation:dot-pulse 2.6s var(--ease-in-out) infinite}@keyframes dot-pulse{0%,to{box-shadow:0 0 10px 1px}50%{box-shadow:0 0 16px 3px}}.landing .pill{height:22px;font-family:var(--font-mono);letter-spacing:.02em;color:var(--text-tertiary);background:var(--wash-3);border:1px solid var(--border-default);white-space:nowrap;border-radius:999px;align-items:center;gap:6px;padding:0 9px;font-size:11.5px;display:inline-flex}.landing .pill-live{color:var(--signal-live);border-color:var(--signal-live-track);background:color-mix(in srgb, var(--signal-live) 7%, transparent)}.landing .pill-amber{color:var(--warn-amber);border-color:var(--warn-amber-line);background:color-mix(in srgb, var(--warn-amber) 7%, transparent)}.landing .pill-brand{color:var(--brand-400);border-color:color-mix(in srgb, var(--iris) 28%, transparent);background:var(--brand-tint)}.landing .num{font-family:var(--font-display);font-variant-numeric:tabular-nums;font-feature-settings:"tnum" 1;letter-spacing:var(--track-display);font-weight:700}.landing .unit{color:var(--text-faint);letter-spacing:0;margin-left:3px;font-size:.42em;font-weight:600}@media (prefers-reduced-motion:reduce){.landing .dot-live,.landing .grad-text{animation:none!important}}.landing [id]{scroll-margin-top:104px}.landing .progress{z-index:60;pointer-events:none;height:2px;position:fixed;top:0;left:0;right:0}.landing .progress i{height:100%;transform:scaleX(var(--scroll-p,0));transform-origin:0;background:var(--gradient-brand);box-shadow:0 0 14px 1px color-mix(in srgb, var(--brand-500) 55%, transparent);will-change:transform;display:block}.landing .hero{padding-block:clamp(140px,16vh,196px) clamp(56px,8vh,96px);position:relative}.landing .hero-grid{grid-template-columns:minmax(0,1.55fr) minmax(0,.85fr);align-items:start;gap:clamp(28px,3.6vw,64px);display:grid}.landing .hero-inner{max-width:940px}.landing .hero-side{padding-top:clamp(34px,4.4vh,58px)}@media (max-width:1080px){.landing .hero-grid{grid-template-columns:1fr}.landing .hero-side{display:none}}.landing .hero-badge{background:color-mix(in srgb, var(--signal-live) 7%, transparent);border:1px solid var(--signal-live-track);color:var(--signal-live);font-size:12.5px;font-family:var(--font-mono);letter-spacing:.01em;border-radius:999px;align-items:center;gap:9px;margin-bottom:32px;padding:7px 15px;display:inline-flex}.landing .hero-badge .n{font-variant-numeric:tabular-nums}.landing .hero-title{position:relative}.landing .hero-h1{margin:0}.landing .hero-h1 .mk{font-family:var(--font-mono);letter-spacing:-.03em;font-weight:700}.landing .hero-flip{pointer-events:none;-webkit-user-select:none;user-select:none;opacity:.26;filter:blur(.8px);width:100%;height:clamp(44px,5.6vh,72px);position:absolute;top:100%;left:0;overflow:hidden;-webkit-mask-image:linear-gradient(#0000006b 0%,#0000001a 40%,#0000 82%);mask-image:linear-gradient(#0000006b 0%,#0000001a 40%,#0000 82%)}.landing .hero-flip>.hero-h1{transform-origin:50% 100%;width:100%;position:absolute;bottom:100%;left:0;transform:scaleY(-1)}.landing .hero-flip .grad-text{background-position:30% 0;animation:none}.landing .hero-sub{max-width:600px;font-size:var(--fs-lead);color:var(--text-muted);margin-top:clamp(62px,7.6vh,92px);line-height:1.78}.landing .hero-acts{flex-wrap:wrap;gap:14px;margin-top:38px;display:flex}.landing .trust{color:var(--text-faint);font-size:12.5px;font-family:var(--font-mono);letter-spacing:.01em;flex-wrap:wrap;gap:12px 26px;margin-top:28px;display:flex}.landing .trust span{align-items:center;gap:8px;display:inline-flex}.landing .trust span:before{content:"";background:var(--brand-400);opacity:.8;flex:0 0 5px;width:5px;height:5px;transform:rotate(45deg)}.landing .rv-line{display:block;overflow:hidden}.landing .rv-line>span{transition:transform 1.15s var(--ease-out);transition-delay:calc(var(--i,0) * .11s);display:block;transform:translateY(106%)}.landing .reveal.in .rv-line>span{transform:none}@media (prefers-reduced-motion:reduce){.landing .rv-line>span{transform:none!important}}.landing .scroll-cue{left:var(--gutter);font-family:var(--font-mono);letter-spacing:var(--track-eyebrow);text-transform:uppercase;color:var(--text-ghost);opacity:max(0, calc(1 - var(--scroll-p) * 22));align-items:center;gap:12px;font-size:9.5px;transition:opacity .2s linear;display:flex;position:absolute;bottom:34px}.landing .scroll-cue .tick{background:linear-gradient(180deg, var(--border-strong), transparent);width:1px;height:40px;position:relative;overflow:hidden}.landing .scroll-cue .tick:after{content:"";background:var(--accent-cyan);width:1px;height:14px;box-shadow:0 0 8px 1px var(--glow-cyan-mid);animation:cue-run 2.4s var(--ease-in-out) infinite;position:absolute;left:0}@keyframes cue-run{0%{opacity:0;top:-14px}25%{opacity:1}75%{opacity:1}to{opacity:0;top:40px}}@media (max-width:900px){.landing .scroll-cue{display:none}}.landing .access{border-radius:var(--radius-xl);background:linear-gradient(180deg, color-mix(in srgb, var(--bg-section-b) 96%, transparent) 0%, color-mix(in srgb, var(--bg-section-a) 94%, transparent) 100%);padding:20px 22px 22px}.landing .access-h{justify-content:space-between;align-items:center;gap:12px;display:flex}.landing .access-url{background:color-mix(in srgb, var(--bg-band) 62%, transparent);border:1px solid var(--border-default);border-radius:var(--radius-md);align-items:center;gap:12px;margin-top:14px;padding:11px 12px 11px 14px;display:flex}.landing .access-url code{min-width:0;font-family:var(--font-mono);color:var(--accent-cyan);text-overflow:ellipsis;white-space:nowrap;flex:1;font-size:12.5px;overflow:hidden}.landing .access-url .copy{height:26px;font-family:var(--font-mono);color:var(--text-muted);cursor:pointer;background:var(--wash-4);border:1px solid var(--border-default);border-radius:var(--radius-xs);transition:color var(--d-hover) var(--ease-out), border-color var(--d-hover) var(--ease-out);flex:none;padding:0 10px;font-size:11px}.landing .access-url .copy:hover{color:var(--text-primary);border-color:var(--border-strong)}.landing .access-note{color:var(--text-ghost);margin-top:12px;font-size:12px;line-height:1.7}.landing .kv{margin:18px 0 0;padding:0}.landing .kv>div{border-top:1px solid var(--border-subtle);justify-content:space-between;align-items:baseline;gap:12px;padding:9px 0;display:flex}.landing .kv>div:last-child{border-bottom:1px solid var(--border-subtle)}.landing .kv dt{color:var(--text-muted);font-size:12.5px}.landing .kv dd{font-family:var(--font-mono);color:var(--text-secondary);font-variant-numeric:tabular-nums;margin:0;font-size:12.5px}.landing .panel-wrap{border-radius:var(--radius-2xl);grid-template-columns:minmax(0,1.3fr) minmax(0,.9fr);margin-top:clamp(52px,7vh,88px);display:grid}.landing .panel-left{min-width:0}.landing .winbar{border-bottom:1px solid var(--border-subtle);background:color-mix(in srgb, var(--bg-page) 40%, transparent);align-items:center;gap:8px;padding:12px 14px 12px 18px;display:flex}.landing .winbar>i{border-radius:50%;width:10px;height:10px;display:block}.landing .winbar .fname{font-family:var(--font-mono);color:var(--text-faint);margin-left:10px;font-size:11.5px}.landing .winbar .wtag{border-radius:var(--radius-xs);font-family:var(--font-mono);letter-spacing:.1em;color:var(--text-ghost);background:var(--wash-4);border:1px solid var(--border-subtle);padding:2px 6px;font-size:9.5px}.landing .winbar .wsp{flex:1}.landing .winbar .wbtn{cursor:pointer;height:24px;font-family:var(--font-mono);color:var(--text-muted);background:var(--wash-4);border:1px solid var(--border-subtle);border-radius:var(--radius-xs);transition:color var(--d-hover) var(--ease-out), border-color var(--d-hover) var(--ease-out);padding:0 10px;font-size:10.5px}.landing .winbar .wbtn:hover{color:var(--text-primary);border-color:var(--border-strong)}.landing .panel-code{font-family:var(--font-mono);padding:12px 0 16px;font-size:12.5px;line-height:1.9}.landing .cl{grid-template-columns:46px minmax(0,1fr);padding-right:20px;display:grid}.landing .cl>i{text-align:right;color:var(--text-faint);-webkit-user-select:none;user-select:none;padding-right:16px;font-style:normal}.landing .cl>span{white-space:pre;color:var(--text-tertiary);overflow-x:auto}.landing .cl.hl{background:color-mix(in srgb, var(--brand-500) 8.5%, transparent);box-shadow:inset 2px 0 0 var(--brand-500)}.landing .cl.hl>i{opacity:.72;color:var(--brand-400)}.landing .panel-code .k{color:var(--accent-cyan)}.landing .panel-code .s{color:var(--signal-live)}.landing .panel-code .c{color:var(--text-faint)}.landing .panel-code .fn{color:var(--text-primary);font-weight:500}.landing .panel-right{border-left:1px solid var(--border-subtle);background:color-mix(in srgb, var(--bg-page) 40%, transparent);padding:16px 20px 20px}.landing .pr-head{justify-content:space-between;align-items:baseline;gap:12px;padding-bottom:12px;display:flex}.landing .panel-right h4{font-family:var(--font-mono);letter-spacing:var(--track-eyebrow);text-transform:uppercase;color:var(--text-ghost);font-size:10.5px;font-weight:500}.landing .pr-count{font-family:var(--font-mono);color:var(--text-ghost);font-size:10.5px}.landing .conn{border-top:1px solid var(--border-subtle);align-items:center;gap:10px;padding:12px 0;font-size:12.5px;display:flex}.landing .conn .cname{min-width:0;color:var(--text-secondary);text-overflow:ellipsis;white-space:nowrap;flex:1;overflow:hidden}.landing .conn .dev{color:var(--text-ghost);font-size:10.5px;font-family:var(--font-mono)}.landing .conn .lat{text-align:right;font-family:var(--font-mono);color:var(--text-faint);font-variant-numeric:tabular-nums;flex:0 0 40px;font-size:10.5px}.landing .panel-metrics{border-top:1px solid var(--border-subtle);grid-template-columns:repeat(3,1fr);gap:14px;margin-top:16px;padding-top:16px;display:grid}.landing .panel-metrics .k{color:var(--text-ghost);margin-bottom:7px;font-size:10.5px}.landing .panel-metrics .v{color:var(--text-primary);font-size:19px}@media (max-width:900px){.landing .panel-wrap{grid-template-columns:1fr}.landing .panel-right{border-left:none;border-top:1px solid var(--border-subtle)}.landing .winbar .wtag,.landing .winbar .wbtn{display:none}}.landing .strip{padding-block:clamp(34px,5vh,52px);position:relative}.landing .strip .cap{color:var(--text-muted);margin-bottom:20px;font-size:13.5px}.landing .strip .cap b{color:var(--text-secondary);font-weight:600}.landing .logos{flex-wrap:wrap;justify-content:space-between;align-items:center;gap:18px 30px;display:flex}.landing .logos span{font-family:var(--font-display);color:var(--text-faint);letter-spacing:.01em;transition:color var(--d-panel) var(--ease-out);font-size:16px;font-weight:600}.landing .logos span:hover{color:var(--text-tertiary)}.landing .logos span.cn{font-family:var(--font-body);color:var(--text-muted);font-size:15px;font-weight:500}.landing .split{grid-template-columns:440px minmax(0,1fr);align-items:start;gap:clamp(40px,5vw,76px);display:grid}.landing .split-l{position:sticky;top:124px}.landing .split-l .display-2{margin:20px 0 18px;font-size:clamp(26px,2.6vw,40px)}.landing .split-l p{color:var(--text-muted);font-size:14px;line-height:1.8}@media (max-width:980px){.landing .split{grid-template-columns:1fr;gap:32px}.landing .split-l{position:static}}.landing .linelist{margin:0;padding:0;list-style:none}.landing .linelist li{border-top:1px solid var(--border-subtle);gap:20px;padding:28px 0;display:flex}.landing .linelist li:last-child{border-bottom:1px solid var(--border-subtle)}.landing .linelist li:first-child{border-top-color:var(--border-default)}.landing .ll-ico{border-radius:var(--radius-md);background:var(--bg-surface-2-grad);border:1px solid var(--border-default);flex:0 0 40px;justify-content:center;align-items:center;width:40px;height:40px;display:flex}.landing .ll-tx b{color:var(--text-primary);margin-bottom:8px;font-size:15.5px;font-weight:600;display:block}.landing .ll-tx i{color:var(--text-tertiary);font-size:13.5px;font-style:normal;line-height:1.75}.landing .steps{grid-template-columns:repeat(3,1fr);margin:0;padding:0;list-style:none;display:grid}.landing .steps li{padding-right:44px;position:relative}.landing .steps li:before{content:"";background:linear-gradient(90deg, color-mix(in srgb, var(--iris) 34%, transparent) 0%, color-mix(in srgb, var(--iris) 34%, transparent) 36%, var(--glow-cyan-core) 50%, color-mix(in srgb, var(--accent-cyan) 30%, transparent) 64%, color-mix(in srgb, var(--accent-cyan) 30%, transparent) 100%);height:1px;animation:4.6s linear infinite step-flow;animation-delay:calc(var(--i,0) * .55s);background-size:280% 100%;position:absolute;top:23px;left:56px;right:12px}.landing .steps li:after{content:"";background:color-mix(in srgb, var(--iris) 70%, transparent);border-radius:50%;width:5px;height:5px;position:absolute;top:20.5px;left:56px}.landing .steps li:last-child:before,.landing .steps li:last-child:after{display:none}@keyframes step-flow{0%{background-position:140% 0}to{background-position:-140% 0}}.landing .st-n{z-index:1;border-radius:var(--radius-lg);width:46px;height:46px;font-family:var(--font-mono);color:var(--brand-400);background:var(--bg-surface-2-grad);border:1px solid var(--border-default);font-variant-numeric:tabular-nums;justify-content:center;align-items:center;font-size:14px;display:flex;position:relative}.landing .steps h3{color:var(--text-primary);margin:22px 0 10px;font-size:16px;font-weight:600}.landing .steps p{color:var(--text-muted);font-size:13.5px;line-height:1.75}.landing .steps .cmd{font-family:var(--font-mono);color:var(--accent-cyan);background:var(--bg-code);border:1px solid var(--border-default);border-radius:var(--radius-sm);white-space:nowrap;margin-top:16px;padding:10px 12px;font-size:11.5px;overflow-x:auto}@media (max-width:900px){.landing .steps{grid-template-columns:1fr;gap:34px}.landing .steps li{padding-right:0}.landing .steps li:before,.landing .steps li:after{display:none}}.landing .term{border:1px solid var(--border-subtle);border-radius:var(--radius-lg);background:color-mix(in srgb, var(--bg-band) 66%, transparent);margin-top:clamp(38px,5vh,62px);overflow:hidden}.landing .term-bar{border-bottom:1px solid var(--border-subtle);background:color-mix(in srgb, var(--bg-page) 52%, transparent);font-family:var(--font-mono);letter-spacing:.02em;color:var(--text-faint);align-items:center;gap:9px;padding:12px 18px;font-size:11px;display:flex}.landing .term-tag{color:var(--text-ghost);margin-left:auto}.landing .term-body{font-family:var(--font-mono);padding:15px 20px 17px;font-size:12.5px;line-height:2.05}.landing .tl{color:var(--text-tertiary)}.landing .tl .pr{color:var(--brand-400);margin-right:9px}.landing .tl.out{color:var(--text-muted)}.landing .tl.ok,.landing .tl .hl{color:var(--signal-live)}@media (max-width:720px){.landing .term-body{font-size:11.5px;line-height:1.95}.landing .tl{word-break:break-all}}.landing .cfg{flex-direction:column;padding:22px;display:flex}.landing .cfg h3{margin-bottom:7px;font-size:16px;font-weight:600}.landing .cfg .sub{color:var(--text-faint);font-size:11.5px;font-family:var(--font-mono);white-space:nowrap;text-overflow:ellipsis;margin-bottom:18px;overflow:hidden}.landing .cfg .code{white-space:pre-wrap;overflow-wrap:anywhere;flex:1;font-size:12px;line-height:1.8}.landing .specbar{background:var(--bg-surface);border:1px solid var(--border-subtle);border-radius:var(--radius-lg);grid-template-columns:repeat(4,1fr);margin-top:22px;display:grid;overflow:hidden}.landing .specbar>div{border-right:1px solid var(--border-subtle);padding:17px 20px}.landing .specbar>div:last-child{border-right:none}.landing .specbar .k{color:var(--text-muted);margin-bottom:9px;font-size:11.5px}.landing .specbar .v{font-family:var(--font-mono);color:var(--text-primary);font-size:14px}@media (max-width:720px){.landing .specbar{grid-template-columns:repeat(2,1fr)}.landing .specbar>div:nth-child(2){border-right:none}.landing .specbar>div:nth-child(-n+2){border-bottom:1px solid var(--border-subtle)}}.landing .cfg-note{background:var(--bg-surface);border:1px solid var(--border-subtle);border-radius:var(--radius-lg);margin-top:18px;padding:16px 20px}.landing .cfg-note-row{border-bottom:1px solid var(--border-subtle);grid-template-columns:132px 1fr;align-items:baseline;gap:6px 14px;padding:9px 0;display:grid}.landing .cfg-note-row .k{color:var(--text-muted);font-size:12.5px}.landing .cfg-note-row code{font-family:var(--font-mono);color:var(--text-primary);font-size:12.5px}.landing .cfg-note-row .v{color:var(--text-tertiary);grid-column:2;font-size:12px}.landing .cfg-note-row .v b{color:var(--text-primary);font-weight:600}.landing .cfg-note-foot{color:var(--text-tertiary);margin-top:12px;font-size:12px;line-height:1.7}.landing .cfg-note-foot:first-of-type{margin-top:14px}.landing .cfg-note-foot code{font-family:var(--font-mono);color:var(--text-primary);overflow-wrap:anywhere;font-size:11.5px}.landing .cfg-note-foot b{color:var(--text-secondary);font-weight:600}@media (max-width:720px){.landing .cfg-note-row{grid-template-columns:1fr}.landing .cfg-note-row .v{grid-column:1}}.landing .band{background:linear-gradient(180deg, transparent 0%, color-mix(in srgb, var(--bg-page) 62%, transparent) 18%, color-mix(in srgb, var(--bg-page) 62%, transparent) 82%, transparent 100%);position:relative}.landing .status-strip{text-align:center;grid-template-columns:repeat(4,1fr);display:grid}.landing .status-strip>div{padding:6px 12px;position:relative}.landing .status-strip>div+div:before{content:"";background:var(--border-subtle);width:1px;position:absolute;top:12%;bottom:12%;left:0}.landing .status-strip .v{color:var(--text-primary);font-size:clamp(34px,4vw,54px);line-height:1}.landing .status-strip .v.live{color:var(--signal-live)}.landing .status-strip .k{color:var(--text-muted);margin-top:14px;font-size:12.5px}@media (max-width:720px){.landing .status-strip{grid-template-columns:repeat(2,1fr);gap:30px 0}.landing .status-strip>div:nth-child(odd):before{display:none}}.landing .cta{text-align:center;padding-block:clamp(96px,15vh,172px);position:relative}.landing .cta:before{content:"";background:radial-gradient(58% 66% at 50% 50%, color-mix(in srgb, var(--bg-band) 88%, transparent) 0%, color-mix(in srgb, var(--bg-band) 55%, transparent) 46%, transparent 76%);pointer-events:none;position:absolute;inset:0}.landing .cta>.wrap{position:relative}.landing .cta h2{max-width:720px;margin:0 auto}.landing .cta .cmdbox{background:color-mix(in srgb, var(--bg-band) 70%, transparent);border:1px solid var(--border-strong);border-radius:var(--radius-lg);font-family:var(--font-mono);color:var(--signal-live);box-shadow:0 0 0 1px color-mix(in srgb, var(--signal-live) 6%, transparent), 0 24px 60px -34px color-mix(in srgb, var(--signal-live) 50%, transparent);align-items:center;gap:12px;margin:32px auto 26px;padding:15px 28px;font-size:15px;display:inline-flex}.landing .cta .cmdbox .pr{color:var(--text-ghost)}.landing .cmdbox .typing:after{content:"";vertical-align:-2px;background:var(--accent-cyan);width:7px;height:1em;margin-left:3px;animation:1s step-end infinite caret;display:inline-block}@keyframes caret{50%{opacity:0}}@media (prefers-reduced-motion:reduce){.landing .cmdbox .typing:after{animation:none}}.landing .cta p.note{color:var(--text-muted);max-width:620px;margin:0 auto;font-size:14px;line-height:1.8}.landing .cta .acts{flex-wrap:wrap;justify-content:center;gap:14px;margin-top:32px;display:flex}.landing .cta .trust{justify-content:center}.landing .footer{padding-block:72px 40px}.landing .foot-top{grid-template-columns:minmax(0,1.6fr) minmax(0,1fr) minmax(0,1fr);gap:44px;display:grid}.landing .foot-brand p{color:var(--text-muted);max-width:340px;margin:20px 0 22px;font-size:13.5px;line-height:1.85}.landing .foot-col h5{color:var(--text-muted);font-size:11.5px;font-weight:500;font-family:var(--font-mono);letter-spacing:var(--track-eyebrow);text-transform:uppercase;margin-bottom:18px}.landing .foot-col a{color:var(--text-faint);transition:color var(--d-hover) var(--ease-out);font-size:13px;line-height:2.2;display:block}.landing .foot-col a:hover{color:var(--text-secondary)}.landing .foot-bar{border-top:1px solid var(--border-subtle);color:var(--text-ghost);flex-wrap:wrap;justify-content:space-between;gap:10px 28px;margin-top:56px;padding-top:24px;font-size:12px;display:flex}@media (max-width:900px){.landing .foot-top{grid-template-columns:1fr 1fr}.landing .foot-brand{grid-column:1/-1}}.landing .rail{align-items:flex-end}.landing .rail a{flex-direction:row-reverse;align-items:center;gap:9px;display:flex}.landing .rail a b{font-family:var(--font-mono);letter-spacing:var(--track-eyebrow);text-transform:uppercase;color:#0000;white-space:nowrap;transition:color var(--d-panel) var(--ease-out);font-size:9.5px}.landing .rail a:hover b,.landing .rail a.on b{color:var(--text-faint)}.landing .rail a i{transition:background var(--d-panel) var(--ease-out), box-shadow var(--d-panel) var(--ease-out)}html.relay-landing{overflow-x:hidden}.landing{overflow-x:visible}.landing .nav{height:auto;box-shadow:none;-webkit-backdrop-filter:none;backdrop-filter:none;background:0 0}.landing .nav:before,.landing .nav:after{content:none}.landing .section{padding-inline:0}.landing .section:after{content:none}.landing .eyebrow{margin-bottom:0;font-weight:400}.landing .pill{font-weight:400}.landing .note{background:0 0;border:0;padding:0;display:block}.landing .btn:hover{transform:none}.btn-primary:hover{box-shadow:0 6px 20px -4px color-mix(in srgb, var(--brand-500) 55%, transparent), inset 0 1px 0 #ffffff2e;border-color:color-mix(in srgb, var(--brand-400) 60%, transparent)}.btn-quiet:hover{border-color:var(--border-strong);box-shadow:0 3px 12px -4px #0000004d}.landing h5{margin:revert}.landing .glass{-webkit-backdrop-filter:blur(var(--glass-blur)) saturate(150%);backdrop-filter:blur(var(--glass-blur)) saturate(150%)}.landing .glass-soft{-webkit-backdrop-filter:blur(calc(var(--glass-blur) * .6));backdrop-filter:blur(calc(var(--glass-blur) * .6))}.landing .nav.stuck{-webkit-backdrop-filter:blur(16px)saturate(140%);backdrop-filter:blur(16px)saturate(140%)}.landing .nav{justify-content:normal}.landing .nav-links{color:var(--text-secondary)}.landing .hero>.wrap{z-index:auto;position:static}.landing .note{border-radius:0;gap:normal}.landing .btn{justify-content:normal}
@@ -0,0 +1 @@
1
+ import{B as e,N as t,_ as n,i as r,it as i,r as a,tt as o}from"./vendor-befEYGHM.js";import{O as s,_ as c,c as l,g as u,j as d,k as f,p,r as m,v as h,x as g}from"./index-BcWmrhMD.js";import{a as _,c as v,i as y,n as b,r as x,s as S,t as C}from"./Select-Bfquh0d_.js";import{r as w}from"./PageSkeleton-DG-Dj4_9.js";import{n as T,t as E}from"./sharedWindow-FDfq75PI.js";import{t as D}from"./useFx-xcrp_LHB.js";import{n as O,t as k}from"./ClientMetricTip-BqIkh3DO.js";var A=i(),j=o();function M({navigate:i}){let[o,M]=(0,A.useState)(()=>E()??`today`),N=d(()=>l.overview(o),[o],{cacheKey:`overview:${o}`});D(`overview-${o}-${N.data?`ready`:`pending`}`);let P=N.data,F={today:(()=>{let e=new Date;return e.getHours()*60+e.getMinutes()||1})(),"1h":60,"24h":1440,"7d":10080,"30d":43200},I=P?F[P.window]:null,L=P&&I?P.metrics.requests/I:null,R=P&&I?P.metrics.totalTokens/I:null,z=e=>{if(!P||P.byClient.length===0)return;let t=[...P.byClient].sort((t,n)=>(n[e]??0)-(t[e]??0));return(0,j.jsx)(k,{rows:t,metric:e,windowLabel:s[P.window],total:e===`credits`?P.metrics.creditsUsed:P.metrics.requests,totalCount:t.length})};return(0,j.jsxs)(`div`,{className:`view on`,children:[(0,j.jsx)(S,{title:`概览`,status:P?(0,j.jsxs)(v,{tone:`live`,dot:!0,children:[`本机日志聚合 · `,h(P.generatedAt)]}):null,actions:(0,j.jsxs)(j.Fragment,{children:[(0,j.jsx)(C,{value:o,options:f,onChange:e=>{T(e),M(e)},width:148}),(0,j.jsxs)(`button`,{type:`button`,className:`btn btn-primary btn-sm`,onClick:()=>i(`keys`),children:[(0,j.jsx)(n,{size:14}),`新建密钥`]})]})}),(0,j.jsx)(`div`,{className:`view-body stack`,children:N.initial&&N.loading?(0,j.jsx)(w,{}):N.error?(0,j.jsx)(_,{children:(0,j.jsx)(b,{kind:`error`,title:`概览数据没取到`,detail:x(N.error),onRetry:N.reload})}):P?(0,j.jsxs)(j.Fragment,{children:[P.alerts.channelReject.count>=P.alerts.channelReject.threshold?(0,j.jsxs)(m,{tone:`warn`,children:[(0,j.jsx)(a,{size:14,"aria-hidden":!0}),`最近 1 小时出现 `,(0,j.jsxs)(`b`,{children:[P.alerts.channelReject.count,` 次`]}),`上游渠道校验拒绝(11128): 请求的 system 提示命中了上游的第三方客户端指纹。本服务会自动改写模板行、被拒时降级重试, 连续失败说明出现了新的指纹变体。请到「请求日志」筛 note 含 upstream_11128 的行排查。`]}):null,P.alerts.credentialInvalid?.count!=null&&P.alerts.credentialInvalid.count>=P.alerts.credentialInvalid.threshold?(0,j.jsxs)(m,{tone:`error`,actions:(0,j.jsx)(`a`,{href:`#/clients`,className:`btn btn-quiet btn-sm`,children:`去提供商管理`}),children:[(0,j.jsx)(a,{size:14,"aria-hidden":!0}),`最近 1 小时出现 `,(0,j.jsxs)(`b`,{children:[P.alerts.credentialInvalid.count,` 次`]}),`上游访问密钥失效: 所有请求将以 502 失败,直到换新为止。`]}):null,(0,j.jsx)(O,{metrics:P.metrics}),(0,j.jsxs)(`div`,{className:`metric-row`,children:[(0,j.jsx)(y,{label:`已消耗积分`,value:p(P.metrics.creditsUsed),detail:P.metrics.creditsUnknownCount>0?`上游实扣 · 另 ${u(P.metrics.creditsUnknownCount)} 条上游未回报,未计入`:`上游实扣 · 全部请求均已回报`,tone:`amber`,icon:(0,j.jsx)(e,{size:14}),tip:z(`credits`),tipPos:`down`}),(0,j.jsx)(y,{label:`平均 RPM`,value:L===null?`—`:u(Math.round(L)),detail:`每分钟请求 · ${s[P.window]}`,tone:`violet`,icon:(0,j.jsx)(t,{size:14}),tip:z(`requests`),tipPos:`down`}),(0,j.jsx)(y,{label:`平均 TPM`,value:R===null?`—`:g(Math.round(R)),detail:`每分钟 tokens · ${s[P.window]}`,tone:`green`,icon:(0,j.jsx)(r,{size:14}),tip:z(`tokens`),tipPos:`down`})]}),(0,j.jsx)(_,{title:`提供商用量摘要`,aside:(0,j.jsxs)(v,{children:[P.byProvider.length,` 个提供商 · 按 Token 排序`]}),children:P.byProvider.length>0?(0,j.jsx)(`div`,{className:`tbl-scroll`,children:(0,j.jsxs)(`table`,{className:`tbl`,children:[(0,j.jsxs)(`caption`,{className:`sr-only`,children:[`提供商用量摘要,共 `,P.byProvider.length,` 个提供商`]}),(0,j.jsx)(`thead`,{children:(0,j.jsxs)(`tr`,{children:[(0,j.jsx)(`th`,{scope:`col`,children:`提供商`}),(0,j.jsx)(`th`,{scope:`col`,className:`r`,children:`请求次数`}),(0,j.jsx)(`th`,{scope:`col`,className:`r`,children:`Token 消耗`}),(0,j.jsx)(`th`,{scope:`col`,className:`r`,children:`消耗积分`}),(0,j.jsx)(`th`,{scope:`col`,className:`r`,children:`Token 占比`}),(0,j.jsx)(`th`,{scope:`col`,children:`分布`})]})}),(0,j.jsx)(`tbody`,{children:[...P.byProvider].sort((e,t)=>(t.tokens??0)-(e.tokens??0)).slice(0,6).map(e=>{let t=P&&P.metrics.totalTokens>0?(e.tokens??0)/P.metrics.totalTokens:null;return(0,j.jsxs)(`tr`,{children:[(0,j.jsx)(`td`,{className:`td-strong`,children:(0,j.jsx)(`span`,{children:e.provider??`未归属`})}),(0,j.jsx)(`td`,{className:`r td-mono`,children:u(e.requests)}),(0,j.jsx)(`td`,{className:`r td-mono`,children:g(e.tokens??0)}),(0,j.jsx)(`td`,{className:`r td-mono`,children:p(e.credits)}),(0,j.jsx)(`td`,{className:`r td-mono`,children:c(t)}),(0,j.jsx)(`td`,{children:(0,j.jsx)(`div`,{className:`ov-bar-track`,children:(0,j.jsx)(`div`,{className:`ov-bar-fill`,style:{width:`${Math.max(2,Math.round((t??0)*100))}%`}})})})]},e.providerId??`__unattributed__`)})})]})}):(0,j.jsxs)(`div`,{className:`empty-note`,style:{padding:`24px 0`},children:[s[P.window],`没有提供商消耗记录。`]})}),(0,j.jsxs)(_,{title:`模型用量摘要`,aside:(0,j.jsxs)(v,{children:[P.byModel.length,` 个模型 · 按 Token 排序`]}),children:[P.byModel.length>0?(0,j.jsx)(`div`,{className:`tbl-scroll`,children:(0,j.jsxs)(`table`,{className:`tbl`,children:[(0,j.jsxs)(`caption`,{className:`sr-only`,children:[`模型用量摘要,共 `,P.byModel.length,` 个模型`]}),(0,j.jsx)(`thead`,{children:(0,j.jsxs)(`tr`,{children:[(0,j.jsx)(`th`,{scope:`col`,children:`模型`}),(0,j.jsx)(`th`,{scope:`col`,className:`r`,children:`请求次数`}),(0,j.jsx)(`th`,{scope:`col`,className:`r`,children:`Token 消耗`}),(0,j.jsx)(`th`,{scope:`col`,className:`r`,children:`消耗积分`}),(0,j.jsx)(`th`,{scope:`col`,className:`r`,children:`Token 占比`}),(0,j.jsx)(`th`,{scope:`col`,children:`分布`})]})}),(0,j.jsx)(`tbody`,{children:[...P.byModel].sort((e,t)=>(t.tokens??0)-(e.tokens??0)).slice(0,8).map(e=>{let t=e.displayName??e.model??`未知`;return(0,j.jsxs)(`tr`,{children:[(0,j.jsx)(`td`,{className:`td-strong`,children:t}),(0,j.jsx)(`td`,{className:`r td-mono`,children:u(e.requests)}),(0,j.jsx)(`td`,{className:`r td-mono`,children:g(e.tokens??0)}),(0,j.jsx)(`td`,{className:`r td-mono`,children:p(e.credits)}),(0,j.jsx)(`td`,{className:`r td-mono`,children:c(e.share)}),(0,j.jsx)(`td`,{children:(0,j.jsx)(`div`,{className:`ov-bar-track`,children:(0,j.jsx)(`div`,{className:`ov-bar-fill`,style:{width:`${Math.max(2,Math.round((e.share??0)*100))}%`}})})})]},e.model??t)})})]})}):(0,j.jsxs)(`div`,{className:`empty-note`,style:{padding:`24px 0`},children:[s[P.window],`没有模型消耗记录。`]}),(0,j.jsx)(`div`,{className:`footer-note`,children:`这一页只留结论。详细构成去「积分与用量」,逐条请求去「请求日志」。`})]}),(0,j.jsx)(`div`,{className:`footer-note`,style:{marginTop:0},children:P.provenance.note})]}):null})]})}export{M as OverviewPage};
@@ -1,4 +1,4 @@
1
- import{B as e,C as t,D as n,G as r,K as i,M as a,N as o,R as s,V as c,W as l,X as u,Z as d,et as f,it as p,j as m,o as h,q as g,tt as _,u as ee}from"./vendor-befEYGHM.js";import{C as v,E as y,M as te,S as b,T as x,_ as ne,a as S,b as C,c as w,f as T,g as E,h as D,j as O,l as k,m as A,p as j,r as re,w as M}from"./index-nQeRK3kW.js";import{a as N,c as P,n as F,o as ie,r as I,s as ae,t as L}from"./Select-G6AhT0TA.js";import{i as oe}from"./PageSkeleton-DG-Dj4_9.js";import{t as se}from"./Drawer-CleQGhRU.js";import{t as ce}from"./useFx-xcrp_LHB.js";var R=p();function le(e,t=320){let[n,r]=(0,R.useState)(e);return(0,R.useEffect)(()=>{let n=window.setTimeout(()=>r(e),t);return()=>window.clearTimeout(n)},[e,t]),n}var z=_(),B=[20,50,100];function ue({page:e,limit:t,total:n,onPage:a,onLimit:o}){let s=Math.max(1,Math.ceil(n/t)),c=[],l=e=>{c[c.length-1]!==e&&c.push(e)},u=[1,e-1,e,e+1,s].filter(e=>e>=1&&e<=s).sort((e,t)=>e-t),d=0;return u.forEach(e=>{e-d>1&&l(`…`),l(e),d=e}),(0,z.jsxs)(`div`,{className:`pager`,children:[(0,z.jsxs)(`span`,{className:`txt`,children:[`第 `,e,` / `,s,` 页 · 每页 `,t,` 条,共 `,E(n),` 条`]}),(0,z.jsxs)(`span`,{className:`btns`,children:[(0,z.jsx)(L,{value:String(t),options:B.map(e=>({value:String(e),label:`${e} / 页`})),onChange:e=>o(Number(e)),size:`sm`,width:92,ariaLabel:`每页条数`}),(0,z.jsx)(`button`,{type:`button`,className:`pg`,disabled:e<=1,onClick:()=>a(e-1),"aria-label":`上一页`,children:(0,z.jsx)(r,{size:13})}),c.map((t,n)=>t===`…`?(0,z.jsx)(`span`,{className:`pg`,style:{cursor:`default`,background:`transparent`,border:`none`},children:`…`},`gap-${n}`):(0,z.jsx)(`button`,{type:`button`,className:`pg${t===e?` on`:``}`,onClick:()=>a(t),children:t},t)),(0,z.jsx)(`button`,{type:`button`,className:`pg`,disabled:e>=s,onClick:()=>a(e+1),"aria-label":`下一页`,children:(0,z.jsx)(i,{size:13})})]})]})}function V(e){let t=e.toLowerCase();return t.includes(`python`)||t.includes(`httpx`)||t.includes(`aiohttp`)?`python`:t.includes(`node`)||t.includes(`deno`)||t.includes(`bun`)||t.includes(`axios`)||t.includes(`undici`)?`node`:t.includes(`curl`)||t.includes(`wget`)||t.includes(`http`)?`terminal`:t.includes(`sdk`)?`sdk`:`cli`}var H=`M11.9 0C8.7 0 8.4 1.7 8.4 1.7v2.4h3.6v.7H5.3S2.4 4.5 2.4 8.4c0 3.8 2.5 3.7 2.5 3.7h1.5v-2.2s-.1-2.5 2.6-2.5h3.6s2.6 0 2.6-2.5V2.1S15.4 0 11.9 0zM9.3 1.5a.9.9 0 1 1 0 1.7.9.9 0 0 1 0-1.7zm6.3 3.4v2.3s.1 2.6-2.6 2.6H9.4s-2.5 0-2.5 2.5v4.4s-.2 2.7 4.8 2.7 4.7-2.3 4.7-2.3v-2.1h-3.6v-.7h6.7s3.2.3 3.2-3.7c0-4-2.8-3.8-2.8-3.8h-1.6v2.3s.1 2.6-2.6 2.6h-3.5s-2.4 0-2.4 2.4v4.1s-.4 2.4 4.4 2.4 4.5-2.1 4.5-2.1v-2h-3.4v-.7h6.6s3.4.4 3.4-3.9c0-4.3-2.9-4.1-2.9-4.1zM14.6 21.9a.9.9 0 1 1 0 1.8.9.9 0 0 1 0-1.8z`,U=`M12 1.5c-.3 0-.6.1-.9.3L3.4 6.4c-.5.3-.9.9-.9 1.5v8.2c0 .6.4 1.2.9 1.5l2 1.2c1 .5 1.8.1 1.8-1v-9c0-.7.5-1.2 1.2-1.2h7c.7 0 1.2.5 1.2 1.2v9c0 1.1.8 1.5 1.8 1l2-1.2c.5-.3.9-.9.9-1.5V7.9c0-.6-.4-1.2-.9-1.5L12.9 1.8c-.3-.2-.6-.3-.9-.3zm5.1 6c-.6 0-1.1.5-1.1 1.1v6.8c0 .6.5 1.1 1.1 1.1h5.2l-1.9 3.3 2.7-1.6c.5-.3.9-.9.9-1.5V7.9c0-.6-.4-1.2-.9-1.5l-7.7-4.6`,W=`M5 7l5 5-5 5m7 0h7`,G=`M14.7 6.3a5 5 0 0 0-6.9 6l-6.1 6.1a2 2 0 1 0 2.8 2.8l6.1-6.1a5 5 0 0 0 6-6.9l-3.2 3.2-2.8-2.8 3.1-3.1z`,K=`M8 6l-6 6 6 6m8-12l6 6-6 6`;function q({tool:e,size:t=14,style:n}){let r=e?V(e):`none`;if(r===`none`)return(0,z.jsxs)(`svg`,{width:t,height:t,viewBox:`0 0 24 24`,fill:`none`,stroke:`currentColor`,strokeWidth:`1.8`,strokeLinecap:`round`,strokeLinejoin:`round`,className:`ua-ico ${r}`,style:n,"aria-hidden":`true`,children:[(0,z.jsx)(`circle`,{cx:`12`,cy:`12`,r:`10`}),(0,z.jsx)(`path`,{d:`M2 12h20`}),(0,z.jsx)(`path`,{d:`M12 2a15.3 15.3 0 0 1 4 10 15.3 15.3 0 0 1-4 10 15.3 15.3 0 0 1-4-10 15.3 15.3 0 0 1 4-10z`})]});if(r===`python`||r===`node`){let e=r===`python`?H:U;return(0,z.jsx)(`svg`,{width:t,height:t,viewBox:`0 0 24 24`,fill:`currentColor`,className:`ua-ico ${r}`,style:n,"aria-hidden":`true`,children:(0,z.jsx)(`path`,{d:e})})}let i=r===`terminal`?W:r===`sdk`?G:K;return(0,z.jsx)(`svg`,{width:t,height:t,viewBox:`0 0 24 24`,fill:`none`,stroke:`currentColor`,strokeWidth:`1.8`,strokeLinecap:`round`,strokeLinejoin:`round`,className:`ua-ico ${r}`,style:n,"aria-hidden":`true`,children:(0,z.jsx)(`path`,{d:i})})}var J={live:`var(--text-tertiary)`,warn:`var(--warn-amber)`,fatal:`var(--danger-red)`,muted:`var(--text-faint)`},Y={live:`var(--signal-live)`,warn:`var(--warn-amber)`,fatal:`var(--danger-red)`,muted:`var(--text-faint)`};function X(e,t){if(!e)return!1;let n=e=>e.toLowerCase().replace(/[^a-z0-9]/g,``),r=n(e.trim().split(/[\s/]/)[0]??``);return r?t.split(/[\s.\-_/]+/).map(n).filter(e=>e.length>=3).some(e=>r.includes(e)):!1}function Z(e){let t=new Date(e);return Number.isNaN(t.getTime())?`--`:t.toLocaleDateString(`zh-CN`)}function de({rows:t,activeId:r,onOpen:l,resolveClientName:u,modelTagOf:d,providerOfModel:p}){return(0,z.jsx)(`div`,{className:`tbl-scroll`,children:(0,z.jsxs)(`table`,{className:`tbl`,children:[(0,z.jsxs)(`caption`,{className:`sr-only`,children:[`请求日志,共 `,t.length,` 条当前筛选结果`]}),(0,z.jsx)(`thead`,{children:(0,z.jsxs)(`tr`,{children:[(0,z.jsx)(`th`,{"aria-hidden":`true`}),(0,z.jsxs)(`th`,{scope:`col`,children:[(0,z.jsx)(c,{size:12}),`请求时间`]}),(0,z.jsxs)(`th`,{scope:`col`,children:[(0,z.jsx)(n,{size:12}),`令牌`]}),(0,z.jsxs)(`th`,{scope:`col`,children:[(0,z.jsx)(s,{size:12}),`模型 / 提供商`]}),(0,z.jsxs)(`th`,{scope:`col`,children:[(0,z.jsx)(m,{size:12}),`User Agent`]}),(0,z.jsxs)(`th`,{scope:`col`,className:`r`,children:[(0,z.jsx)(f,{size:12}),`状态`]}),(0,z.jsxs)(`th`,{scope:`col`,className:`r`,children:[(0,z.jsx)(h,{size:12}),`耗时`]}),(0,z.jsxs)(`th`,{scope:`col`,className:`r`,children:[(0,z.jsx)(o,{size:12}),`输出速度`]}),(0,z.jsxs)(`th`,{scope:`col`,className:`r`,children:[(0,z.jsx)(e,{size:12}),`Tokens`]}),(0,z.jsxs)(`th`,{scope:`col`,className:`r`,children:[(0,z.jsx)(a,{size:12}),`积分`]})]})}),(0,z.jsx)(`tbody`,{children:t.map(e=>{let t=x(e.status,e.note),n=v(e.note),a=e.modelDisplay||e.model;return(0,z.jsxs)(`tr`,{onClick:()=>l(e),className:r===e.id?`row-on`:void 0,style:{cursor:`pointer`,background:r===e.id?`var(--brand-tint)`:t===`fatal`?`color-mix(in srgb, var(--danger-red) 5%, transparent)`:void 0},children:[(0,z.jsx)(`td`,{className:`row-x-td`,children:(0,z.jsx)(`button`,{type:`button`,className:`row-open`,"aria-label":`打开 ${Z(e.ts)} ${T(e.ts)} 的请求详情`,onClick:t=>{t.stopPropagation(),l(e)},children:(0,z.jsx)(i,{size:14,className:`row-x`,"aria-hidden":`true`})})}),(0,z.jsxs)(`td`,{children:[(0,z.jsx)(`div`,{className:`cell-date`,children:Z(e.ts)}),(0,z.jsx)(`div`,{className:`td-mono`,style:{color:`var(--text-ghost)`},children:T(e.ts)})]}),(0,z.jsx)(`td`,{className:`td-mono`,style:{color:`var(--text-tertiary)`},children:(0,z.jsx)(S,{content:`密钥 ${e.keyHint}`,placement:`below`,children:(0,z.jsx)(`span`,{children:e.keyHint})})}),(0,z.jsxs)(`td`,{children:[(0,z.jsx)(`div`,{className:`td-strong`,children:a}),(0,z.jsxs)(`div`,{className:`model-meta`,children:[(0,z.jsx)(S,{content:`提供商:${p(e.model)??u(e)}(按模型目录归属解析)`,children:(0,z.jsx)(`span`,{className:`prov-pill`,children:p(e.model)??u(e)})}),d(e.model)?(0,z.jsx)(`span`,{className:`mu-tag`,children:d(e.model)}):null]})]}),(0,z.jsx)(`td`,{className:`td-ua`,children:e.ua?(0,z.jsx)(S,{content:e.ua,children:(0,z.jsxs)(`span`,{style:{display:`block`},children:[(0,z.jsxs)(`span`,{className:`ua-raw`,children:[(0,z.jsx)(q,{tool:e.tool,size:14,style:{marginRight:5,verticalAlign:-2}}),e.ua]}),e.tool&&!X(e.ua,e.tool)?(0,z.jsx)(`div`,{className:`ua-tool`,children:e.tool}):e.tool?null:(0,z.jsx)(`div`,{className:`ua-tool`,children:(0,z.jsx)(`span`,{style:{color:`var(--text-ghost)`},children:`未识别`})})]})}):(0,z.jsxs)(z.Fragment,{children:[(0,z.jsx)(`span`,{className:`ua-raw`,style:{color:`var(--text-ghost)`},children:`未采集`}),e.tool?(0,z.jsx)(`div`,{className:`ua-tool`,children:e.tool}):(0,z.jsx)(`div`,{className:`ua-tool`,children:(0,z.jsx)(`span`,{style:{color:`var(--text-ghost)`},children:`未识别`})})]})}),(0,z.jsx)(`td`,{className:`r td-mono`,style:{color:J[t]},children:n.length>0?(0,z.jsx)(S,{content:n.join(` · `),children:(0,z.jsxs)(`span`,{children:[(0,z.jsx)(`span`,{className:`dotc`,style:{background:Y[t]},"aria-hidden":`true`}),e.status]})}):(0,z.jsxs)(z.Fragment,{children:[(0,z.jsx)(`span`,{className:`dotc`,style:{background:Y[t]},"aria-hidden":`true`}),e.status]})}),(0,z.jsxs)(`td`,{className:`r td-mono`,children:[(0,z.jsx)(`div`,{children:(0,z.jsx)(S,{content:`首字耗时 —— 从发出请求到收到第一个内容块的等待
1
+ import{B as e,C as t,D as n,G as r,K as i,M as a,N as o,R as s,V as c,W as l,X as u,Z as d,et as f,it as p,j as m,o as h,q as g,tt as _,u as ee}from"./vendor-befEYGHM.js";import{C as v,E as y,M as te,S as b,T as x,_ as ne,a as S,b as C,c as w,f as T,g as E,h as D,j as O,l as k,m as A,p as j,r as re,w as M}from"./index-BcWmrhMD.js";import{a as N,c as P,n as F,o as ie,r as I,s as ae,t as L}from"./Select-Bfquh0d_.js";import{i as oe}from"./PageSkeleton-DG-Dj4_9.js";import{t as se}from"./Drawer-CleQGhRU.js";import{t as ce}from"./useFx-xcrp_LHB.js";var R=p();function le(e,t=320){let[n,r]=(0,R.useState)(e);return(0,R.useEffect)(()=>{let n=window.setTimeout(()=>r(e),t);return()=>window.clearTimeout(n)},[e,t]),n}var z=_(),B=[20,50,100];function ue({page:e,limit:t,total:n,onPage:a,onLimit:o}){let s=Math.max(1,Math.ceil(n/t)),c=[],l=e=>{c[c.length-1]!==e&&c.push(e)},u=[1,e-1,e,e+1,s].filter(e=>e>=1&&e<=s).sort((e,t)=>e-t),d=0;return u.forEach(e=>{e-d>1&&l(`…`),l(e),d=e}),(0,z.jsxs)(`div`,{className:`pager`,children:[(0,z.jsxs)(`span`,{className:`txt`,children:[`第 `,e,` / `,s,` 页 · 每页 `,t,` 条,共 `,E(n),` 条`]}),(0,z.jsxs)(`span`,{className:`btns`,children:[(0,z.jsx)(L,{value:String(t),options:B.map(e=>({value:String(e),label:`${e} / 页`})),onChange:e=>o(Number(e)),size:`sm`,width:92,ariaLabel:`每页条数`}),(0,z.jsx)(`button`,{type:`button`,className:`pg`,disabled:e<=1,onClick:()=>a(e-1),"aria-label":`上一页`,children:(0,z.jsx)(r,{size:13})}),c.map((t,n)=>t===`…`?(0,z.jsx)(`span`,{className:`pg`,style:{cursor:`default`,background:`transparent`,border:`none`},children:`…`},`gap-${n}`):(0,z.jsx)(`button`,{type:`button`,className:`pg${t===e?` on`:``}`,onClick:()=>a(t),children:t},t)),(0,z.jsx)(`button`,{type:`button`,className:`pg`,disabled:e>=s,onClick:()=>a(e+1),"aria-label":`下一页`,children:(0,z.jsx)(i,{size:13})})]})]})}function V(e){let t=e.toLowerCase();return t.includes(`python`)||t.includes(`httpx`)||t.includes(`aiohttp`)?`python`:t.includes(`node`)||t.includes(`deno`)||t.includes(`bun`)||t.includes(`axios`)||t.includes(`undici`)?`node`:t.includes(`curl`)||t.includes(`wget`)||t.includes(`http`)?`terminal`:t.includes(`sdk`)?`sdk`:`cli`}var H=`M11.9 0C8.7 0 8.4 1.7 8.4 1.7v2.4h3.6v.7H5.3S2.4 4.5 2.4 8.4c0 3.8 2.5 3.7 2.5 3.7h1.5v-2.2s-.1-2.5 2.6-2.5h3.6s2.6 0 2.6-2.5V2.1S15.4 0 11.9 0zM9.3 1.5a.9.9 0 1 1 0 1.7.9.9 0 0 1 0-1.7zm6.3 3.4v2.3s.1 2.6-2.6 2.6H9.4s-2.5 0-2.5 2.5v4.4s-.2 2.7 4.8 2.7 4.7-2.3 4.7-2.3v-2.1h-3.6v-.7h6.7s3.2.3 3.2-3.7c0-4-2.8-3.8-2.8-3.8h-1.6v2.3s.1 2.6-2.6 2.6h-3.5s-2.4 0-2.4 2.4v4.1s-.4 2.4 4.4 2.4 4.5-2.1 4.5-2.1v-2h-3.4v-.7h6.6s3.4.4 3.4-3.9c0-4.3-2.9-4.1-2.9-4.1zM14.6 21.9a.9.9 0 1 1 0 1.8.9.9 0 0 1 0-1.8z`,U=`M12 1.5c-.3 0-.6.1-.9.3L3.4 6.4c-.5.3-.9.9-.9 1.5v8.2c0 .6.4 1.2.9 1.5l2 1.2c1 .5 1.8.1 1.8-1v-9c0-.7.5-1.2 1.2-1.2h7c.7 0 1.2.5 1.2 1.2v9c0 1.1.8 1.5 1.8 1l2-1.2c.5-.3.9-.9.9-1.5V7.9c0-.6-.4-1.2-.9-1.5L12.9 1.8c-.3-.2-.6-.3-.9-.3zm5.1 6c-.6 0-1.1.5-1.1 1.1v6.8c0 .6.5 1.1 1.1 1.1h5.2l-1.9 3.3 2.7-1.6c.5-.3.9-.9.9-1.5V7.9c0-.6-.4-1.2-.9-1.5l-7.7-4.6`,W=`M5 7l5 5-5 5m7 0h7`,G=`M14.7 6.3a5 5 0 0 0-6.9 6l-6.1 6.1a2 2 0 1 0 2.8 2.8l6.1-6.1a5 5 0 0 0 6-6.9l-3.2 3.2-2.8-2.8 3.1-3.1z`,K=`M8 6l-6 6 6 6m8-12l6 6-6 6`;function q({tool:e,size:t=14,style:n}){let r=e?V(e):`none`;if(r===`none`)return(0,z.jsxs)(`svg`,{width:t,height:t,viewBox:`0 0 24 24`,fill:`none`,stroke:`currentColor`,strokeWidth:`1.8`,strokeLinecap:`round`,strokeLinejoin:`round`,className:`ua-ico ${r}`,style:n,"aria-hidden":`true`,children:[(0,z.jsx)(`circle`,{cx:`12`,cy:`12`,r:`10`}),(0,z.jsx)(`path`,{d:`M2 12h20`}),(0,z.jsx)(`path`,{d:`M12 2a15.3 15.3 0 0 1 4 10 15.3 15.3 0 0 1-4 10 15.3 15.3 0 0 1-4-10 15.3 15.3 0 0 1 4-10z`})]});if(r===`python`||r===`node`){let e=r===`python`?H:U;return(0,z.jsx)(`svg`,{width:t,height:t,viewBox:`0 0 24 24`,fill:`currentColor`,className:`ua-ico ${r}`,style:n,"aria-hidden":`true`,children:(0,z.jsx)(`path`,{d:e})})}let i=r===`terminal`?W:r===`sdk`?G:K;return(0,z.jsx)(`svg`,{width:t,height:t,viewBox:`0 0 24 24`,fill:`none`,stroke:`currentColor`,strokeWidth:`1.8`,strokeLinecap:`round`,strokeLinejoin:`round`,className:`ua-ico ${r}`,style:n,"aria-hidden":`true`,children:(0,z.jsx)(`path`,{d:i})})}var J={live:`var(--text-tertiary)`,warn:`var(--warn-amber)`,fatal:`var(--danger-red)`,muted:`var(--text-faint)`},Y={live:`var(--signal-live)`,warn:`var(--warn-amber)`,fatal:`var(--danger-red)`,muted:`var(--text-faint)`};function X(e,t){if(!e)return!1;let n=e=>e.toLowerCase().replace(/[^a-z0-9]/g,``),r=n(e.trim().split(/[\s/]/)[0]??``);return r?t.split(/[\s.\-_/]+/).map(n).filter(e=>e.length>=3).some(e=>r.includes(e)):!1}function Z(e){let t=new Date(e);return Number.isNaN(t.getTime())?`--`:t.toLocaleDateString(`zh-CN`)}function de({rows:t,activeId:r,onOpen:l,resolveClientName:u,modelTagOf:d,providerOfModel:p}){return(0,z.jsx)(`div`,{className:`tbl-scroll`,children:(0,z.jsxs)(`table`,{className:`tbl`,children:[(0,z.jsxs)(`caption`,{className:`sr-only`,children:[`请求日志,共 `,t.length,` 条当前筛选结果`]}),(0,z.jsx)(`thead`,{children:(0,z.jsxs)(`tr`,{children:[(0,z.jsx)(`th`,{"aria-hidden":`true`}),(0,z.jsxs)(`th`,{scope:`col`,children:[(0,z.jsx)(c,{size:12}),`请求时间`]}),(0,z.jsxs)(`th`,{scope:`col`,children:[(0,z.jsx)(n,{size:12}),`令牌`]}),(0,z.jsxs)(`th`,{scope:`col`,children:[(0,z.jsx)(s,{size:12}),`模型 / 提供商`]}),(0,z.jsxs)(`th`,{scope:`col`,children:[(0,z.jsx)(m,{size:12}),`User Agent`]}),(0,z.jsxs)(`th`,{scope:`col`,className:`r`,children:[(0,z.jsx)(f,{size:12}),`状态`]}),(0,z.jsxs)(`th`,{scope:`col`,className:`r`,children:[(0,z.jsx)(h,{size:12}),`耗时`]}),(0,z.jsxs)(`th`,{scope:`col`,className:`r`,children:[(0,z.jsx)(o,{size:12}),`输出速度`]}),(0,z.jsxs)(`th`,{scope:`col`,className:`r`,children:[(0,z.jsx)(e,{size:12}),`Tokens`]}),(0,z.jsxs)(`th`,{scope:`col`,className:`r`,children:[(0,z.jsx)(a,{size:12}),`积分`]})]})}),(0,z.jsx)(`tbody`,{children:t.map(e=>{let t=x(e.status,e.note),n=v(e.note),a=e.modelDisplay||e.model;return(0,z.jsxs)(`tr`,{onClick:()=>l(e),className:r===e.id?`row-on`:void 0,style:{cursor:`pointer`,background:r===e.id?`var(--brand-tint)`:t===`fatal`?`color-mix(in srgb, var(--danger-red) 5%, transparent)`:void 0},children:[(0,z.jsx)(`td`,{className:`row-x-td`,children:(0,z.jsx)(`button`,{type:`button`,className:`row-open`,"aria-label":`打开 ${Z(e.ts)} ${T(e.ts)} 的请求详情`,onClick:t=>{t.stopPropagation(),l(e)},children:(0,z.jsx)(i,{size:14,className:`row-x`,"aria-hidden":`true`})})}),(0,z.jsxs)(`td`,{children:[(0,z.jsx)(`div`,{className:`cell-date`,children:Z(e.ts)}),(0,z.jsx)(`div`,{className:`td-mono`,style:{color:`var(--text-ghost)`},children:T(e.ts)})]}),(0,z.jsx)(`td`,{className:`td-mono`,style:{color:`var(--text-tertiary)`},children:(0,z.jsx)(S,{content:`密钥 ${e.keyHint}`,placement:`below`,children:(0,z.jsx)(`span`,{children:e.keyHint})})}),(0,z.jsxs)(`td`,{children:[(0,z.jsx)(`div`,{className:`td-strong`,children:a}),(0,z.jsxs)(`div`,{className:`model-meta`,children:[(0,z.jsx)(S,{content:`提供商:${p(e.model)??u(e)}(按模型目录归属解析)`,children:(0,z.jsx)(`span`,{className:`prov-pill`,children:p(e.model)??u(e)})}),d(e.model)?(0,z.jsx)(`span`,{className:`mu-tag`,children:d(e.model)}):null]})]}),(0,z.jsx)(`td`,{className:`td-ua`,children:e.ua?(0,z.jsx)(S,{content:e.ua,children:(0,z.jsxs)(`span`,{style:{display:`block`},children:[(0,z.jsxs)(`span`,{className:`ua-raw`,children:[(0,z.jsx)(q,{tool:e.tool,size:14,style:{marginRight:5,verticalAlign:-2}}),e.ua]}),e.tool&&!X(e.ua,e.tool)?(0,z.jsx)(`div`,{className:`ua-tool`,children:e.tool}):e.tool?null:(0,z.jsx)(`div`,{className:`ua-tool`,children:(0,z.jsx)(`span`,{style:{color:`var(--text-ghost)`},children:`未识别`})})]})}):(0,z.jsxs)(z.Fragment,{children:[(0,z.jsx)(`span`,{className:`ua-raw`,style:{color:`var(--text-ghost)`},children:`未采集`}),e.tool?(0,z.jsx)(`div`,{className:`ua-tool`,children:e.tool}):(0,z.jsx)(`div`,{className:`ua-tool`,children:(0,z.jsx)(`span`,{style:{color:`var(--text-ghost)`},children:`未识别`})})]})}),(0,z.jsx)(`td`,{className:`r td-mono`,style:{color:J[t]},children:n.length>0?(0,z.jsx)(S,{content:n.join(` · `),children:(0,z.jsxs)(`span`,{children:[(0,z.jsx)(`span`,{className:`dotc`,style:{background:Y[t]},"aria-hidden":`true`}),e.status]})}):(0,z.jsxs)(z.Fragment,{children:[(0,z.jsx)(`span`,{className:`dotc`,style:{background:Y[t]},"aria-hidden":`true`}),e.status]})}),(0,z.jsxs)(`td`,{className:`r td-mono`,children:[(0,z.jsx)(`div`,{children:(0,z.jsx)(S,{content:`首字耗时 —— 从发出请求到收到第一个内容块的等待
2
2
  (含上游排队与思考时间;失败行没有首字)`,children:(0,z.jsx)(`span`,{className:`cell-sub`,children:e.firstByteMs===null?`无首字`:`首字 ${D(e.firstByteMs)}`})})}),(0,z.jsx)(`div`,{children:(0,z.jsx)(S,{content:`总耗时 —— 从发出请求到流结束`,children:(0,z.jsxs)(`span`,{children:[`耗时 `,D(e.ms)]})})})]}),(0,z.jsx)(`td`,{className:`r td-mono`,children:(0,z.jsx)(S,{content:`输出速度 = 输出 tokens ÷ 生成时长(总耗时 − 首字)
3
3
  上游不回报生成时长,此值由本服务按两端观测推算;
4
4
  失败行或首字即结束的请求没有生成过程,显示 --`,children:(0,z.jsx)(`span`,{children:C(M(e.completionTokens,e.ms,e.firstByteMs))})})}),(0,z.jsxs)(`td`,{className:`r td-mono`,children:[(0,z.jsx)(`div`,{children:(0,z.jsx)(S,{content:`输入 ${E(e.promptTokens)} tokens / 输出 ${E(e.completionTokens)} tokens`,children:(0,z.jsxs)(`span`,{children:[E(e.promptTokens),`/`,E(e.completionTokens)]})})}),e.cachedTokens>0?(0,z.jsx)(`div`,{children:(0,z.jsx)(S,{content:`输入中命中缓存 ${E(e.cachedTokens)} tokens\n上游按缓存价计费(已体现在积分里)`,children:(0,z.jsxs)(`span`,{className:`cell-cached`,children:[`+`,E(e.cachedTokens)]})})}):null]}),(0,z.jsx)(`td`,{className:`r td-mono`,children:e.credits===null?(0,z.jsx)(S,{content:`上游未回报该次费用(未知)
@@ -1 +1 @@
1
- import{J as e,S as t,it as n,k as r,m as i,q as a,r as o,rt as s,tt as c}from"./vendor-befEYGHM.js";import{a as l}from"./index-nQeRK3kW.js";var u=c();function d({tone:e=`ghost`,dot:t=!1,children:n}){return(0,u.jsxs)(`span`,{className:`pill pill-${e}`,children:[t?(0,u.jsx)(`span`,{className:`dot dot-live`}):null,n]})}function f({tone:e=`off`,children:t}){return(0,u.jsx)(`span`,{className:`tag tag-${e}`,children:t})}function p({title:e,status:t,actions:n}){return(0,u.jsxs)(`div`,{className:`topbar`,children:[(0,u.jsxs)(`div`,{className:`topbar-left`,children:[(0,u.jsx)(`h1`,{children:e}),t]}),n?(0,u.jsx)(`div`,{className:`topbar-right`,children:n}):null]})}function m({title:e,aside:t,children:n,className:r=``,padded:i=!0}){return(0,u.jsxs)(`div`,{className:`card${i?` panel`:``} ${r}`.trim(),children:[e?(0,u.jsxs)(`div`,{className:`panel-head`,style:i?void 0:{padding:`18px 20px 0`,marginBottom:12},children:[(0,u.jsx)(`h3`,{children:e}),t]}):null,n]})}function h({items:e}){return(0,u.jsx)(`div`,{className:`statbar`,"data-count":e.length,children:e.map(e=>(0,u.jsxs)(`div`,{children:[(0,u.jsxs)(`div`,{className:`sb-top`,children:[(0,u.jsx)(`span`,{className:`lb`,children:e.label}),e.detail?(0,u.jsx)(`span`,{className:`sdl`,children:e.detail}):null]}),e.tip?(0,u.jsx)(l,{content:e.tip,placement:e.tipPos===`down`?`below`:`auto`,className:`tooltip-value-anchor`,children:(0,u.jsx)(`div`,{className:`vl`,style:e.tone===`live`?{color:`var(--signal-live)`}:e.tone===`amber`?{color:`var(--warn-amber)`}:void 0,children:e.value})}):(0,u.jsx)(`div`,{className:`vl`,style:e.tone===`live`?{color:`var(--signal-live)`}:e.tone===`amber`?{color:`var(--warn-amber)`}:void 0,children:e.value})]},e.label))})}function g({label:e,value:t,detail:n,tone:r,icon:i,tip:a,tipPos:o}){let s=r===`cyan`||r===`violet`||r===`green`||r===`amber`||r===`blue`||r===`rose`?` m-${r}`:``;return(0,u.jsxs)(`div`,{className:`card metric`,children:[(0,u.jsxs)(`div`,{className:`m-top`,children:[i?(0,u.jsx)(`span`,{className:`m-ico${s}`,"aria-hidden":`true`,children:i}):null,(0,u.jsx)(`span`,{className:`lb`,children:e})]}),a?(0,u.jsx)(l,{content:a,placement:o===`down`?`below`:`auto`,className:`tooltip-value-anchor`,children:(0,u.jsx)(`div`,{className:`vl`,children:t})}):(0,u.jsx)(`div`,{className:`vl`,children:t}),n?(0,u.jsx)(`div`,{className:`dl${r===`up`?` up`:r===`warn`?` warn`:``}`,children:n}):null]})}function _({kind:e,title:n,detail:a,onRetry:s,children:c}){return e===`loading`?(0,u.jsxs)(`div`,{className:`state-block`,role:`status`,"aria-live":`polite`,"aria-busy":`true`,children:[(0,u.jsx)(t,{size:22,className:`spin`,style:{animation:`spin 1s linear infinite`}}),(0,u.jsx)(`div`,{className:`t`,children:n??`加载中…`})]}):e===`empty`?(0,u.jsxs)(`div`,{className:`state-block`,role:`status`,"aria-live":`polite`,children:[(0,u.jsx)(r,{size:26}),(0,u.jsx)(`div`,{className:`t`,children:n??`暂无数据`}),a?(0,u.jsx)(`div`,{className:`d`,children:a}):null,c]}):(0,u.jsxs)(`div`,{className:`state-block`,role:`alert`,"aria-live":`assertive`,children:[(0,u.jsx)(o,{size:26}),(0,u.jsx)(`div`,{className:`t`,children:n??`加载失败`}),a?(0,u.jsx)(`div`,{className:`d`,children:a}):null,s?(0,u.jsxs)(`button`,{type:`button`,className:`btn btn-quiet btn-sm`,onClick:s,children:[(0,u.jsx)(i,{size:14}),`重试`]}):null]})}function v(e){if(!e)return``;let t={40001:`有字段没通过校验,回退一步检查刚填的内容。`,40002:`确认文字不匹配 —— 这是刻意设计的门槛。`,40101:`管理口令不正确,注意区分大小写。`,40102:`会话已过期,登录后继续。`,40290:`登录失败次数过多,请 ${e.retryAfterSeconds?Math.ceil(e.retryAfterSeconds/60):10} 分钟后重试。`,40301:`请求来源校验失败(CSRF 防护),刷新页面重试。`,40401:`这条记录已不存在,可能刚被删掉了。`,40901:`同名密钥已存在,换一个名字。`,50001:`服务端未分类异常,可稍后重试或查看服务日志。`,50301:`数据库暂时不可用,确认后端进程是否在运行。`};return(e.code===40001||e.code===50001)&&/[\u4e00-\u9fa5]/.test(e.message)?e.message:t[e.code]?t[e.code]:e.status===0?e.message:e.message||`请求失败(HTTP ${e.status})`}var y=n(),b=s();function x({value:t,options:n,onChange:r,width:i,disabled:o,size:s=`md`,ariaLabel:c}){let[l,d]=(0,y.useState)(!1),[f,p]=(0,y.useState)(0),[m,h]=(0,y.useState)(null),[g,_]=(0,y.useState)(!1),v=(0,y.useRef)(null),x=(0,y.useRef)(null),S=(0,y.useRef)({buf:``,at:0}),C=(0,y.useId)(),w=`${C}list`,T=e=>`${C}opt${e}`,E=Math.max(0,n.findIndex(e=>e.value===t)),D=(0,y.useCallback)(()=>{let e=v.current;if(!e)return;let t=e.getBoundingClientRect();h({left:t.left,top:t.top,bottom:t.bottom,width:t.width})},[]),O=(0,y.useCallback)(()=>{o||n.length===0||(S.current={buf:``,at:0},p(E),D(),d(!0))},[o,D,n.length,E]),k=(0,y.useCallback)(e=>{let t=n[e];t&&r(t.value),d(!1),v.current?.focus()},[r,n]);(0,y.useLayoutEffect)(()=>{l&&x.current?.focus()},[l]),(0,y.useLayoutEffect)(()=>{if(!l||!m)return;let e=x.current;if(!e)return;let t=window.innerHeight-m.bottom;_(t<e.offsetHeight+12&&m.top>t)},[l,m,n.length]),(0,y.useEffect)(()=>{l&&x.current?.querySelector(`[data-opt="${f}"]`)?.scrollIntoView({block:`nearest`})},[f,l]),(0,y.useEffect)(()=>{if(!l)return;let e=()=>D(),t=e=>{let t=e.target;t&&(v.current?.contains(t)||x.current?.contains(t))||d(!1)};return window.addEventListener(`scroll`,e,!0),window.addEventListener(`resize`,e),document.addEventListener(`pointerdown`,t,!0),()=>{window.removeEventListener(`scroll`,e,!0),window.removeEventListener(`resize`,e),document.removeEventListener(`pointerdown`,t,!0)}},[l,D]);let A=(0,y.useCallback)((e,t)=>{let r=Date.now(),i=(r-S.current.at>700?``:S.current.buf)+e;S.current={buf:i,at:r};let a=i.toLowerCase(),o=n.length,s=i.length===1?(t+1)%o:0;for(let e=0;e<o;e+=1){let t=(s+e)%o;if(n[t].label.toLowerCase().startsWith(a)){p(t);return}}},[n]),j=e=>e.key.length===1&&!e.ctrlKey&&!e.metaKey&&!e.altKey&&/\S/.test(e.key),M=e=>{if(!(o||l)){if(e.key===`ArrowDown`||e.key===`ArrowUp`||e.key===`Enter`||e.key===` `){e.preventDefault(),O();return}j(e)&&(e.preventDefault(),O(),A(e.key,E))}},N=e=>{let t=n.length;switch(e.key){case`ArrowDown`:e.preventDefault(),p(e=>(e+1)%t);break;case`ArrowUp`:e.preventDefault(),p(e=>(e-1+t)%t);break;case`Home`:e.preventDefault(),p(0);break;case`End`:e.preventDefault(),p(t-1);break;case`Enter`:case` `:e.preventDefault(),k(f);break;case`Escape`:e.preventDefault(),e.stopPropagation(),d(!1),v.current?.focus();break;case`Tab`:d(!1),v.current?.focus();break;default:j(e)&&A(e.key,f)}},P=n[E]?.label??``;return(0,u.jsxs)(`div`,{className:`sel-field`,style:i?{width:i}:void 0,children:[(0,u.jsxs)(`button`,{type:`button`,ref:v,className:s===`sm`?`sel sm`:`sel`,"aria-haspopup":`listbox`,"aria-expanded":l,"aria-controls":l?w:void 0,"aria-label":c,"data-value":t,disabled:o,onClick:()=>l?d(!1):O(),onKeyDown:M,children:[(0,u.jsx)(`span`,{className:`sel-val`,children:P}),(0,u.jsx)(a,{size:s===`sm`?12:13,className:`ic caret-glyph`,"aria-hidden":!0})]}),l&&m?(0,b.createPortal)((0,u.jsx)(`div`,{ref:x,id:w,role:`listbox`,tabIndex:-1,"aria-activedescendant":n.length?T(f):void 0,className:s===`sm`?`sel-pop sm`:`sel-pop`,onKeyDown:N,style:{left:Math.max(8,Math.min(m.left,window.innerWidth-Math.max(m.width,168)-8)),top:g?void 0:m.bottom+6,bottom:g?window.innerHeight-m.top+6:void 0,minWidth:m.width},children:n.map((n,r)=>(0,u.jsxs)(`div`,{id:T(r),"data-opt":r,"data-value":n.value,role:`option`,"aria-selected":n.value===t,className:`sel-opt${r===f?` on`:``}${n.value===t?` picked`:``}`,onMouseEnter:()=>p(r),onPointerDown:e=>e.preventDefault(),onClick:()=>k(r),children:[(0,u.jsx)(`span`,{className:`sel-opt-lb`,children:n.label}),n.value===t?(0,u.jsx)(e,{size:13,className:`ic`,"aria-hidden":!0}):null]},n.value))}),document.body):null]})}export{m as a,d as c,g as i,f as l,_ as n,h as o,v as r,p as s,x as t};
1
+ import{J as e,S as t,it as n,k as r,m as i,q as a,r as o,rt as s,tt as c}from"./vendor-befEYGHM.js";import{a as l}from"./index-BcWmrhMD.js";var u=c();function d({tone:e=`ghost`,dot:t=!1,children:n}){return(0,u.jsxs)(`span`,{className:`pill pill-${e}`,children:[t?(0,u.jsx)(`span`,{className:`dot dot-live`}):null,n]})}function f({tone:e=`off`,children:t}){return(0,u.jsx)(`span`,{className:`tag tag-${e}`,children:t})}function p({title:e,status:t,actions:n}){return(0,u.jsxs)(`div`,{className:`topbar`,children:[(0,u.jsxs)(`div`,{className:`topbar-left`,children:[(0,u.jsx)(`h1`,{children:e}),t]}),n?(0,u.jsx)(`div`,{className:`topbar-right`,children:n}):null]})}function m({title:e,aside:t,children:n,className:r=``,padded:i=!0}){return(0,u.jsxs)(`div`,{className:`card${i?` panel`:``} ${r}`.trim(),children:[e?(0,u.jsxs)(`div`,{className:`panel-head`,style:i?void 0:{padding:`18px 20px 0`,marginBottom:12},children:[(0,u.jsx)(`h3`,{children:e}),t]}):null,n]})}function h({items:e}){return(0,u.jsx)(`div`,{className:`statbar`,"data-count":e.length,children:e.map(e=>(0,u.jsxs)(`div`,{children:[(0,u.jsxs)(`div`,{className:`sb-top`,children:[(0,u.jsx)(`span`,{className:`lb`,children:e.label}),e.detail?(0,u.jsx)(`span`,{className:`sdl`,children:e.detail}):null]}),e.tip?(0,u.jsx)(l,{content:e.tip,placement:e.tipPos===`down`?`below`:`auto`,className:`tooltip-value-anchor`,children:(0,u.jsx)(`div`,{className:`vl`,style:e.tone===`live`?{color:`var(--signal-live)`}:e.tone===`amber`?{color:`var(--warn-amber)`}:void 0,children:e.value})}):(0,u.jsx)(`div`,{className:`vl`,style:e.tone===`live`?{color:`var(--signal-live)`}:e.tone===`amber`?{color:`var(--warn-amber)`}:void 0,children:e.value})]},e.label))})}function g({label:e,value:t,detail:n,tone:r,icon:i,tip:a,tipPos:o}){let s=r===`cyan`||r===`violet`||r===`green`||r===`amber`||r===`blue`||r===`rose`?` m-${r}`:``;return(0,u.jsxs)(`div`,{className:`card metric`,children:[(0,u.jsxs)(`div`,{className:`m-top`,children:[i?(0,u.jsx)(`span`,{className:`m-ico${s}`,"aria-hidden":`true`,children:i}):null,(0,u.jsx)(`span`,{className:`lb`,children:e})]}),a?(0,u.jsx)(l,{content:a,placement:o===`down`?`below`:`auto`,className:`tooltip-value-anchor`,children:(0,u.jsx)(`div`,{className:`vl`,children:t})}):(0,u.jsx)(`div`,{className:`vl`,children:t}),n?(0,u.jsx)(`div`,{className:`dl${r===`up`?` up`:r===`warn`?` warn`:``}`,children:n}):null]})}function _({kind:e,title:n,detail:a,onRetry:s,children:c}){return e===`loading`?(0,u.jsxs)(`div`,{className:`state-block`,role:`status`,"aria-live":`polite`,"aria-busy":`true`,children:[(0,u.jsx)(t,{size:22,className:`spin`,style:{animation:`spin 1s linear infinite`}}),(0,u.jsx)(`div`,{className:`t`,children:n??`加载中…`})]}):e===`empty`?(0,u.jsxs)(`div`,{className:`state-block`,role:`status`,"aria-live":`polite`,children:[(0,u.jsx)(r,{size:26}),(0,u.jsx)(`div`,{className:`t`,children:n??`暂无数据`}),a?(0,u.jsx)(`div`,{className:`d`,children:a}):null,c]}):(0,u.jsxs)(`div`,{className:`state-block`,role:`alert`,"aria-live":`assertive`,children:[(0,u.jsx)(o,{size:26}),(0,u.jsx)(`div`,{className:`t`,children:n??`加载失败`}),a?(0,u.jsx)(`div`,{className:`d`,children:a}):null,s?(0,u.jsxs)(`button`,{type:`button`,className:`btn btn-quiet btn-sm`,onClick:s,children:[(0,u.jsx)(i,{size:14}),`重试`]}):null]})}function v(e){if(!e)return``;let t={40001:`有字段没通过校验,回退一步检查刚填的内容。`,40002:`确认文字不匹配 —— 这是刻意设计的门槛。`,40101:`管理口令不正确,注意区分大小写。`,40102:`会话已过期,登录后继续。`,40290:`登录失败次数过多,请 ${e.retryAfterSeconds?Math.ceil(e.retryAfterSeconds/60):10} 分钟后重试。`,40301:`请求来源校验失败(CSRF 防护),刷新页面重试。`,40401:`这条记录已不存在,可能刚被删掉了。`,40901:`同名密钥已存在,换一个名字。`,50001:`服务端未分类异常,可稍后重试或查看服务日志。`,50301:`数据库暂时不可用,确认后端进程是否在运行。`};return(e.code===40001||e.code===50001)&&/[\u4e00-\u9fa5]/.test(e.message)?e.message:t[e.code]?t[e.code]:e.status===0?e.message:e.message||`请求失败(HTTP ${e.status})`}var y=n(),b=s();function x({value:t,options:n,onChange:r,width:i,disabled:o,size:s=`md`,ariaLabel:c}){let[l,d]=(0,y.useState)(!1),[f,p]=(0,y.useState)(0),[m,h]=(0,y.useState)(null),[g,_]=(0,y.useState)(!1),v=(0,y.useRef)(null),x=(0,y.useRef)(null),S=(0,y.useRef)({buf:``,at:0}),C=(0,y.useId)(),w=`${C}list`,T=e=>`${C}opt${e}`,E=Math.max(0,n.findIndex(e=>e.value===t)),D=(0,y.useCallback)(()=>{let e=v.current;if(!e)return;let t=e.getBoundingClientRect();h({left:t.left,top:t.top,bottom:t.bottom,width:t.width})},[]),O=(0,y.useCallback)(()=>{o||n.length===0||(S.current={buf:``,at:0},p(E),D(),d(!0))},[o,D,n.length,E]),k=(0,y.useCallback)(e=>{let t=n[e];t&&r(t.value),d(!1),v.current?.focus()},[r,n]);(0,y.useLayoutEffect)(()=>{l&&x.current?.focus()},[l]),(0,y.useLayoutEffect)(()=>{if(!l||!m)return;let e=x.current;if(!e)return;let t=window.innerHeight-m.bottom;_(t<e.offsetHeight+12&&m.top>t)},[l,m,n.length]),(0,y.useEffect)(()=>{l&&x.current?.querySelector(`[data-opt="${f}"]`)?.scrollIntoView({block:`nearest`})},[f,l]),(0,y.useEffect)(()=>{if(!l)return;let e=()=>D(),t=e=>{let t=e.target;t&&(v.current?.contains(t)||x.current?.contains(t))||d(!1)};return window.addEventListener(`scroll`,e,!0),window.addEventListener(`resize`,e),document.addEventListener(`pointerdown`,t,!0),()=>{window.removeEventListener(`scroll`,e,!0),window.removeEventListener(`resize`,e),document.removeEventListener(`pointerdown`,t,!0)}},[l,D]);let A=(0,y.useCallback)((e,t)=>{let r=Date.now(),i=(r-S.current.at>700?``:S.current.buf)+e;S.current={buf:i,at:r};let a=i.toLowerCase(),o=n.length,s=i.length===1?(t+1)%o:0;for(let e=0;e<o;e+=1){let t=(s+e)%o;if(n[t].label.toLowerCase().startsWith(a)){p(t);return}}},[n]),j=e=>e.key.length===1&&!e.ctrlKey&&!e.metaKey&&!e.altKey&&/\S/.test(e.key),M=e=>{if(!(o||l)){if(e.key===`ArrowDown`||e.key===`ArrowUp`||e.key===`Enter`||e.key===` `){e.preventDefault(),O();return}j(e)&&(e.preventDefault(),O(),A(e.key,E))}},N=e=>{let t=n.length;switch(e.key){case`ArrowDown`:e.preventDefault(),p(e=>(e+1)%t);break;case`ArrowUp`:e.preventDefault(),p(e=>(e-1+t)%t);break;case`Home`:e.preventDefault(),p(0);break;case`End`:e.preventDefault(),p(t-1);break;case`Enter`:case` `:e.preventDefault(),k(f);break;case`Escape`:e.preventDefault(),e.stopPropagation(),d(!1),v.current?.focus();break;case`Tab`:d(!1),v.current?.focus();break;default:j(e)&&A(e.key,f)}},P=n[E]?.label??``;return(0,u.jsxs)(`div`,{className:`sel-field`,style:i?{width:i}:void 0,children:[(0,u.jsxs)(`button`,{type:`button`,ref:v,className:s===`sm`?`sel sm`:`sel`,"aria-haspopup":`listbox`,"aria-expanded":l,"aria-controls":l?w:void 0,"aria-label":c,"data-value":t,disabled:o,onClick:()=>l?d(!1):O(),onKeyDown:M,children:[(0,u.jsx)(`span`,{className:`sel-val`,children:P}),(0,u.jsx)(a,{size:s===`sm`?12:13,className:`ic caret-glyph`,"aria-hidden":!0})]}),l&&m?(0,b.createPortal)((0,u.jsx)(`div`,{ref:x,id:w,role:`listbox`,tabIndex:-1,"aria-activedescendant":n.length?T(f):void 0,className:s===`sm`?`sel-pop sm`:`sel-pop`,onKeyDown:N,style:{left:Math.max(8,Math.min(m.left,window.innerWidth-Math.max(m.width,168)-8)),top:g?void 0:m.bottom+6,bottom:g?window.innerHeight-m.top+6:void 0,minWidth:m.width},children:n.map((n,r)=>(0,u.jsxs)(`div`,{id:T(r),"data-opt":r,"data-value":n.value,role:`option`,"aria-selected":n.value===t,className:`sel-opt${r===f?` on`:``}${n.value===t?` picked`:``}`,onMouseEnter:()=>p(r),onPointerDown:e=>e.preventDefault(),onClick:()=>k(r),children:[(0,u.jsx)(`span`,{className:`sel-opt-lb`,children:n.label}),n.value===t?(0,u.jsx)(e,{size:13,className:`ic`,"aria-hidden":!0}):null]},n.value))}),document.body):null]})}export{m as a,d as c,g as i,f as l,_ as n,h as o,v as r,p as s,x as t};
@@ -1,5 +1,5 @@
1
- import{D as e,J as t,S as n,f as r,it as i,l as a,p as o,tt as s,w as c,z as l}from"./vendor-befEYGHM.js";import{M as u,a as d,c as f,g as p,j as m,p as h,r as g}from"./index-nQeRK3kW.js";import{t as _}from"./accessUrl-DbL5DLDz.js";import{a as v,c as y,l as b,n as x,r as S,s as C,t as w}from"./Select-G6AhT0TA.js";import{t as T}from"./Modal-B-rIrvXS.js";import{t as E}from"./Drawer-CleQGhRU.js";import{t as D}from"./Switch-0KA1AbiV.js";var O=i(),k=s();function A({item:e,value:t,disabled:n,onChange:r}){if(e.type===`switch`)return(0,k.jsx)(D,{checked:!!t,disabled:n||e.readonly,label:e.label,onChange:e=>r(e)});if(e.type===`badge`)return(0,k.jsx)(b,{tone:`live`,children:String(t)});if(e.type===`select`){let i=(e.options??[]).map(e=>({value:e.value,label:e.label}));return(0,k.jsx)(w,{value:String(t),options:i,disabled:n||e.readonly,onChange:e=>r(e),width:188})}return e.type===`number`?(0,k.jsx)(`input`,{className:`field-input num`,type:`number`,value:t==null?``:String(t),disabled:n||e.readonly,onChange:e=>r(e.target.value===``?``:Number(e.target.value)),"aria-label":e.label}):e.type===`mapping`?null:(0,k.jsx)(`input`,{className:`field-input text`,value:t==null?``:String(t),disabled:n||e.readonly,onChange:e=>r(e.target.value),"aria-label":e.label})}function j(){let e=_(),[n,r]=(0,O.useState)(!1),i=async()=>{try{await navigator.clipboard.writeText(e),r(!0),window.setTimeout(()=>r(!1),1200)}catch{}};return(0,k.jsxs)(`div`,{className:`card access-card`,children:[(0,k.jsxs)(`div`,{className:`access-head`,children:[(0,k.jsxs)(`span`,{className:`access-title`,children:[(0,k.jsx)(c,{size:13,"aria-hidden":!0}),`接入地址`]}),(0,k.jsx)(`span`,{className:`access-sub`,children:`客户端与 API 同源 —— 这就是你当前访问控制台的地址`})]}),(0,k.jsxs)(`div`,{className:`key-plain access-url`,children:[(0,k.jsx)(`code`,{children:e}),(0,k.jsxs)(`button`,{type:`button`,className:`copy`,"aria-label":n?`已复制接入地址`:`复制接入地址`,onClick:()=>void i(),children:[n?(0,k.jsx)(t,{size:13}):(0,k.jsx)(l,{size:13}),n?`已复制`:`复制`]})]}),(0,k.jsxs)(`p`,{className:`chain-note`,children:[`客户端里要填两组值:`,(0,k.jsx)(`b`,{children:`base_url`}),` 就是上面这串;`,(0,k.jsx)(`b`,{children:`API Key`}),` 用你在本页`,(0,k.jsx)(`b`,{children:`新建的那把`}),(0,k.jsx)(`span`,{className:`code-chip`,children:`sk-waygate-…`}),`(明文只在创建时显示一次,丢了只能删掉重建)。`]}),(0,k.jsxs)(`div`,{className:`cred-note access-cert`,children:[(0,k.jsx)(a,{size:14,"aria-hidden":!0}),(0,k.jsxs)(`span`,{children:[`本服务的 TLS 是`,(0,k.jsx)(`b`,{children:`自签证书`}),`:客户端得先信任它的根证书,否则会以「证书错误」失败 —— 那`,(0,k.jsx)(`b`,{children:`不是`}),`地址填错。把根证书装进系统信任库,或让客户端通过`,(0,k.jsx)(`span`,{className:`code-chip`,children:`NODE_EXTRA_CA_CERTS`}),` /`,(0,k.jsx)(`span`,{className:`code-chip`,children:`SSL_CERT_FILE`}),`指向随部署产出的`,(0,k.jsx)(`span`,{className:`code-chip`,children:`relay-ca.crt`}),`。`]})]})]})}var M=8,N=128;function P({onClose:r,onDone:i}){let[o,s]=(0,O.useState)(`reset`),[c,d]=(0,O.useState)(`warn`),[p,m]=(0,O.useState)(``),[h,_]=(0,O.useState)(!1),[v,y]=(0,O.useState)(null),[b,x]=(0,O.useState)(null),[C,w]=(0,O.useState)(!1),[E,D]=(0,O.useState)(``),[A,j]=(0,O.useState)(``),[P,I]=(0,O.useState)(null),L=p===`确认`,R=async()=>{if(L&&!h){_(!0),y(null);try{let e=await f.resetAdminPassword();x(e),d(`result`)}catch(e){y(e instanceof u?S(e):String(e))}finally{_(!1)}}},z=async()=>{if(b)try{await navigator.clipboard.writeText(b.password),w(!0),window.setTimeout(()=>w(!1),2e3)}catch{y(`浏览器拒绝了剪贴板访问,请手动选中口令复制。`)}},B=()=>{x(null),D(``),j(``),i?.(),r()},V=async()=>{if(h)return;let e=E.trim();if(e.length===0){y(`管理口令不能为空或纯空白。`);return}if(e.length<M){y(`管理口令至少 ${M} 个字符,当前 ${e.length} 个。`);return}if(E.length>N){y(`管理口令最多 ${N} 个字符,当前 ${E.length} 个。`);return}if(E!==A){y(`两次输入不一致,请重新确认。`);return}_(!0),y(null);try{let e=await f.setAdminPassword(E);D(``),j(``),I(e.persisted?`已生效,下次登录用新口令。当前会话不受影响。`:`已生效(仅内存),下次登录用新口令 —— 但服务端数据库不可写,重启后会回到上一个口令。`)}catch(e){y(e instanceof u?S(e):String(e))}finally{_(!1)}};if(o===`manual`&&P)return(0,k.jsxs)(T,{title:`管理口令已更新`,onClose:B,footer:(0,k.jsx)(`button`,{type:`button`,className:`btn btn-primary btn-sm`,onClick:B,children:`知道了`}),children:[(0,k.jsx)(`div`,{className:`pw-note`,children:P}),(0,k.jsxs)(`p`,{className:`ov-sub`,style:{marginTop:12},children:[`服务端只存了口令的 scrypt 哈希,`,(0,k.jsx)(`b`,{children:`回不出明文`}),`。请确保你已经记住了刚才输入的口令。`]})]});if(o===`manual`){let t=E.trim().length>0&&E.trim().length<M,i=A.length>0&&E!==A;return(0,k.jsxs)(T,{title:`手动设定管理口令`,onClose:r,footer:(0,k.jsxs)(k.Fragment,{children:[(0,k.jsx)(`button`,{type:`button`,className:`btn btn-quiet btn-sm`,onClick:r,children:`取消`}),(0,k.jsxs)(`button`,{type:`button`,className:`btn btn-primary btn-sm`,disabled:h||t||i||E.trim().length===0,onClick:()=>void V(),children:[h?(0,k.jsx)(n,{size:14}):(0,k.jsx)(e,{size:14}),h?`保存中…`:`保存并生效`]})]}),children:[(0,k.jsxs)(`p`,{className:`ov-sub`,children:[`设定一个你自己方便记忆的管理口令(至少 `,M,` 个字符)。 保存后`,(0,k.jsx)(`b`,{children:`立即生效、无需重启`}),`,当前会话不会被打断。`]}),(0,k.jsxs)(`div`,{className:`ov-field`,children:[(0,k.jsx)(`label`,{htmlFor:`pw-new`,children:`新管理口令`}),(0,k.jsx)(`input`,{id:`pw-new`,type:`password`,className:`field-input text`,style:{width:`100%`},value:E,autoFocus:!0,autoComplete:`new-password`,placeholder:`至少 ${M} 个字符`,onChange:e=>{D(e.target.value),y(null)}}),t?(0,k.jsxs)(`div`,{className:`ov-hint`,style:{color:`var(--warn-amber)`},children:[`至少 `,M,` 个字符,当前 `,E.trim().length,` 个。`]}):null]}),(0,k.jsxs)(`div`,{className:`ov-field`,children:[(0,k.jsx)(`label`,{htmlFor:`pw-new-confirm`,children:`再次输入`}),(0,k.jsx)(`input`,{id:`pw-new-confirm`,type:`password`,className:`field-input text`,style:{width:`100%`},value:A,autoComplete:`new-password`,placeholder:`重复上面输入的口令`,onChange:e=>{j(e.target.value),y(null)}}),i?(0,k.jsx)(`div`,{className:`ov-hint`,style:{color:`var(--warn-amber)`},children:`两次输入不一致。`}):null]}),(0,k.jsxs)(`div`,{className:`ov-lose`,children:[(0,k.jsx)(`b`,{children:`请记住它:`}),`设定后旧口令立即失效,且本产品没有「忘记口令」的找回通道。 口令明文不会保存在浏览器任何位置,也不会被回显。`]}),v?(0,k.jsx)(g,{tone:`error`,children:(0,k.jsx)(`span`,{style:{display:`block`,marginTop:14},children:v})}):null]})}return c===`result`&&b?(0,k.jsxs)(T,{title:`新管理口令`,onClose:B,footer:(0,k.jsx)(`button`,{type:`button`,className:`btn btn-primary btn-sm`,onClick:B,children:`我已保存,关闭`}),children:[(0,k.jsxs)(`div`,{className:`pw-once`,children:[(0,k.jsxs)(`div`,{className:`pw-once-head`,children:[(0,k.jsx)(a,{size:16}),(0,k.jsx)(`b`,{children:`这是唯一一次显示`})]}),(0,k.jsx)(`div`,{className:`pw-once-body`,children:`关闭这个窗口后,服务端也回不出这份明文 —— 库里只存了它的 scrypt 哈希。 请现在就复制并保存到你的密码管理器里。`})]}),(0,k.jsxs)(`div`,{className:`pw-plain`,children:[(0,k.jsx)(`code`,{children:b.password}),(0,k.jsxs)(`button`,{type:`button`,className:`btn btn-quiet btn-sm`,onClick:()=>void z(),children:[C?(0,k.jsx)(t,{size:14}):(0,k.jsx)(l,{size:14}),C?`已复制`:`复制`]})]}),b.persisted?(0,k.jsxs)(`div`,{className:`pw-note`,children:[`已写入服务端数据库,`,(0,k.jsx)(`b`,{children:`立即生效、无需重启`}),`,并会随每日备份一起保存。 下次登录请使用新口令。`]}):(0,k.jsx)(g,{tone:`warn`,children:(0,k.jsxs)(`span`,{style:{display:`block`,marginTop:14},children:[`服务端数据库不可写,新口令`,(0,k.jsx)(`b`,{children:`仅本次运行有效`}),`:重启后会回到旧口令。 请先修好数据目录权限,再重置一次。`]})}),v?(0,k.jsx)(g,{tone:`error`,children:(0,k.jsx)(`span`,{style:{display:`block`,marginTop:14},children:v})}):null]}):c===`confirm`?(0,k.jsxs)(T,{title:`确认重置管理口令?`,onClose:r,footer:(0,k.jsxs)(k.Fragment,{children:[(0,k.jsx)(`button`,{type:`button`,className:`btn btn-primary btn-sm`,onClick:r,children:`取消(保持现状)`}),(0,k.jsxs)(`button`,{type:`button`,className:`btn btn-danger btn-sm`,disabled:!L||h,onClick:()=>void R(),children:[h?(0,k.jsx)(n,{size:14}):null,h?`重置中…`:`确认重置`]})]}),children:[(0,k.jsxs)(`p`,{className:`ov-sub`,children:[`重置后,`,(0,k.jsx)(`b`,{children:`当前口令立即失效`}),`。你正在使用的这个会话不会被打断,但下次登录必须用新口令。`]}),(0,k.jsxs)(`div`,{className:`ov-lose`,children:[(0,k.jsx)(`b`,{children:`会失去什么:`}),`旧口令的所有副本(笔记、密码管理器里的旧条目)都会变成无效值。本产品没有「忘记口令」的找回通道。`]}),(0,k.jsxs)(`div`,{className:`ov-field`,children:[(0,k.jsxs)(`label`,{htmlFor:`pw-confirm`,children:[`输入 `,(0,k.jsx)(`b`,{style:{color:`var(--text-secondary)`,fontWeight:500},children:`确认`}),` 以继续`]}),(0,k.jsx)(`input`,{id:`pw-confirm`,className:`field-input text`,style:{width:`100%`,fontFamily:`var(--font-mono)`},value:p,autoFocus:!0,placeholder:`确认`,onChange:e=>m(e.target.value)}),(0,k.jsx)(`div`,{className:`ov-hint`,children:`打错一个字就没法继续。重置入口凭证值得这一步。`})]}),v?(0,k.jsx)(g,{tone:`error`,children:v}):null]}):(0,k.jsxs)(T,{title:`重置管理口令`,onClose:r,footer:(0,k.jsxs)(k.Fragment,{children:[(0,k.jsx)(`button`,{type:`button`,className:`btn btn-quiet btn-sm`,onClick:r,children:`取消`}),(0,k.jsxs)(`button`,{type:`button`,className:`btn btn-danger btn-sm`,onClick:()=>d(`confirm`),children:[(0,k.jsx)(e,{size:14}),`我明白,继续`]})]}),children:[(0,k.jsx)(F,{mode:o,onChange:e=>{s(e),y(null)}}),(0,k.jsxs)(`p`,{className:`ov-sub`,children:[`服务端会生成一个新的 16 位随机口令。`,(0,k.jsx)(`b`,{children:`新口令只显示一次`}),`,请准备好记录工具。`]}),(0,k.jsxs)(`div`,{className:`pw-warn-list`,children:[(0,k.jsxs)(`div`,{children:[(0,k.jsx)(`span`,{className:`pw-dot`}),(0,k.jsxs)(`span`,{children:[(0,k.jsx)(`b`,{children:`当前口令立即失效`}),` —— 但已登录的会话`,(0,k.jsx)(`b`,{children:`不受影响`}),`:会话由独立密钥 (RELAY_SECRET)签名,与口令本身无关。包括其它浏览器标签页在内的登录态, 都会保持有效直到各自过期。本版本未提供「改密强制所有会话下线」。`]})]}),(0,k.jsxs)(`div`,{children:[(0,k.jsx)(`span`,{className:`pw-dot`}),(0,k.jsxs)(`span`,{children:[(0,k.jsx)(`b`,{children:`没有找回通道`}),` —— 忘记新口令后,只能上服务器删除数据结构后重新引导。`]})]}),(0,k.jsxs)(`div`,{children:[(0,k.jsx)(`span`,{className:`pw-dot`}),(0,k.jsxs)(`span`,{children:[(0,k.jsx)(`b`,{children:`立即生效、无需重启`}),` —— 哈希写进数据库后立刻对后续登录起作用。`]})]})]}),(0,k.jsx)(`div`,{className:`ov-hint`,style:{marginTop:12},children:`想用自己的口令?切到上方「手动设定」—— 随机口令更安全,手动口令更好记,按需选择。`})]})}function F({mode:e,onChange:t}){return(0,k.jsxs)(`span`,{className:`seg-tabs`,role:`group`,"aria-label":`口令变更方式`,style:{marginBottom:14},children:[(0,k.jsx)(`button`,{type:`button`,className:e===`reset`?`on`:``,"aria-pressed":e===`reset`,onClick:()=>t(`reset`),children:`随机重置`}),(0,k.jsx)(`button`,{type:`button`,className:e===`manual`?`on`:``,"aria-pressed":e===`manual`,onClick:()=>t(`manual`),children:`手动设定`})]})}function I({spec:e,onClose:t,onDone:r}){let[i,a]=(0,O.useState)(``),[o,s]=(0,O.useState)(!1),[c,l]=(0,O.useState)(null),d=i===`确认`,p=async()=>{if(d&&!o){s(!0),l(null);try{r(await f.danger(e.action,i))}catch(e){l(e instanceof u?e:new u(String(e),0,0)),s(!1)}}};return(0,k.jsxs)(T,{title:e.title,onClose:t,footer:(0,k.jsxs)(k.Fragment,{children:[(0,k.jsx)(`button`,{type:`button`,className:`btn btn-primary btn-sm`,onClick:t,children:`取消(保持现状)`}),(0,k.jsxs)(`button`,{type:`button`,className:`btn btn-danger btn-sm`,disabled:!d||o,onClick:()=>void p(),children:[o?(0,k.jsx)(n,{size:14}):null,o?`执行中…`:e.ok]})]}),children:[(0,k.jsx)(`p`,{className:`ov-sub`,children:e.body}),(0,k.jsxs)(`div`,{className:`ov-lose`,children:[(0,k.jsx)(`b`,{children:`会失去什么:`}),e.lose]}),(0,k.jsxs)(`div`,{className:`ov-field`,children:[(0,k.jsxs)(`label`,{htmlFor:`danger-confirm`,children:[`输入 `,(0,k.jsx)(`b`,{style:{color:`var(--text-secondary)`,fontWeight:500},children:`确认`}),` 以继续`]}),(0,k.jsx)(`input`,{id:`danger-confirm`,className:`field-input text`,style:{width:`100%`,fontFamily:`var(--font-mono)`},value:i,autoFocus:!0,placeholder:`确认`,onChange:e=>a(e.target.value)}),(0,k.jsx)(`div`,{className:`ov-hint`,children:`打错一个字就没法继续。破坏性操作值得这一步。`})]}),c?(0,k.jsx)(g,{tone:`error`,children:S(c)}):null]})}var L={"danger.clearLogs":{action:`clearLogs`,title:`清空全部日志?`,body:`删除后「按模型 / 按客户端」明细会一并归零。剩余积分不受影响,服务也不中断。`,lose:`将删除本机全部请求日志,覆盖保留天数内的所有记录,没有备份入口。`,ok:`确认清空`},"danger.resetKeys":{action:`resetKeys`,title:`重置全部密钥?`,body:`所有密钥会立即失效,每个客户端都要重新填一次。已消耗的积分不受影响。`,lose:`将失效全部 sk-waygate- 密钥,正在使用它们的客户端会立刻收到 401。`,ok:`确认重置`},"danger.restoreDefaults":{action:`restoreDefaults`,title:`恢复默认配置?`,body:`会用默认值覆盖 ~/.relay/config.yml。你改过的端口、并发、日志保留天数都会回到出厂值。`,lose:`将覆盖所有自定义配置,服务重启后生效。`,ok:`确认恢复`}},R={openai:`OpenAI 方言`,anthropic:`Anthropic 方言`,qoder:`COSY 协议`};function z(){let e=m(()=>f.providers(),[],{cacheKey:`providers`}),t=e.data?.items??[],[n,r]=(0,O.useState)(null),i=m(()=>f.providerGrowthPanel(n.id),[n?.id],{enabled:n!==null});return(0,k.jsxs)(v,{title:`提供商健康`,aside:(0,k.jsxs)(y,{children:[t.length,` 家 · 只读总览`]}),children:[e.initial&&e.loading?(0,k.jsx)(`div`,{className:`empty-note`,style:{padding:`8px 0`},children:`正在读取提供商…`}):e.error?(0,k.jsx)(`div`,{className:`empty-note`,style:{padding:`8px 0`},children:`提供商列表没取到,稍后重试。`}):t.length===0?(0,k.jsx)(`div`,{className:`empty-note`,style:{padding:`8px 0`},children:`还没有登记任何提供商 —— 到「提供商管理 → 提供商」新增。`}):(0,k.jsx)(`div`,{className:`tbl-scroll`,children:(0,k.jsxs)(`table`,{className:`tbl`,children:[(0,k.jsx)(`caption`,{className:`sr-only`,children:`各提供商的健康状态`}),(0,k.jsx)(`thead`,{children:(0,k.jsxs)(`tr`,{children:[(0,k.jsx)(`th`,{scope:`col`,children:`提供商`}),(0,k.jsx)(`th`,{scope:`col`,children:`协议`}),(0,k.jsx)(`th`,{scope:`col`,children:`凭证`}),(0,k.jsx)(`th`,{scope:`col`,children:`状态`}),(0,k.jsx)(`th`,{scope:`col`,className:`r`,children:`模型数`}),(0,k.jsx)(`th`,{scope:`col`,children:`积分 / 签到`})]})}),(0,k.jsx)(`tbody`,{children:t.map(e=>(0,k.jsxs)(`tr`,{children:[(0,k.jsx)(`td`,{className:`td-strong`,children:e.name}),(0,k.jsx)(`td`,{className:`td-sub`,children:R[e.protocol]??e.protocol}),(0,k.jsx)(`td`,{children:(0,k.jsx)(`span`,{className:`up-badge${e.configured?``:` warn`}`,children:e.configured?`有效`:`未配置`})}),(0,k.jsx)(`td`,{children:e.active?(0,k.jsx)(y,{tone:`live`,children:`已启用`}):(0,k.jsx)(y,{tone:`ghost`,children:`未启用`})}),(0,k.jsx)(`td`,{className:`r td-mono`,children:p(e.modelCount??0)}),(0,k.jsx)(`td`,{className:`td-sub td-mono`,children:e.credits?.available?(0,k.jsxs)(k.Fragment,{children:[`剩余 `,h(e.credits.remaining??0),e.credits.consumed===null?null:(0,k.jsxs)(k.Fragment,{children:[` `,(0,k.jsx)(d,{content:`已消耗 / 累计发放 —— 账户级全部历史(含官方客户端直连的用量)。
2
- 不是本服务转发的那部分,与剩余不是同一种量。`,children:(0,k.jsxs)(`span`,{className:`credit-aside`,children:[`已消耗 `,h(e.credits.consumed),e.credits.granted===null?``:` / 发放 ${h(e.credits.granted)}`]})})]}),e.credits.stale?`(偏旧)`:``]}):e.qoderCredits?(0,k.jsxs)(k.Fragment,{children:[e.qoderCredits.remaining===null?`余额未知`:`剩余 ${h(e.qoderCredits.remaining)}`,e.qoderCredits.lifetimeConsumed!==null&&e.qoderCredits.lifetimeConsumed!==void 0?(0,k.jsxs)(k.Fragment,{children:[` `,(0,k.jsx)(d,{content:`累计消耗 —— 这个账号近一年在该平台消耗掉的 credits 总量(账号级)。
3
- 它不是当前余额,也不是本服务转发的那部分:含官方客户端直连的用量。
4
- 数值等于每日消耗热力图近 371 天之和。`,children:(0,k.jsxs)(`span`,{className:`credit-aside`,children:[`累计消耗 `,h(e.qoderCredits.lifetimeConsumed),e.qoderCredits.granted===null?``:` / 发放 ${h(e.qoderCredits.granted)}`]})})]}):null,e.qoderCredits.stale?`(偏旧)`:``,e.signin?.streak?`(连续活跃 ${p(e.signin.streak)} 天)`:``]}):e.wbCredits?(0,k.jsxs)(k.Fragment,{children:[`剩余 `,h(e.wbCredits.remaining??0),e.wbCredits.consumed===null?null:(0,k.jsxs)(k.Fragment,{children:[` `,(0,k.jsx)(d,{content:`已消耗 / 累计发放 —— 账户全部资源包的历史合计(含已过期包、
1
+ import{D as e,J as t,S as n,f as r,it as i,l as a,p as o,tt as s,w as c,z as l}from"./vendor-befEYGHM.js";import{M as u,a as d,c as f,g as p,j as m,p as h,r as g}from"./index-BcWmrhMD.js";import{t as _}from"./accessUrl-DbL5DLDz.js";import{a as v,c as y,l as b,n as x,r as S,s as C,t as w}from"./Select-Bfquh0d_.js";import{t as T}from"./Modal-B-rIrvXS.js";import{t as E}from"./Drawer-CleQGhRU.js";import{t as D}from"./Switch-0KA1AbiV.js";var O=i(),k=s();function A({item:e,value:t,disabled:n,onChange:r}){if(e.type===`switch`)return(0,k.jsx)(D,{checked:!!t,disabled:n||e.readonly,label:e.label,onChange:e=>r(e)});if(e.type===`badge`)return(0,k.jsx)(b,{tone:`live`,children:String(t)});if(e.type===`select`){let i=(e.options??[]).map(e=>({value:e.value,label:e.label}));return(0,k.jsx)(w,{value:String(t),options:i,disabled:n||e.readonly,onChange:e=>r(e),width:188})}return e.type===`number`?(0,k.jsx)(`input`,{className:`field-input num`,type:`number`,value:t==null?``:String(t),disabled:n||e.readonly,onChange:e=>r(e.target.value===``?``:Number(e.target.value)),"aria-label":e.label}):e.type===`mapping`?null:(0,k.jsx)(`input`,{className:`field-input text`,value:t==null?``:String(t),disabled:n||e.readonly,onChange:e=>r(e.target.value),"aria-label":e.label})}function j(){let e=_(),[n,r]=(0,O.useState)(!1),i=async()=>{try{await navigator.clipboard.writeText(e),r(!0),window.setTimeout(()=>r(!1),1200)}catch{}};return(0,k.jsxs)(`div`,{className:`card access-card`,children:[(0,k.jsxs)(`div`,{className:`access-head`,children:[(0,k.jsxs)(`span`,{className:`access-title`,children:[(0,k.jsx)(c,{size:13,"aria-hidden":!0}),`接入地址`]}),(0,k.jsx)(`span`,{className:`access-sub`,children:`客户端与 API 同源 —— 这就是你当前访问控制台的地址`})]}),(0,k.jsxs)(`div`,{className:`key-plain access-url`,children:[(0,k.jsx)(`code`,{children:e}),(0,k.jsxs)(`button`,{type:`button`,className:`copy`,"aria-label":n?`已复制接入地址`:`复制接入地址`,onClick:()=>void i(),children:[n?(0,k.jsx)(t,{size:13}):(0,k.jsx)(l,{size:13}),n?`已复制`:`复制`]})]}),(0,k.jsxs)(`p`,{className:`chain-note`,children:[`客户端里要填两组值:`,(0,k.jsx)(`b`,{children:`base_url`}),` 就是上面这串;`,(0,k.jsx)(`b`,{children:`API Key`}),` 用你在本页`,(0,k.jsx)(`b`,{children:`新建的那把`}),(0,k.jsx)(`span`,{className:`code-chip`,children:`sk-waygate-…`}),`(明文只在创建时显示一次,丢了只能删掉重建)。`]}),(0,k.jsxs)(`div`,{className:`cred-note access-cert`,children:[(0,k.jsx)(a,{size:14,"aria-hidden":!0}),(0,k.jsxs)(`span`,{children:[`本服务的 TLS 是`,(0,k.jsx)(`b`,{children:`自签证书`}),`:客户端得先信任它的根证书,否则会以「证书错误」失败 —— 那`,(0,k.jsx)(`b`,{children:`不是`}),`地址填错。把根证书装进系统信任库,或让客户端通过`,(0,k.jsx)(`span`,{className:`code-chip`,children:`NODE_EXTRA_CA_CERTS`}),` /`,(0,k.jsx)(`span`,{className:`code-chip`,children:`SSL_CERT_FILE`}),`指向随部署产出的`,(0,k.jsx)(`span`,{className:`code-chip`,children:`relay-ca.crt`}),`。`]})]})]})}var M=8,N=128;function P({onClose:r,onDone:i}){let[o,s]=(0,O.useState)(`reset`),[c,d]=(0,O.useState)(`warn`),[p,m]=(0,O.useState)(``),[h,_]=(0,O.useState)(!1),[v,y]=(0,O.useState)(null),[b,x]=(0,O.useState)(null),[C,w]=(0,O.useState)(!1),[E,D]=(0,O.useState)(``),[A,j]=(0,O.useState)(``),[P,I]=(0,O.useState)(null),L=p===`确认`,R=async()=>{if(L&&!h){_(!0),y(null);try{let e=await f.resetAdminPassword();x(e),d(`result`)}catch(e){y(e instanceof u?S(e):String(e))}finally{_(!1)}}},z=async()=>{if(b)try{await navigator.clipboard.writeText(b.password),w(!0),window.setTimeout(()=>w(!1),2e3)}catch{y(`浏览器拒绝了剪贴板访问,请手动选中口令复制。`)}},B=()=>{x(null),D(``),j(``),i?.(),r()},V=async()=>{if(h)return;let e=E.trim();if(e.length===0){y(`管理口令不能为空或纯空白。`);return}if(e.length<M){y(`管理口令至少 ${M} 个字符,当前 ${e.length} 个。`);return}if(E.length>N){y(`管理口令最多 ${N} 个字符,当前 ${E.length} 个。`);return}if(E!==A){y(`两次输入不一致,请重新确认。`);return}_(!0),y(null);try{let e=await f.setAdminPassword(E);D(``),j(``),I(e.persisted?`已生效,下次登录用新口令。当前会话不受影响。`:`已生效(仅内存),下次登录用新口令 —— 但服务端数据库不可写,重启后会回到上一个口令。`)}catch(e){y(e instanceof u?S(e):String(e))}finally{_(!1)}};if(o===`manual`&&P)return(0,k.jsxs)(T,{title:`管理口令已更新`,onClose:B,footer:(0,k.jsx)(`button`,{type:`button`,className:`btn btn-primary btn-sm`,onClick:B,children:`知道了`}),children:[(0,k.jsx)(`div`,{className:`pw-note`,children:P}),(0,k.jsxs)(`p`,{className:`ov-sub`,style:{marginTop:12},children:[`服务端只存了口令的 scrypt 哈希,`,(0,k.jsx)(`b`,{children:`回不出明文`}),`。请确保你已经记住了刚才输入的口令。`]})]});if(o===`manual`){let t=E.trim().length>0&&E.trim().length<M,i=A.length>0&&E!==A;return(0,k.jsxs)(T,{title:`手动设定管理口令`,onClose:r,footer:(0,k.jsxs)(k.Fragment,{children:[(0,k.jsx)(`button`,{type:`button`,className:`btn btn-quiet btn-sm`,onClick:r,children:`取消`}),(0,k.jsxs)(`button`,{type:`button`,className:`btn btn-primary btn-sm`,disabled:h||t||i||E.trim().length===0,onClick:()=>void V(),children:[h?(0,k.jsx)(n,{size:14}):(0,k.jsx)(e,{size:14}),h?`保存中…`:`保存并生效`]})]}),children:[(0,k.jsxs)(`p`,{className:`ov-sub`,children:[`设定一个你自己方便记忆的管理口令(至少 `,M,` 个字符)。 保存后`,(0,k.jsx)(`b`,{children:`立即生效、无需重启`}),`,当前会话不会被打断。`]}),(0,k.jsxs)(`div`,{className:`ov-field`,children:[(0,k.jsx)(`label`,{htmlFor:`pw-new`,children:`新管理口令`}),(0,k.jsx)(`input`,{id:`pw-new`,type:`password`,className:`field-input text`,style:{width:`100%`},value:E,autoFocus:!0,autoComplete:`new-password`,placeholder:`至少 ${M} 个字符`,onChange:e=>{D(e.target.value),y(null)}}),t?(0,k.jsxs)(`div`,{className:`ov-hint`,style:{color:`var(--warn-amber)`},children:[`至少 `,M,` 个字符,当前 `,E.trim().length,` 个。`]}):null]}),(0,k.jsxs)(`div`,{className:`ov-field`,children:[(0,k.jsx)(`label`,{htmlFor:`pw-new-confirm`,children:`再次输入`}),(0,k.jsx)(`input`,{id:`pw-new-confirm`,type:`password`,className:`field-input text`,style:{width:`100%`},value:A,autoComplete:`new-password`,placeholder:`重复上面输入的口令`,onChange:e=>{j(e.target.value),y(null)}}),i?(0,k.jsx)(`div`,{className:`ov-hint`,style:{color:`var(--warn-amber)`},children:`两次输入不一致。`}):null]}),(0,k.jsxs)(`div`,{className:`ov-lose`,children:[(0,k.jsx)(`b`,{children:`请记住它:`}),`设定后旧口令立即失效,且本产品没有「忘记口令」的找回通道。 口令明文不会保存在浏览器任何位置,也不会被回显。`]}),v?(0,k.jsx)(g,{tone:`error`,children:(0,k.jsx)(`span`,{style:{display:`block`,marginTop:14},children:v})}):null]})}return c===`result`&&b?(0,k.jsxs)(T,{title:`新管理口令`,onClose:B,footer:(0,k.jsx)(`button`,{type:`button`,className:`btn btn-primary btn-sm`,onClick:B,children:`我已保存,关闭`}),children:[(0,k.jsxs)(`div`,{className:`pw-once`,children:[(0,k.jsxs)(`div`,{className:`pw-once-head`,children:[(0,k.jsx)(a,{size:16}),(0,k.jsx)(`b`,{children:`这是唯一一次显示`})]}),(0,k.jsx)(`div`,{className:`pw-once-body`,children:`关闭这个窗口后,服务端也回不出这份明文 —— 库里只存了它的 scrypt 哈希。 请现在就复制并保存到你的密码管理器里。`})]}),(0,k.jsxs)(`div`,{className:`pw-plain`,children:[(0,k.jsx)(`code`,{children:b.password}),(0,k.jsxs)(`button`,{type:`button`,className:`btn btn-quiet btn-sm`,onClick:()=>void z(),children:[C?(0,k.jsx)(t,{size:14}):(0,k.jsx)(l,{size:14}),C?`已复制`:`复制`]})]}),b.persisted?(0,k.jsxs)(`div`,{className:`pw-note`,children:[`已写入服务端数据库,`,(0,k.jsx)(`b`,{children:`立即生效、无需重启`}),`,并会随每日备份一起保存。 下次登录请使用新口令。`]}):(0,k.jsx)(g,{tone:`warn`,children:(0,k.jsxs)(`span`,{style:{display:`block`,marginTop:14},children:[`服务端数据库不可写,新口令`,(0,k.jsx)(`b`,{children:`仅本次运行有效`}),`:重启后会回到旧口令。 请先修好数据目录权限,再重置一次。`]})}),v?(0,k.jsx)(g,{tone:`error`,children:(0,k.jsx)(`span`,{style:{display:`block`,marginTop:14},children:v})}):null]}):c===`confirm`?(0,k.jsxs)(T,{title:`确认重置管理口令?`,onClose:r,footer:(0,k.jsxs)(k.Fragment,{children:[(0,k.jsx)(`button`,{type:`button`,className:`btn btn-primary btn-sm`,onClick:r,children:`取消(保持现状)`}),(0,k.jsxs)(`button`,{type:`button`,className:`btn btn-danger btn-sm`,disabled:!L||h,onClick:()=>void R(),children:[h?(0,k.jsx)(n,{size:14}):null,h?`重置中…`:`确认重置`]})]}),children:[(0,k.jsxs)(`p`,{className:`ov-sub`,children:[`重置后,`,(0,k.jsx)(`b`,{children:`当前口令立即失效`}),`。你正在使用的这个会话不会被打断,但下次登录必须用新口令。`]}),(0,k.jsxs)(`div`,{className:`ov-lose`,children:[(0,k.jsx)(`b`,{children:`会失去什么:`}),`旧口令的所有副本(笔记、密码管理器里的旧条目)都会变成无效值。本产品没有「忘记口令」的找回通道。`]}),(0,k.jsxs)(`div`,{className:`ov-field`,children:[(0,k.jsxs)(`label`,{htmlFor:`pw-confirm`,children:[`输入 `,(0,k.jsx)(`b`,{style:{color:`var(--text-secondary)`,fontWeight:500},children:`确认`}),` 以继续`]}),(0,k.jsx)(`input`,{id:`pw-confirm`,className:`field-input text`,style:{width:`100%`,fontFamily:`var(--font-mono)`},value:p,autoFocus:!0,placeholder:`确认`,onChange:e=>m(e.target.value)}),(0,k.jsx)(`div`,{className:`ov-hint`,children:`打错一个字就没法继续。重置入口凭证值得这一步。`})]}),v?(0,k.jsx)(g,{tone:`error`,children:v}):null]}):(0,k.jsxs)(T,{title:`重置管理口令`,onClose:r,footer:(0,k.jsxs)(k.Fragment,{children:[(0,k.jsx)(`button`,{type:`button`,className:`btn btn-quiet btn-sm`,onClick:r,children:`取消`}),(0,k.jsxs)(`button`,{type:`button`,className:`btn btn-danger btn-sm`,onClick:()=>d(`confirm`),children:[(0,k.jsx)(e,{size:14}),`我明白,继续`]})]}),children:[(0,k.jsx)(F,{mode:o,onChange:e=>{s(e),y(null)}}),(0,k.jsxs)(`p`,{className:`ov-sub`,children:[`服务端会生成一个新的 16 位随机口令。`,(0,k.jsx)(`b`,{children:`新口令只显示一次`}),`,请准备好记录工具。`]}),(0,k.jsxs)(`div`,{className:`pw-warn-list`,children:[(0,k.jsxs)(`div`,{children:[(0,k.jsx)(`span`,{className:`pw-dot`}),(0,k.jsxs)(`span`,{children:[(0,k.jsx)(`b`,{children:`当前口令立即失效`}),` —— 但已登录的会话`,(0,k.jsx)(`b`,{children:`不受影响`}),`:会话由独立密钥 (RELAY_SECRET)签名,与口令本身无关。包括其它浏览器标签页在内的登录态, 都会保持有效直到各自过期。本版本未提供「改密强制所有会话下线」。`]})]}),(0,k.jsxs)(`div`,{children:[(0,k.jsx)(`span`,{className:`pw-dot`}),(0,k.jsxs)(`span`,{children:[(0,k.jsx)(`b`,{children:`没有找回通道`}),` —— 忘记新口令后,只能上服务器删除数据结构后重新引导。`]})]}),(0,k.jsxs)(`div`,{children:[(0,k.jsx)(`span`,{className:`pw-dot`}),(0,k.jsxs)(`span`,{children:[(0,k.jsx)(`b`,{children:`立即生效、无需重启`}),` —— 哈希写进数据库后立刻对后续登录起作用。`]})]})]}),(0,k.jsx)(`div`,{className:`ov-hint`,style:{marginTop:12},children:`想用自己的口令?切到上方「手动设定」—— 随机口令更安全,手动口令更好记,按需选择。`})]})}function F({mode:e,onChange:t}){return(0,k.jsxs)(`span`,{className:`seg-tabs`,role:`group`,"aria-label":`口令变更方式`,style:{marginBottom:14},children:[(0,k.jsx)(`button`,{type:`button`,className:e===`reset`?`on`:``,"aria-pressed":e===`reset`,onClick:()=>t(`reset`),children:`随机重置`}),(0,k.jsx)(`button`,{type:`button`,className:e===`manual`?`on`:``,"aria-pressed":e===`manual`,onClick:()=>t(`manual`),children:`手动设定`})]})}function I({spec:e,onClose:t,onDone:r}){let[i,a]=(0,O.useState)(``),[o,s]=(0,O.useState)(!1),[c,l]=(0,O.useState)(null),d=i===`确认`,p=async()=>{if(d&&!o){s(!0),l(null);try{r(await f.danger(e.action,i))}catch(e){l(e instanceof u?e:new u(String(e),0,0)),s(!1)}}};return(0,k.jsxs)(T,{title:e.title,onClose:t,footer:(0,k.jsxs)(k.Fragment,{children:[(0,k.jsx)(`button`,{type:`button`,className:`btn btn-primary btn-sm`,onClick:t,children:`取消(保持现状)`}),(0,k.jsxs)(`button`,{type:`button`,className:`btn btn-danger btn-sm`,disabled:!d||o,onClick:()=>void p(),children:[o?(0,k.jsx)(n,{size:14}):null,o?`执行中…`:e.ok]})]}),children:[(0,k.jsx)(`p`,{className:`ov-sub`,children:e.body}),(0,k.jsxs)(`div`,{className:`ov-lose`,children:[(0,k.jsx)(`b`,{children:`会失去什么:`}),e.lose]}),(0,k.jsxs)(`div`,{className:`ov-field`,children:[(0,k.jsxs)(`label`,{htmlFor:`danger-confirm`,children:[`输入 `,(0,k.jsx)(`b`,{style:{color:`var(--text-secondary)`,fontWeight:500},children:`确认`}),` 以继续`]}),(0,k.jsx)(`input`,{id:`danger-confirm`,className:`field-input text`,style:{width:`100%`,fontFamily:`var(--font-mono)`},value:i,autoFocus:!0,placeholder:`确认`,onChange:e=>a(e.target.value)}),(0,k.jsx)(`div`,{className:`ov-hint`,children:`打错一个字就没法继续。破坏性操作值得这一步。`})]}),c?(0,k.jsx)(g,{tone:`error`,children:S(c)}):null]})}var L={"danger.clearLogs":{action:`clearLogs`,title:`清空全部日志?`,body:`删除后「按模型 / 按客户端」明细会一并归零。剩余积分不受影响,服务也不中断。`,lose:`将删除本机全部请求日志,覆盖保留天数内的所有记录,没有备份入口。`,ok:`确认清空`},"danger.resetKeys":{action:`resetKeys`,title:`重置全部密钥?`,body:`所有密钥会立即失效,每个客户端都要重新填一次。已消耗的积分不受影响。`,lose:`将失效全部 sk-waygate- 密钥,正在使用它们的客户端会立刻收到 401。`,ok:`确认重置`},"danger.restoreDefaults":{action:`restoreDefaults`,title:`恢复默认配置?`,body:`会用默认值覆盖 ~/.relay/config.yml。你改过的端口、并发、日志保留天数都会回到出厂值。`,lose:`将覆盖所有自定义配置,服务重启后生效。`,ok:`确认恢复`}},R={openai:`OpenAI 方言`,anthropic:`Anthropic 方言`,qoder:`COSY 协议`};function z(){let e=m(()=>f.providers(),[],{cacheKey:`providers`}),t=e.data?.items??[],[n,r]=(0,O.useState)(null),i=m(()=>f.providerGrowthPanel(n.id),[n?.id],{enabled:n!==null});return(0,k.jsxs)(v,{title:`提供商健康`,aside:(0,k.jsxs)(y,{children:[t.length,` 家 · 只读总览`]}),children:[e.initial&&e.loading?(0,k.jsx)(`div`,{className:`empty-note`,style:{padding:`8px 0`},children:`正在读取提供商…`}):e.error?(0,k.jsx)(`div`,{className:`empty-note`,style:{padding:`8px 0`},children:`提供商列表没取到,稍后重试。`}):t.length===0?(0,k.jsx)(`div`,{className:`empty-note`,style:{padding:`8px 0`},children:`还没有登记任何提供商 —— 到「提供商管理 → 提供商」新增。`}):(0,k.jsx)(`div`,{className:`tbl-scroll`,children:(0,k.jsxs)(`table`,{className:`tbl`,children:[(0,k.jsx)(`caption`,{className:`sr-only`,children:`各提供商的健康状态`}),(0,k.jsx)(`thead`,{children:(0,k.jsxs)(`tr`,{children:[(0,k.jsx)(`th`,{scope:`col`,children:`提供商`}),(0,k.jsx)(`th`,{scope:`col`,children:`协议`}),(0,k.jsx)(`th`,{scope:`col`,children:`凭证`}),(0,k.jsx)(`th`,{scope:`col`,children:`状态`}),(0,k.jsx)(`th`,{scope:`col`,className:`r`,children:`模型数`}),(0,k.jsx)(`th`,{scope:`col`,children:`积分 / 签到`})]})}),(0,k.jsx)(`tbody`,{children:t.map(e=>(0,k.jsxs)(`tr`,{children:[(0,k.jsx)(`td`,{className:`td-strong`,children:e.name}),(0,k.jsx)(`td`,{className:`td-sub`,children:R[e.protocol]??e.protocol}),(0,k.jsx)(`td`,{children:(0,k.jsx)(`span`,{className:`up-badge${e.configured?``:` warn`}`,children:e.configured?`有效`:`未配置`})}),(0,k.jsx)(`td`,{children:e.active?(0,k.jsx)(y,{tone:`live`,children:`已启用`}):(0,k.jsx)(y,{tone:`ghost`,children:`未启用`})}),(0,k.jsx)(`td`,{className:`r td-mono`,children:p(e.modelCount??0)}),(0,k.jsx)(`td`,{className:`td-sub td-mono`,children:e.credits?.available?(0,k.jsxs)(k.Fragment,{children:[`剩余 `,h(e.credits.remaining??0),e.credits.consumed===null?null:(0,k.jsxs)(k.Fragment,{children:[` `,(0,k.jsx)(d,{content:`已消耗 / 累计发放 —— 账户级全部历史(含官方客户端直连的用量)。
2
+ 不是本服务转发的那部分,与剩余不是同一种量。`,children:(0,k.jsxs)(`span`,{className:`credit-aside`,children:[`已消耗 `,h(e.credits.consumed),e.credits.granted===null?``:` / 发放 ${h(e.credits.granted)}`]})})]}),e.credits.stale?`(偏旧)`:``]}):e.qoderCredits?(0,k.jsxs)(k.Fragment,{children:[e.qoderCredits.remaining===null?`余额未知`:`剩余 ${h(e.qoderCredits.remaining)}`,e.qoderCredits.lifetimeConsumed!==null&&e.qoderCredits.lifetimeConsumed!==void 0?(0,k.jsxs)(k.Fragment,{children:[` `,(0,k.jsx)(d,{content:`已消耗 / 累计发放 —— me/usage 的套餐内 + 资源包口径(与剩余同源同刻)。
3
+ 含官方客户端直连的用量,不是本服务转发的那部分。
4
+ 「累计消耗(账号级)」是另一个量(每日消耗热力图近 371 天之和),口径不同不并列。`,children:(0,k.jsxs)(`span`,{className:`credit-aside`,children:[`已消耗 `,h(e.qoderCredits.consumed??0),` / 发放 `,e.qoderCredits.granted===null?`—`:h(e.qoderCredits.granted)]})})]}):null,e.qoderCredits.stale?`(偏旧)`:``,e.signin?.streak?`(连续活跃 ${p(e.signin.streak)} 天)`:``]}):e.wbCredits?(0,k.jsxs)(k.Fragment,{children:[`剩余 `,h(e.wbCredits.remaining??0),e.wbCredits.consumed===null?null:(0,k.jsxs)(k.Fragment,{children:[` `,(0,k.jsx)(d,{content:`已消耗 / 累计发放 —— 账户全部资源包的历史合计(含已过期包、
5
5
  含官方客户端直连的用量)。剩余只统计未过期包,两者口径不同。`,children:(0,k.jsxs)(`span`,{className:`credit-aside`,children:[`已消耗 `,h(e.wbCredits.consumed),e.wbCredits.granted===null?``:` / 发放 ${h(e.wbCredits.granted)}`]})})]}),e.wbSignin?.streak?`(连签 ${p(e.wbSignin.streak)} 天)`:``]}):e.signin?.checkedOn?(0,k.jsxs)(k.Fragment,{children:[`今日已签到`,e.signin.lastPoints?` +${p(e.signin.lastPoints)}`:``]}):e.wbSignin?.checkedOn?(0,k.jsxs)(k.Fragment,{children:[`今日已签到`,e.wbSignin.lastPoints?` +${p(e.wbSignin.lastPoints)}`:``]}):`—`}),(0,k.jsx)(`td`,{children:e.protocol===`openai`&&e.wbOAuth?.configured?(0,k.jsx)(d,{content:`查看成长任务的完成情况(进度/奖励/状态,只读)`,children:(0,k.jsx)(`button`,{type:`button`,className:`mini-pill`,onClick:()=>r(e),children:`任务`})}):(0,k.jsx)(`span`,{className:`td-sub`,children:`—`})})]},e.id))})]})}),(0,k.jsxs)(`ul`,{className:`ph-notes`,children:[(0,k.jsxs)(`li`,{children:[(0,k.jsx)(`b`,{children:`积分口径(三家各不同)`}),`:本表「积分」列都取`,(0,k.jsx)(`b`,{children:`上游真实余额`}),`,非本地推算。 MiniMax Code 来自 `,(0,k.jsx)(`span`,{className:`code-chip`,children:`credit/details`}),`(余额/已用/累计发放齐全,精确到 0.01); WorkBuddy 来自资源包聚合 `,(0,k.jsx)(`span`,{className:`code-chip`,children:`get-user-resource`}),`(剩余/发放为包级真实数); Qoder CN 来自 `,(0,k.jsx)(`span`,{className:`code-chip`,children:`v2/me/usage`}),`(套餐内 + 资源包合计 —— 签到赠送的 Credits 进资源包,故签完此处会上涨)。`,(0,k.jsx)(`b`,{children:`到期时刻仅 Qoder 不提供`}),`(上游无此字段), 概览「积分账本」对应列显示 `,(0,k.jsx)(`span`,{className:`code-chip`,children:`—`}),`。 另一种「累计消耗」是`,(0,k.jsx)(`b`,{children:`账号级近一年消耗总量`}),`(含官方客户端直连),与余额不是一回事, 两者不混算。`]}),(0,k.jsxs)(`li`,{children:[(0,k.jsx)(`b`,{children:`每日签到`}),`:MiniMax Code 由本服务每天 08:05 后自动代签(OAuth 链)。WorkBuddy 分两档: 已导入桌面端 OAuth 凭证的(提供商管理 → 提供商 → 导入OAuth)每天 08:05 `,(0,k.jsx)(`b`,{children:`自动代领`}),`签到 + 成长任务 + 连登兑换;未导入的只做状态同步(上游不允许 API 密钥代领,403 实证)。 OAuth 与转发用的 API 密钥互不影响(实验实证多会话共存,桌面端不受干扰)。成长任务的 完成情况点本表「任务」查看(未完成的需在官方客户端真实使用后才能领)。`]}),(0,k.jsxs)(`li`,{children:[(0,k.jsx)(`b`,{children:`凭证口径(两家不同)`}),`:`,(0,k.jsx)(`b`,{children:`MiniMax Code 是真互斥`}),` —— refresh token 一次性,且「同一账号同时只有一个有效会话」, 桌面客户端登录会把本服务顶下线,反之亦然;`,(0,k.jsx)(`b`,{children:`建议给本服务用专用账号`}),`。`,(0,k.jsx)(`b`,{children:`Qoder CN 不互斥`}),` —— 支持多会话并存,本服务与桌面客户端可同时用同一账号(实测 2026-10-16),`,(0,k.jsx)(`b`,{children:`无需`}),`专用账号。任一凭证失效时到「提供商管理 → 提供商」重新导入。`]}),(0,k.jsxs)(`li`,{children:[(0,k.jsx)(`b`,{children:`Qoder 零内容断流自动重试`}),`:Qoder 网关在大上下文时偶发「返回 200 但零字节即断开」, 本服务会自动重发一次(最多 1 次,对客户端无感 —— 重试发生在响应提交之前)。 请求日志里记 `,(0,k.jsx)(`span`,{className:`code-chip`,children:`retry_count`}),` 与 `,(0,k.jsx)(`span`,{className:`code-chip`,children:`retried`}),`。`]}),(0,k.jsxs)(`li`,{children:[(0,k.jsx)(`b`,{children:`提供商归属的已知限制`}),`:请求表不记录「这条走的是哪家」,提供商归属按`,(0,k.jsx)(`b`,{children:`模型 id → 目录`}),`推断。因此同名的模型 id 分属两家时归属可能不准; 请求日志的「提供商」列也是用同一推断口径。`]})]}),n?(0,k.jsx)(E,{title:`成长任务 · ${n.name}`,subtitle:`完成态与奖励(上游实时只读;未完成的需在官方客户端真实使用后才能领)`,onClose:()=>r(null),children:(0,k.jsxs)(`div`,{className:`drawer-body`,children:[i.initial&&i.loading?(0,k.jsx)(`div`,{className:`empty-note`,children:`正在读取任务面板…`}):i.error||!i.data?.ok?(0,k.jsx)(`div`,{className:`empty-note`,children:i.error?.message??i.data?.message??`任务面板没取到,稍后重试。`}):(0,k.jsx)(`div`,{style:{maxHeight:`min(68vh, 640px)`,overflow:`auto`},children:(0,k.jsxs)(`table`,{className:`tbl`,style:{minWidth:480},children:[(0,k.jsx)(`caption`,{className:`sr-only`,children:`成长任务完成情况`}),(0,k.jsx)(`thead`,{children:(0,k.jsxs)(`tr`,{children:[(0,k.jsx)(`th`,{scope:`col`,children:`任务`}),(0,k.jsx)(`th`,{scope:`col`,style:{width:56},children:`进度`}),(0,k.jsx)(`th`,{scope:`col`,className:`r`,style:{width:84},children:`奖励`}),(0,k.jsx)(`th`,{scope:`col`,style:{width:72},children:`状态`})]})}),(0,k.jsx)(`tbody`,{children:i.data.tasks.map(e=>(0,k.jsxs)(`tr`,{children:[(0,k.jsx)(`td`,{style:{maxWidth:104},children:(0,k.jsx)(d,{content:e.desc?`${e.title??e.code} —— ${e.desc}`:e.title??e.code,children:(0,k.jsx)(`span`,{className:`td-strong`,style:{display:`inline-block`,maxWidth:`100%`,whiteSpace:`nowrap`,overflow:`hidden`,textOverflow:`ellipsis`,verticalAlign:`bottom`},children:e.title??e.code})})}),(0,k.jsx)(`td`,{className:`td-mono`,children:e.progress?`${e.progress.current}/${e.progress.target}`:`—`}),(0,k.jsx)(`td`,{className:`r td-mono`,children:e.rewardCredit?`${e.rewardCredit} 积分`:`—`}),(0,k.jsx)(`td`,{children:e.status===`claimed`?(0,k.jsx)(y,{tone:`live`,children:`已领取`}):e.status===`in_progress`?(0,k.jsx)(y,{tone:`amber`,children:`进行中`}):e.locked?(0,k.jsx)(y,{tone:`ghost`,children:`未解锁`}):(0,k.jsx)(y,{tone:`ghost`,children:`待完成`})})]},e.code))})]})}),(0,k.jsx)(`div`,{className:`footer-note`,children:`每天 08:05 自动代领一轮(签到 + 已完成的任务 + 连登兑换);这里的数据来自上游任务面板,实时只读。`})]})}):null]})}var B=new Set([`credential.source`,`credential.status`]),V={service:`ghost`,credential:`cyan`,quota:`amber`,limits:`rose`,logs:`ghost`,password:`amber`,danger:`amber`,mapping:`cyan`};function H(){let t=m(()=>f.settings(),[],{cacheKey:`settings`}),[n,i]=(0,O.useState)({}),[a,s]=(0,O.useState)(!1),[c,l]=(0,O.useState)(null),[d,p]=(0,O.useState)(null),[h,_]=(0,O.useState)(null),[b,w]=(0,O.useState)(null),[T,E]=(0,O.useState)(!1),[D,A]=(0,O.useState)(null),[M,N]=(0,O.useState)(`access`),F=t.data?.groups??[],R=(0,O.useMemo)(()=>{let e=[{id:`access`,label:`接入地址`,tone:`cyan`}];for(let t of F)t.id!==`mapping`&&e.push({id:t.id,label:t.label,tone:V[t.id]??`ghost`});return e.push({id:`password`,label:`管理口令`,tone:`amber`}),e.push({id:`mapping`,label:`键位映射`,tone:`cyan`}),e},[F]),H=(0,O.useMemo)(()=>{let e={};for(let t of F){let r=0;for(let e of t.items)B.has(e.key)||e.readonly||e.type===`action`||e.type===`mapping`||e.key in n&&n[e.key]!==e.value&&(r+=1);r>0&&(e[t.id]=r)}return e},[F,n]),W=(e,t)=>e in n?n[e]:t,G=(0,O.useMemo)(()=>{if(!t.data)return[];let e=[];return t.data.groups.forEach(t=>t.items.forEach(t=>{B.has(t.key)||t.readonly||t.type===`action`||t.type===`mapping`||t.key in n&&n[t.key]!==t.value&&e.push({key:t.key,value:n[t.key]})})),e},[t.data,n]),K=async()=>{if(!(G.length===0||a)){s(!0),l(null),p(null);try{let e=await f.putSettings(G);i({}),p(e.requiresRestart?`已应用 ${e.applied} 项,配置版本 → v${e.version}。其中含需重启才生效的项。`:`已应用 ${e.applied} 项,配置版本 → v${e.version}。`),setTimeout(()=>p(null),4e3),t.reload()}catch(e){l(e instanceof u?e:new u(String(e),0,0))}finally{s(!1)}}},q=e=>{let n=e.affected.logs??e.affected.keys??0;w(`操作已完成,影响 ${n} 条记录。`),setTimeout(()=>w(null),4e3),_(null),t.reload()},J=F.find(e=>e.id===`mapping`)?.items[0],Y=F.find(e=>e.id===M),X=F.find(e=>e.id===`danger`)?.items??[];return(0,k.jsxs)(`div`,{className:`view on`,children:[(0,k.jsx)(C,{title:`设置`,status:t.data?(0,k.jsx)(y,{tone:G.length?`amber`:`ghost`,dot:G.length>0,children:G.length?`${G.length} 项待保存`:`配置版本 v${t.data.version}`}):null,actions:(0,k.jsxs)(k.Fragment,{children:[G.length?(0,k.jsxs)(`button`,{type:`button`,className:`btn btn-quiet btn-sm`,onClick:()=>i({}),children:[(0,k.jsx)(o,{size:14}),`放弃改动`]}):null,(0,k.jsxs)(`button`,{type:`button`,className:`btn btn-primary btn-sm`,disabled:G.length===0||a,onClick:()=>void K(),children:[(0,k.jsx)(r,{size:14}),a?`保存中…`:`保存`]})]})}),(0,k.jsxs)(`div`,{className:`view-body stack`,children:[c?(0,k.jsx)(g,{tone:`error`,children:S(c)}):null,d?(0,k.jsx)(g,{tone:`success`,children:d}):null,b?(0,k.jsx)(g,{tone:`success`,children:b}):null,D?(0,k.jsx)(g,{tone:`success`,children:D}):null,(0,k.jsxs)(`div`,{className:`settings-split`,children:[(0,k.jsx)(`nav`,{className:`settings-nav`,"aria-label":`设置分组`,children:R.map(e=>{let t=H[e.id]??0;return(0,k.jsxs)(`button`,{type:`button`,className:`settings-nav-i${M===e.id?` on`:``}`,"aria-current":M===e.id?`page`:void 0,onClick:()=>N(e.id),children:[(0,k.jsx)(`span`,{className:`settings-nav-label`,children:e.label}),t>0?(0,k.jsx)(`span`,{className:`settings-nav-dirty`,children:t}):null]},e.id)})}),(0,k.jsx)(`div`,{className:`settings-content`,children:t.initial&&t.loading?(0,k.jsx)(v,{children:(0,k.jsx)(x,{kind:`loading`,title:`正在读取配置…`})}):t.error?(0,k.jsx)(v,{children:(0,k.jsx)(x,{kind:`error`,title:`配置没取到`,detail:S(t.error),onRetry:t.reload})}):(0,k.jsxs)(k.Fragment,{children:[M===`access`?(0,k.jsxs)(k.Fragment,{children:[(0,k.jsx)(j,{}),(0,k.jsx)(z,{})]}):null,M===`password`?(0,k.jsxs)(`div`,{className:`card`,children:[(0,k.jsxs)(`div`,{className:`group-head`,children:[(0,k.jsxs)(`h3`,{children:[(0,k.jsx)(e,{size:14,style:{verticalAlign:-2,marginRight:6}}),`管理口令`]}),(0,k.jsx)(`p`,{children:`控制台的唯一入口凭证`})]}),(0,k.jsxs)(`div`,{className:`set-row`,children:[(0,k.jsxs)(`div`,{className:`info`,children:[(0,k.jsx)(`b`,{children:`管理口令`}),(0,k.jsxs)(`span`,{children:[`两种改法:`,(0,k.jsx)(`b`,{children:`随机重置`}),`由服务端生成 16 位新口令(更强,但需当场保存);`,(0,k.jsx)(`b`,{children:`手动设定`}),`由你输入一个方便记忆的口令(至少 8 个字符)。 两种都立即生效、无需重启;新口令不回显、不落浏览器任何位置。`]})]}),(0,k.jsx)(`div`,{className:`ctl`,children:(0,k.jsxs)(`button`,{type:`button`,className:`btn btn-quiet btn-sm`,disabled:a,onClick:()=>E(!0),children:[(0,k.jsx)(e,{size:13}),`修改`]})})]})]}):null,M===`danger`?(0,k.jsxs)(`div`,{className:`card danger-zone`,children:[(0,k.jsxs)(`div`,{className:`group-head`,children:[(0,k.jsx)(`h3`,{style:{color:`var(--warn-amber)`},children:`危险操作`}),(0,k.jsx)(`p`,{children:`不可撤销,需二次确认`})]}),X.map(e=>(0,k.jsxs)(`div`,{className:`set-row`,children:[(0,k.jsxs)(`div`,{className:`info`,children:[(0,k.jsx)(`b`,{children:e.label}),(0,k.jsx)(`span`,{children:e.why})]}),(0,k.jsx)(`div`,{className:`ctl`,children:(0,k.jsx)(`button`,{type:`button`,className:`mini-pill danger`,disabled:a,onClick:()=>_(L[e.key]??null),children:e.label})})]},e.key))]}):null,M===`mapping`&&J?.type===`mapping`?(0,k.jsxs)(v,{title:J.label,aside:(0,k.jsx)(y,{children:`config.yml`}),children:[(0,k.jsx)(`div`,{className:`code`,style:{fontSize:12},children:Object.entries(J.value??{}).map(([e,t])=>(0,k.jsxs)(`div`,{children:[(0,k.jsx)(`span`,{className:`k`,children:e}),` → `,(0,k.jsx)(`span`,{className:`st`,children:t})]},e))}),(0,k.jsx)(`div`,{className:`footer-note`,children:J.why})]}):null,Y&&Y.id!==`danger`&&Y.id!==`mapping`?(0,k.jsx)(U,{group:Y,saving:a,valueOf:W,onChange:(e,t)=>i(n=>({...n,[e]:t}))}):null]})})]})]}),h?(0,k.jsx)(I,{spec:h,onClose:()=>_(null),onDone:q}):null,T?(0,k.jsx)(P,{onClose:()=>E(!1),onDone:()=>{A(`管理口令已更新并立即生效。下次登录请使用新口令。`),setTimeout(()=>A(null),4e3),t.reload()}}):null]})}function U({group:e,saving:t,valueOf:n,onChange:r}){let i=e.items.filter(e=>!B.has(e.key));if(i.length===0)return null;let a=i.filter(e=>!e.noop),o=i.filter(e=>e.noop);return(0,k.jsxs)(`div`,{className:`card`,children:[(0,k.jsxs)(`div`,{className:`group-head`,children:[(0,k.jsx)(`h3`,{children:e.label}),(0,k.jsx)(`p`,{children:W(e.id)})]}),a.map(e=>(0,k.jsx)(G,{item:e,value:n(e.key,e.value),saving:t,onChange:t=>r(e.key,t)},e.key)),o.length>0?(0,k.jsxs)(`details`,{className:`dormant`,children:[(0,k.jsxs)(`summary`,{children:[o.length,` 项暂未生效`,(0,k.jsx)(`span`,{children:`改了不会有任何变化 —— 依赖的功能未实现或上游未供货`})]}),o.map(e=>(0,k.jsx)(G,{item:e,value:n(e.key,e.value),saving:t,onChange:t=>r(e.key,t)},e.key))]}):null]})}function W(e){return{service:`进程监听与启动方式`,credential:`跨提供商的全局策略(部分项仅对 WorkBuddy 生效)`,quota:`积分口径与额度轮询(仅 WorkBuddy;MiniMax 走独立账本,Qoder 无端点)`,signin:`每日 08:05 自动签到(WorkBuddy 可关;MiniMax 恒开,Qoder 无签到)`,limits:`自用场景的保护,而非配额限制`,logs:`留在本机,不参与同步`}[e]??``}function G({item:e,value:t,saving:n,onChange:r}){return(0,k.jsxs)(`div`,{className:`set-row`,children:[(0,k.jsxs)(`div`,{className:`info`,children:[(0,k.jsxs)(`b`,{children:[e.label,e.requiresRestart?(0,k.jsx)(`span`,{style:{marginLeft:8,fontSize:10.5,color:`var(--warn-amber)`},children:`需重启`}):null]}),(0,k.jsx)(`span`,{children:e.why})]}),(0,k.jsx)(`div`,{className:`ctl`,children:(0,k.jsx)(A,{item:e,value:t,disabled:n,onChange:r})})]})}export{H as SettingsPage};
@@ -0,0 +1 @@
1
+ import{A as e,E as t,it as n,r,tt as i}from"./vendor-befEYGHM.js";import{O as a,_ as o,a as s,c,g as l,j as u,k as d,p as f,u as p,v as m,x as h}from"./index-BcWmrhMD.js";import{a as g,c as _,n as v,o as y,r as b,s as x,t as S}from"./Select-Bfquh0d_.js";import{a as C}from"./PageSkeleton-DG-Dj4_9.js";import{n as w,t as T}from"./sharedWindow-FDfq75PI.js";import{t as E}from"./useFx-xcrp_LHB.js";import{n as D,t as O}from"./ClientMetricTip-BqIkh3DO.js";var k=n(),A=i(),j={tokens:`消耗 tokens`,requests:`请求次数`};function M({points:e,metric:t,avg:n}){let[r,i]=(0,k.useState)(null),[a,o]=(0,k.useState)(null),s=(0,k.useRef)(null),c=(0,k.useRef)(null),[u,d]=(0,k.useState)(null);(0,k.useLayoutEffect)(()=>{let t=c.current,n=s.current;if(!t||!n||r===null||e.length===0){d(null);return}let i=()=>{let i=(r+.5)/e.length*n.clientWidth,a=n.getBoundingClientRect(),o=t.getBoundingClientRect(),s=i-(o.left-a.left);d(Math.max(12,Math.min(s,o.width-12)))};return i(),window.addEventListener(`resize`,i),()=>window.removeEventListener(`resize`,i)},[r,t,e.length]);let f=(0,k.useMemo)(()=>e.map((n,r)=>{let i=r>0?e[r-1]:null,a=i?t===`tokens`?n.tokens-i.tokens:n.requests-i.requests:null,o=/T\d{2}$/.test(n.bucket),s=(n.models??[]).slice(0,5).map(e=>`${e.model} ${h(e.tokens)} tokens`).join(`、`),c=a===null?``:` · 较${o?`上一小时`:`昨日`} ${a>0?`增加`:a<0?`减少`:`持平`}${a===0?``:` ${l(Math.abs(a))}`}`;return`${p(n.bucket)} · ${l(n.requests)} 次请求 · ${h(n.tokens)} tokens`+(n.errors>0?` · ${l(n.errors)} 次失败`:``)+(s?` · 模型:${s}`:``)+c}),[e,t]);if(e.length===0)return(0,A.jsx)(`div`,{className:`empty-note`,style:{padding:`24px 0`},children:`该窗口内没有请求记录。`});let m=e.map(e=>t===`tokens`?e.tokens:e.requests),g=Math.max(1,...m),_=l,v=n===null?null:Math.round(Math.min(1,Math.max(0,n/g))*1e4)/1e4,y=Math.ceil(e.length/5),b=a??e.length-1,x=t=>{let n=e.length-1,r;if(t.key===`ArrowRight`)r=Math.min(n,b+1);else if(t.key===`ArrowLeft`)r=Math.max(0,b-1);else if(t.key===`Home`)r=0;else if(t.key===`End`)r=n;else return;t.preventDefault(),o(r),i(r),(s.current?.querySelector(`[data-idx="${r}"]`)??void 0)?.focus()},S=r===null?null:e[r],C=S?/T\d{2}$/.test(S.bucket):!1,w=S&&r!==null&&r>0?e[r-1]:null,T=S&&w?t===`tokens`?S.tokens-w.tokens:S.requests-w.requests:null;return(0,A.jsxs)(A.Fragment,{children:[(0,A.jsxs)(`div`,{className:`avgline`,style:{"--avg":v??0},children:[v===null?null:(0,A.jsxs)(`span`,{className:`avg-row`,children:[(0,A.jsxs)(`span`,{className:`avg-tag`,children:[`日均 `,_(n)]}),(0,A.jsx)(`i`,{className:`avg-rule`})]}),(0,A.jsxs)(`div`,{className:`bars30 js-grow`,ref:s,onKeyDown:x,onMouseLeave:()=>i(null),children:[(0,A.jsxs)(`span`,{className:`grid`,"aria-hidden":`true`,children:[(0,A.jsx)(`i`,{className:`base`}),(0,A.jsx)(`i`,{className:`mid`}),(0,A.jsx)(`i`,{className:`q1`})]}),e.map((n,a)=>{let o=t===`tokens`?n.tokens:n.requests,s=a===e.length-1?`today`:o>=g?`peak`:``,c=n.errors>0,l=f[a];return(0,A.jsx)(`div`,{"data-idx":a,className:`bcol${a===r?` on`:``}`,role:`img`,"aria-label":l,tabIndex:a===b?0:-1,onMouseEnter:()=>i(a),onFocus:()=>i(a),onBlur:()=>i(e=>e===a?null:e),children:(0,A.jsx)(`div`,{className:`b ${s}`.trim()+(c?` err`:``),style:{height:`${Math.max(2,Math.round(o/g*100))}%`},children:c?(0,A.jsx)(`span`,{className:`err-dot`,"aria-hidden":`true`}):null})},n.bucket)}),S?(()=>{let n=r!==null&&e.length>0?(r+.5)/e.length*100:50;return(0,A.jsxs)(`div`,{ref:c,className:`bar-tip${n<12?` tip-left`:n>88?` tip-right`:``}`,style:{"--tip-x":`${n}%`,"--tip-arrow":u===null?void 0:`${u}px`},"aria-hidden":`true`,children:[(0,A.jsxs)(`div`,{className:`bt-head`,children:[(0,A.jsx)(`b`,{children:p(S.bucket)}),r===e.length-1?(0,A.jsx)(`span`,{className:`bt-tag`,children:`最新`}):null]}),(0,A.jsxs)(`div`,{className:`bt-row${t===`tokens`?` hot`:``}`,children:[(0,A.jsx)(`span`,{children:`消耗 tokens`}),(0,A.jsx)(`i`,{children:h(S.tokens)})]}),(S.models??[]).length>0?(0,A.jsx)(`div`,{className:`bt-models`,children:(S.models??[]).map(e=>(0,A.jsxs)(`div`,{className:`bt-model`,children:[(0,A.jsx)(`span`,{className:`bt-model-name`,children:e.model}),(0,A.jsxs)(`i`,{children:[h(e.tokens),(0,A.jsx)(`em`,{children:` · ${S.tokens>0?Math.round(e.tokens/S.tokens*100):0}%`})]})]},e.model))}):null,(0,A.jsxs)(`div`,{className:`bt-row${t===`requests`?` hot`:``}`,children:[(0,A.jsx)(`span`,{children:`请求次数`}),(0,A.jsx)(`i`,{children:l(S.requests)})]}),S.errors>0?(0,A.jsxs)(`div`,{className:`bt-row bt-err`,children:[(0,A.jsx)(`span`,{children:`失败`}),(0,A.jsxs)(`i`,{children:[l(S.errors),(0,A.jsxs)(`em`,{children:[` `,`(`,l(S.requests)===`--`||S.requests===0?`—`:`${(S.errors/S.requests*100).toFixed(1)}%`,`)`]})]})]}):null,T===null?null:(0,A.jsxs)(`div`,{className:`bt-delta${T>0?` up`:T<0?` down`:` flat`}`,children:[`较`,C?`上一小时`:`昨日`,T>0?` ▲`:T<0?` ▼`:` — `,T>0||T<0?l(Math.abs(T)):`持平`]})]})})():null]})]}),(0,A.jsx)(`div`,{className:`axis`,children:e.map((t,n)=>(0,A.jsx)(`span`,{children:n%y===0||n===e.length-1?p(t.bucket):``},t.bucket))})]})}function N({items:e,windowLabel:t}){if(e.length===0)return(0,A.jsxs)(`div`,{className:`empty-note`,children:[t,`没有可拆分的请求。`]});let n=Math.max(1,...e.map(e=>e.value)),r=e=>e?void 0:{fontFamily:`var(--font-body)`};return(0,A.jsx)(`div`,{className:`dist js-stagger js-grow`,children:e.map(e=>(0,A.jsxs)(`div`,{className:`d-row`,children:[e.tip?(0,A.jsx)(s,{content:e.tip,children:(0,A.jsx)(`span`,{className:`d-name`,style:r(e.mono),children:e.label})}):(0,A.jsx)(`span`,{className:`d-name`,style:r(e.mono),children:e.label}),(0,A.jsxs)(`span`,{className:`d-val`,children:[e.format===`credits`?f(e.value):l(e.value),` · `,e.trailing]}),(0,A.jsx)(`span`,{className:`d-track`,children:(0,A.jsx)(`i`,{style:{width:`${Math.max(2,Math.round(e.value/n*100))}%`}})})]},e.key))})}function P({row:e}){let t=e.models??[],n=Math.max(0,(e.modelCount??t.length)-t.length),r=Math.max(0,e.tokens??0),i=e.client??`未归属`;return(0,A.jsxs)(`div`,{className:`client-model-tip`,children:[(0,A.jsxs)(`div`,{className:`client-model-tip-head`,children:[(0,A.jsxs)(`div`,{className:`client-model-tip-title`,children:[(0,A.jsx)(`strong`,{children:i}),(0,A.jsx)(`span`,{children:`模型消耗明细`})]}),(0,A.jsx)(`span`,{className:`client-model-tip-tag`,children:`按模型`})]}),(0,A.jsxs)(`div`,{className:`client-model-tip-summary`,children:[(0,A.jsxs)(`div`,{children:[(0,A.jsx)(`span`,{children:`总 tokens`}),(0,A.jsx)(`b`,{children:h(r)})]}),(0,A.jsxs)(`div`,{children:[(0,A.jsx)(`span`,{children:`总积分`}),(0,A.jsx)(`b`,{children:f(e.credits)})]})]}),t.length>0?(0,A.jsx)(`div`,{className:`client-model-tip-list`,children:t.map((e,t)=>{let n=r>0?e.tokens/r:0,i=e.displayName??e.model,a=!!(e.displayName&&e.displayName!==e.model);return(0,A.jsxs)(`div`,{className:`client-model-tip-row`,children:[(0,A.jsxs)(`div`,{className:`client-model-tip-row-head`,children:[(0,A.jsx)(`span`,{className:`client-model-tip-rank`,children:String(t+1).padStart(2,`0`)}),(0,A.jsxs)(`div`,{className:`client-model-tip-name`,children:[(0,A.jsx)(`strong`,{children:i}),a?(0,A.jsx)(`span`,{children:e.model}):null]}),(0,A.jsxs)(`b`,{children:[h(e.tokens),` `,(0,A.jsx)(`em`,{children:`tokens`})]})]}),(0,A.jsxs)(`div`,{className:`client-model-tip-row-meta`,children:[(0,A.jsx)(`span`,{className:`client-model-tip-track`,children:(0,A.jsx)(`i`,{style:{width:`${Math.max(0,Math.min(100,n*100))}%`}})}),(0,A.jsx)(`span`,{children:o(n)}),(0,A.jsxs)(`span`,{children:[l(e.requests),` 次`]}),(0,A.jsxs)(`span`,{children:[f(e.credits),` 积分`]})]})]},e.model)})}):(0,A.jsx)(`div`,{className:`client-model-tip-empty`,children:`当前窗口没有可拆分的模型记录。`}),n>0?(0,A.jsxs)(`div`,{className:`client-model-tip-note`,children:[`另有 `,n,` 个模型未展开,完整明细见「按模型消耗明细」。`]}):null]})}function F({items:e,windowLabel:t}){return e.length===0?(0,A.jsxs)(`div`,{className:`empty-note`,style:{padding:`8px 0`},children:[t,`没有按模型的消耗记录。`]}):(0,A.jsxs)(A.Fragment,{children:[(0,A.jsx)(`div`,{className:`tbl-scroll`,children:(0,A.jsxs)(`table`,{className:`tbl`,children:[(0,A.jsxs)(`caption`,{className:`sr-only`,children:[`按模型的 token 消耗明细,共 `,e.length,` 个模型`]}),(0,A.jsx)(`thead`,{children:(0,A.jsxs)(`tr`,{children:[(0,A.jsx)(`th`,{scope:`col`,children:`模型`}),(0,A.jsx)(`th`,{scope:`col`,className:`r`,children:`请求次数`}),(0,A.jsx)(`th`,{scope:`col`,className:`r`,children:`Token 消耗`}),(0,A.jsx)(`th`,{scope:`col`,className:`r`,children:`Token 占比`}),(0,A.jsx)(`th`,{scope:`col`,className:`r`,children:`消耗积分`}),(0,A.jsx)(`th`,{scope:`col`,className:`r`,children:`平均单次 Token`})]})}),(0,A.jsx)(`tbody`,{children:e.map(e=>{let t=e.displayName??e.model??`未知模型`;return(0,A.jsxs)(`tr`,{children:[(0,A.jsxs)(`td`,{className:`td-strong`,children:[t,e.tag?(0,A.jsx)(`span`,{className:`mu-tag`,children:e.tag}):null,e.multiplier==null?(0,A.jsx)(s,{content:`接口与本地快照都缺此模型倍率 —— 该行积分按中性倍率估算,不是上游真实计费`,children:(0,A.jsx)(`span`,{className:`mu-unknown`,children:`倍率未知`})}):null]}),(0,A.jsx)(`td`,{className:`r td-mono`,children:l(e.requests)}),(0,A.jsx)(`td`,{className:`r td-mono`,children:h(e.tokens??0)}),(0,A.jsx)(`td`,{className:`r td-mono`,children:o(e.share)}),(0,A.jsx)(`td`,{className:`r td-mono`,children:e.credits===null?(0,A.jsx)(s,{content:e.creditsUnknownCount?`本窗口 ${l(e.creditsUnknownCount)} 条请求上游均未回报单次费用(该上游只在账本给累计值)。真实消耗见上方「积分账本」。`:`上游未回报单次费用。真实消耗见上方「积分账本」。`,children:(0,A.jsx)(`span`,{className:`cred-unknown`,children:`--`})}):f(e.credits)}),(0,A.jsx)(`td`,{className:`r td-mono`,children:e.requests>0?h(Math.round((e.tokens??0)/e.requests)):`--`})]},e.model??t)})})]})}),(0,A.jsxs)(`div`,{className:`footer-note`,children:[`平均单次 = Token 消耗 ÷ 请求次数。接口不提供按模型的耗时,「较昨日」与「本计费周期」也无对应字段 —— 这三样一律留空而不是补一个看着合理的数。`,(0,A.jsx)(`br`,{}),`标着`,(0,A.jsx)(`b`,{children:`「倍率未知」`}),`的行,是 /v3/config 接口与本地快照都没有的模型:`,(0,A.jsx)(`b`,{children:`该行积分是按中性倍率估算的,不是上游真实计费`}),`。`]})]})}var I={ok:`额度接口正常`,quota_endpoint_not_configured:`未配置额度端点`,quota_endpoint_error:`额度端点拉取失败`};function L({quota:n,provenance:i,windowLabel:a}){let o=n.available&&n.remain!==null;return(0,A.jsxs)(g,{title:`配额数据来源`,aside:(0,A.jsx)(_,{tone:n.available?`live`:`amber`,dot:!0,children:I[n.reason]}),children:[(0,A.jsxs)(`div`,{className:`src-grid`,children:[(0,A.jsxs)(`div`,{className:`src-col`,children:[(0,A.jsxs)(`div`,{className:`src-head`,children:[(0,A.jsx)(t,{size:13,"aria-hidden":!0}),`来自上游额度接口`,(0,A.jsx)(`span`,{className:`tag tag-live`,children:`官方口径`})]}),(0,A.jsxs)(`ul`,{children:[(0,A.jsxs)(`li`,{children:[(0,A.jsx)(`b`,{children:`剩余积分`}),(0,A.jsx)(`i`,{children:`quota.remain`})]}),(0,A.jsxs)(`li`,{children:[(0,A.jsx)(`b`,{children:`总量`}),(0,A.jsx)(`i`,{children:`quota.total`})]}),(0,A.jsxs)(`li`,{children:[(0,A.jsx)(`b`,{children:`重置时间`}),(0,A.jsx)(`i`,{children:`quota.resetAt`})]})]}),(0,A.jsx)(`div`,{className:`src-state`,children:o?n.stale?(0,A.jsxs)(A.Fragment,{children:[(0,A.jsx)(r,{size:13,"aria-hidden":!0}),`上次拉取失败,当前显示的是上一次成功值(不会清空)。`]}):`已接入,随配额端点轮询刷新。`:(0,A.jsxs)(A.Fragment,{children:[`未接入 —— 上面三项显示 `,(0,A.jsx)(`i`,{children:`--`}),`。服务端不做估算,前端更不会替它编一个。`]})})]}),(0,A.jsxs)(`div`,{className:`src-col`,children:[(0,A.jsxs)(`div`,{className:`src-head`,children:[(0,A.jsx)(e,{size:13,"aria-hidden":!0}),`本机按请求累计`,(0,A.jsx)(`span`,{className:`tag tag-off`,children:`非官方口径`})]}),(0,A.jsxs)(`ul`,{children:[(0,A.jsxs)(`li`,{children:[(0,A.jsx)(`b`,{children:`已消耗积分`}),(0,A.jsx)(`i`,{children:`仅统计经本服务转发的请求,按上游实扣累加(官方客户端直连不计入)`})]}),(0,A.jsxs)(`li`,{children:[(0,A.jsxs)(`b`,{children:[a,`趋势`]}),(0,A.jsx)(`i`,{children:`本机日志按天聚合`})]}),(0,A.jsxs)(`li`,{children:[(0,A.jsx)(`b`,{children:`按模型 / 按提供商消耗`}),(0,A.jsx)(`i`,{children:`同一次聚合的一体两面`})]})]}),(0,A.jsx)(`div`,{className:`src-state`,children:`这些数即时产生,不等额度接口 —— 也正是它和「剩余积分」会对不齐的原因。`})]})]}),n.message?(0,A.jsx)(`div`,{className:`footer-note`,children:n.message}):null,(0,A.jsx)(`div`,{className:`footer-note`,children:i.note}),(0,A.jsxs)(`div`,{className:`footer-note`,children:[`官方额度接口按 `,(0,A.jsx)(`span`,{className:`code-chip`,children:`quota.pollSeconds`}),`(默认 `,(0,A.jsx)(`b`,{children:`30 秒`}),`)轮询, 所以「剩余积分」最多滞后 30 秒;本机累计的消耗是即时的。 两者最多相差 `,(0,A.jsx)(`b`,{children:`30 秒内的消耗量`}),` —— 这是取样时刻不同,不是账对不上。 来源标记:已消耗积分 `,(0,A.jsx)(`span`,{className:`code-chip`,children:i.creditsUsed}),` · `,`剩余积分 `,(0,A.jsx)(`span`,{className:`code-chip`,children:i.quotaRemain}),`。`]})]})}var R=`today`,z={today:null,"1h":null,"24h":null,"7d":7,"30d":30};function B(){let[e,t]=(0,k.useState)(()=>T()??R),n=u(()=>c.overview(e),[e],{cacheKey:`overview:${e}`});E(`usage-${e}-${n.data?`ready`:`pending`}`);let[r,i]=(0,k.useState)(`tokens`),s=n.data,p=z[e],I=s&&p?s.metrics.creditsUsed/p:null,B=s&&p?s.metrics.requests/p:null,V=s&&p?s.metrics.totalTokens/p:null,H=s?[...s.byModel].sort((e,t)=>(t.tokens??0)-(e.tokens??0)):[],U=s?[...s.byClient].sort((e,t)=>(t.tokens??0)-(e.tokens??0)):[],W=s&&s.quota.available&&s.quota.remain!==null&&I!==null&&I>0?Math.floor(s.quota.remain/I):null,G=s?s.quota.available?I===null||I<=0?`${a[s.window]}无消耗记录`:`按日均 ${f(I)} 积分估算`:`需要额度接口`:void 0,K=e=>{if(!s||s.byClient.length===0)return;let t=[...s.byClient].sort((t,n)=>(n[e]??0)-(t[e]??0));return(0,A.jsx)(O,{rows:t,metric:e,windowLabel:a[s.window],total:e===`credits`?s.metrics.creditsUsed:e===`tokens`?s.metrics.totalTokens:s.metrics.requests,totalCount:t.length})};return(0,A.jsxs)(`div`,{className:`view on`,children:[(0,A.jsx)(x,{title:`积分与用量`,status:s?(0,A.jsxs)(_,{tone:`live`,dot:!0,children:[a[s.window],` · `,m(s.generatedAt)]}):null,actions:(0,A.jsx)(S,{value:e,options:d,onChange:e=>{w(e),t(e)},width:148})}),(0,A.jsx)(`div`,{className:`view-body stack`,children:n.initial&&n.loading?(0,A.jsx)(C,{}):n.error?(0,A.jsx)(g,{children:(0,A.jsx)(v,{kind:`error`,title:`用量数据没取到`,detail:b(n.error),onRetry:n.reload})}):s?(0,A.jsxs)(A.Fragment,{children:[(0,A.jsx)(D,{metrics:s.metrics}),(0,A.jsx)(y,{items:[{label:`${a[s.window]}消耗`,value:f(s.metrics.creditsUsed),detail:`经本服务转发 · 上游实扣累计`,tip:K(`credits`),tipPos:`down`},{label:`${a[s.window]}请求`,value:l(s.metrics.requests),detail:`${l(s.metrics.activeClients)} 个密钥活跃`,tip:K(`requests`),tipPos:`down`},...I===null?[{label:`本窗口总 tokens`,value:h(s.metrics.totalTokens),detail:`输入 ${h(s.metrics.promptTokens)} · 输出 ${h(s.metrics.completionTokens)}`,tip:K(`tokens`),tipPos:`down`}]:[{label:`日均消耗`,value:f(I),detail:`${a[s.window]}消耗 ÷ ${p} 天`,tip:K(`credits`),tipPos:`down`},{label:`按当前速度可用天数`,value:W===null?`—`:l(W),detail:G,tone:s.quota.available?void 0:`amber`}]]}),(0,A.jsx)(g,{title:`${a[s.window]}趋势`,aside:(0,A.jsxs)(`span`,{className:`panel-aside-row`,children:[(0,A.jsx)(`span`,{className:`seg-tabs`,role:`group`,"aria-label":`趋势口径`,children:[`tokens`,`requests`].map(e=>(0,A.jsx)(`button`,{type:`button`,className:r===e?`on`:``,"aria-pressed":r===e,onClick:()=>i(e),children:e===`tokens`?`Token`:`请求数`},e))}),(0,A.jsxs)(_,{children:[`单位:`,j[r],` `,e===`1h`||e===`24h`||e===`today`?`/ 小时`:`/ 天`]})]}),padded:!1,children:(0,A.jsx)(`div`,{style:{padding:`0 20px 18px`},children:(0,A.jsx)(M,{points:s.trend,metric:r,avg:r===`tokens`?V:B})})}),(0,A.jsx)(g,{title:`按模型消耗明细`,aside:(0,A.jsx)(_,{children:`按 Token 排序`}),padded:!1,children:(0,A.jsx)(`div`,{style:{padding:`0 20px 18px`},children:(0,A.jsx)(F,{items:H,windowLabel:a[s.window]})})}),(0,A.jsxs)(g,{title:`按提供商消耗`,aside:(0,A.jsx)(_,{children:`按 Token 排序`}),children:[(0,A.jsx)(N,{windowLabel:a[s.window],items:U.map(e=>({key:e.clientId??`—`,label:e.client??`未识别`,value:e.tokens??0,format:`int`,trailing:`${o(e.share)} · ${f(e.credits)} 积分 · ${l(e.requests)} 次`,tip:(0,A.jsx)(P,{row:e})}))}),(0,A.jsx)(`div`,{className:`footer-note`,children:`「未识别」是正常的识别分支,不是错误 —— 没绑定密钥又没匹配到特征时归到这里。`})]}),(0,A.jsx)(L,{quota:s.quota,provenance:s.provenance,windowLabel:a[s.window]})]}):null})]})}export{B as UsagePage};
@@ -1,2 +1,2 @@
1
- const __vite__mapDeps=(i,m=__vite__mapDeps,d=(m.f||(m.f=["./LandingPage-P2QNDFaP.js","./vendor-befEYGHM.js","./accessUrl-DbL5DLDz.js","./LandingPage-B2hMgbmZ.css","./OverviewPage-BgBo_XhF.js","./Select-G6AhT0TA.js","./PageSkeleton-DG-Dj4_9.js","./sharedWindow-FDfq75PI.js","./useFx-xcrp_LHB.js","./ClientMetricTip-C2VuiT4-.js","./UsagePage-cxZ-GnpO.js","./ClientsPage-Dy68uQDl.js","./Modal-B-rIrvXS.js","./useFocusTrap-Cj84bnpH.js","./Drawer-CleQGhRU.js","./Switch-0KA1AbiV.js","./ApiKeysPage-Ck0Gry6E.js","./RequestsPage-CVB0wpCH.js","./SettingsPage-B4Mew-7b.js"])))=>i.map(i=>d[i]);
2
- import{$ as e,D as t,F as n,O as r,P as i,S as a,T as o,U as s,Y as c,b as l,c as u,d,it as f,nt as p,r as m,rt as h,s as g,tt as _,v,x as y,y as b}from"./vendor-befEYGHM.js";(function(){let e=document.createElement(`link`).relList;if(e&&e.supports&&e.supports(`modulepreload`))return;for(let e of document.querySelectorAll(`link[rel="modulepreload"]`))n(e);new MutationObserver(e=>{for(let t of e)if(t.type===`childList`)for(let e of t.addedNodes)e.tagName===`LINK`&&e.rel===`modulepreload`&&n(e)}).observe(document,{childList:!0,subtree:!0});function t(e){let t={};return e.integrity&&(t.integrity=e.integrity),e.referrerPolicy&&(t.referrerPolicy=e.referrerPolicy),t.credentials=e.crossOrigin===`use-credentials`?`include`:e.crossOrigin===`anonymous`?`omit`:`same-origin`,t}function n(e){if(e.ep)return;e.ep=!0;let n=t(e);fetch(e.href,n)}})();var x=f(),S=p();function C(e=window.location.pathname){let t=e.replace(/\/+$/,``)||`/`;return t===`/console`||t.startsWith(`/console/`)?`console`:`landing`}function w(e=!1){let{pathname:t,hash:n}=window.location;if(C(t)===`console`||!n.startsWith(`#/`))return;let r=`/console${n}`;e?window.location.replace(r):window.history.replaceState(null,``,r)}function T(){window.addEventListener(`hashchange`,()=>w(!0))}var E=`relay.theme`,D=`system`;function O(){try{return window.matchMedia?.(`(prefers-color-scheme: light)`).matches?`light`:`dark`}catch{return`dark`}}function k(e,t=window.location.pathname,n=window.location.hash){return e===`system`?O():e}function A(){try{let e=window.localStorage.getItem(E);return e===`light`||e===`dark`||e===`system`?e:D}catch{return D}}function ee(e){document.documentElement.dataset.theme=e}var j=null,M=new Set;function N(){if(j===null){let e=document.documentElement.dataset.theme,t=A();j={theme:e===`light`||e===`dark`?e:k(t),preference:t}}return j}function P(e){return M.add(e),()=>M.delete(e)}function te(e){try{window.localStorage.setItem(E,e)}catch{}F()}function F(){let e=A(),t=k(e);ee(t),j={theme:t,preference:e},M.forEach(e=>e())}typeof window<`u`&&(window.matchMedia?.(`(prefers-color-scheme: light)`).addEventListener?.(`change`,()=>{A()===`system`&&F()}),window.addEventListener(`storage`,e=>{(e.key===null||e.key===E)&&F()}));var I=[`overview`,`usage`,`clients`,`keys`,`requests`,`settings`];function L(e){let t=e.replace(/^#\/?/,``).split(`?`)[0];return I.includes(t)?t:`overview`}function ne(){let[e,t]=(0,x.useState)(()=>L(window.location.hash));return(0,x.useEffect)(()=>{let e=()=>t(L(window.location.hash));return window.addEventListener(`hashchange`,e),()=>window.removeEventListener(`hashchange`,e)},[]),{route:e,navigate:e=>{window.location.hash=`#/${e}`}}}var R=class extends Error{code;status;retryAfterSeconds;constructor(e,t,n,r){super(e),this.name=`ApiError`,this.code=t,this.status=n,this.retryAfterSeconds=r}get isSessionExpired(){return this.code===40102}},z=new Set;function re(e){return z.add(e),()=>z.delete(e)}function ie(e){z.forEach(t=>t(e))}async function ae(e){let t=await e.text(),n=null;try{n=t?JSON.parse(t):null}catch{throw new R(`服务端返回了非 JSON 响应(HTTP ${e.status})`,0,e.status)}if(!n||typeof n.code!=`number`)throw new R(`响应缺少统一信封(HTTP ${e.status})`,0,e.status);if(n.code===0)return n.data;let r=n.data?.retryAfterSeconds;throw new R(n.message||`请求失败(code ${n.code})`,n.code,e.status,r)}var B=2e4;function oe(e,t){let n=new AbortController,r=!1,i=()=>n.abort(e?.reason);e&&(e.aborted?n.abort(e.reason):e.addEventListener(`abort`,i,{once:!0}));let a=t===null?void 0:setTimeout(()=>{r=!0,n.abort()},t);return{signal:n.signal,isTimedOut:()=>r,dispose:()=>{a!==void 0&&clearTimeout(a),e?.removeEventListener(`abort`,i)}}}function se(e){return e instanceof DOMException&&e.name===`AbortError`}async function V(e,t){let n=(t?.method??`GET`).toUpperCase(),r=oe(t?.signal,n===`GET`?B:null),i=new Headers(t?.headers);i.has(`accept`)||i.set(`Accept`,`application/json`),t?.body&&!i.has(`content-type`)&&i.set(`Content-Type`,`application/json`);let a;try{a=await fetch(e,{...t,signal:r.signal,credentials:`same-origin`,headers:i})}catch(e){throw r.dispose(),r.isTimedOut()?new R(`请求超时(${B/1e3}s 无响应),稍后重试。`,0,0):se(e)?e:new R(`连不上本机服务。确认后端已在 127.0.0.1:8787 启动。`,0,0)}try{let e=await ae(a);if(!a.ok)throw new R(`请求失败(HTTP ${a.status})`,0,a.status);return e}catch(e){throw r.isTimedOut()?new R(`请求超时(${B/1e3}s 无响应),稍后重试。`,0,0):e}finally{r.dispose()}}async function H(e,t){try{return await V(e,t)}catch(e){throw e instanceof R&&e.isSessionExpired&&ie(e),e}}function U(e){let t=new URLSearchParams;Object.entries(e).forEach(([e,n])=>{n!=null&&n!==``&&t.set(e,String(n))});let n=t.toString();return n?`?${n}`:``}var W=new Map,G=new Map;function ce(){W.clear(),G.clear()}function le(e,t){W.has(e)&&W.set(e,t(W.get(e)))}function ue(e,t,n){let r=G.get(e);if(r&&!n)return r;let i=t().then(t=>(G.get(e)===i&&W.set(e,t),t));return G.set(e,i),i.finally(()=>{G.get(e)===i&&G.delete(e)}).catch(()=>{}),i}function de(e,t,n={}){let r=n.enabled??!0,i=n.cacheKey,a=r&&i!==void 0&&W.has(i),[o,s]=(0,x.useState)(()=>a?W.get(i):null),[c,l]=(0,x.useState)(null),[u,d]=(0,x.useState)(r),[f,p]=(0,x.useState)(!a),m=(0,x.useRef)(0),h=(0,x.useRef)(e);h.current=e;let g=(0,x.useRef)(i);g.current=i;let _=(0,x.useCallback)(e=>{let t=++m.current,n=g.current;d(!0),(n===void 0?h.current():ue(n,()=>h.current(),e)).then(e=>{t===m.current&&(s(e),l(null),d(!1),p(!1))},e=>{t!==m.current||se(e)||(l(e instanceof R?e:new R(String(e),0,0)),d(!1),p(!1))})},[]);return(0,x.useEffect)(()=>{if(!r){m.current+=1,s(null),l(null),d(!1),p(!0);return}i!==void 0&&W.has(i)&&(s(W.get(i)),l(null),p(!1)),_(!1)},[r,i,...t]),{data:o,error:c,loading:u,initial:f,reload:(0,x.useCallback)(()=>_(!0),[_])}}var fe={today:`今日`,"1h":`最近 1 小时`,"24h":`最近 24 小时`,"7d":`最近 7 天`,"30d":`最近 30 天`},pe=Object.keys(fe).map(e=>({value:e,label:fe[e]}));function me(e,t){return t&&new Date(t).getTime()<Date.now()?`exp`:e?`live`:`off`}var he={live:`启用`,off:`已停用`,exp:`已过期`},ge=new Intl.NumberFormat(`zh-CN`),_e=new Intl.NumberFormat(`zh-CN`,{minimumFractionDigits:2,maximumFractionDigits:2});function ve(e){return e==null||Number.isNaN(e)?`--`:ge.format(Math.round(e))}function ye(e){return e==null||Number.isNaN(e)?`--`:_e.format(e)}function be(e,t=1){return e==null||Number.isNaN(e)?`--`:`${(e*100).toFixed(t)}%`}function xe(e,t=1){return`${((Number.isFinite(e)?Math.max(0,Math.min(1,e)):0)*100).toFixed(t)}%`}var Se=[{limit:0x38d7ea4c68000,div:0x38d7ea4c68000,digits:2,suffix:`Q`},{limit:0xe8d4a51000,div:0xe8d4a51000,digits:2,suffix:`T`},{limit:1e9,div:1e9,digits:2,suffix:`B`},{limit:1e6,div:1e6,digits:2,suffix:`M`},{limit:1e3,div:1e3,digits:1,suffix:`K`}];function Ce(e){if(e==null||Number.isNaN(e))return`--`;let t=Math.round(e),n=Se.find(e=>Math.abs(t)>=e.limit);return n?`${(t/n.div).toFixed(n.digits)}${n.suffix}`:String(t)}function we(e){return e==null||Number.isNaN(e)?`--`:e<1e3?`${Math.round(e)}ms`:e<6e4?`${(e/1e3).toFixed(1)}s`:`${Math.floor(e/6e4)}m${Math.round(e%6e4/1e3)}s`}function Te(e,t,n){let r=e??0;if(r<=0||t==null||t<=0)return null;let i=n==null?t:t-n;return i<=0?null:r/(i/1e3)}function Ee(e){return e==null||Number.isNaN(e)?`--`:`${e.toFixed(1)} t/s`}function De(e){if(!e)return`--`;let t=new Date(e);return Number.isNaN(t.getTime())?`--`:t.toLocaleTimeString(`zh-CN`,{hour12:!1})}function Oe(e){if(!e)return`--`;let t=new Date(e);return Number.isNaN(t.getTime())?`--`:`${t.toLocaleDateString(`zh-CN`)} ${t.toLocaleTimeString(`zh-CN`,{hour12:!1})}`}function ke(e){if(!e)return`--`;let t=new Date(e).getTime();if(Number.isNaN(t))return`--`;let n=Date.now()-t;if(n<0){let e=-n;return e<6e4?`马上`:e<36e5?`${Math.floor(e/6e4)} 分钟后`:e<864e5?`${Math.floor(e/36e5)} 小时后`:`${Math.floor(e/864e5)} 天后`}let r=Math.floor(n/6e4);if(r<1)return`刚刚`;if(r<60)return`${r} 分钟前`;let i=Math.floor(r/60);if(i<24)return`${i} 小时前`;let a=Math.floor(i/24);return a<30?`${a} 天前`:`${Math.floor(a/30)} 个月前`}function Ae(e){let t=e.match(/^(\d{4})-(\d{2})-(\d{2})(?:T(\d{2}))?/);if(!t)return e.slice(5,10);let n=`${Number(t[2])}/${Number(t[3])}`;return t[4]===void 0?n:`${n} ${Number(t[4])}时`}function je(e){switch(e.type){case`all`:return`全部模型`;case`family`:return`仅 ${e.value} 系`;case`tag`:return`仅 ${e.value}`;case`models`:return`指定 ${e.value.length} 个模型`;default:return`未知范围`}}var Me=`upstream_credential_invalid`;function Ne(e,t=Me){return e.split(`,`).includes(t)}function Pe(e,t=``){return Ne(t)||e===401?`fatal`:e>=400?`warn`:`live`}var Fe={[Me]:`上游访问密钥失效`,"upstream unreachable":`上游不可达`,"upstream empty body":`上游返回空响应`,upstream_error:`上游错误`,"bad request body":`请求体不合法`,"model not permitted":`模型未授权`,"model not found":`模型不存在`,"concurrency limit":`本机并发上限`,"rate limited":`命中上游限流`,rate_limited:`命中上游限流`,"upstream timeout":`上游超时`,model_not_available:`账号未开通此模型`,invalid_max_tokens:`max_tokens 不合法`,context_length_exceeded:`上下文超限`,upstream_11101:`上游要求强制流式`,upstream_11128:`上游渠道校验拒绝(提示指纹)`,retried:`已自动重试`,"cache hit":`命中缓存`,system_injected:`已补 system`,developer_role_normalized:`已规范 developer 角色`,stream_options_stripped:`已移除 stream_options`,sysprompt_degraded_retry:`命中渠道校验,已降级重试`,stream_aborted:`流式中断`,client_detached:`客户端已断开`,usage_missing:`上游未返回用量`,"minimax tokens unavailable":`MiniMax token 不可用`,"token refresh failed":`上游 token 刷新失败`,"missing credential":`缺少上游访问凭证`,"wb oauth unavailable":`WorkBuddy 授权服务不可用`,"missing wb oauth credential":`WorkBuddy 未导入授权`,"wb token refresh failed":`WorkBuddy 授权刷新失败`,"qoder credential invalid":`Qoder 凭证无效`,"multiplier-unknown":`倍率未知(历史:积分按中性估算)`,cache_discounted:`缓存命中已按折扣计(历史)`,credits_from_upstream:`上游实扣积分`,credits_unknown:`上游未回报积分`,credits_recalibrated:`历史积分已重算`,estimate_voided:`历史估算已作废(上游未回报)`};function Ie(e){if(!e)return`-`;let t=e.split(`,`)[0];return Fe[t]??t}function Le(e){return e?e.split(`,`).map(e=>e.trim()).filter(Boolean).map(e=>Fe[e]??e):[]}function Re(e){return e.upstreamCode===11102?`11102:当前账号未开通该模型。该项已在模型表标为未验证,不会自动删除——订阅变动后可能再开。`:e.upstreamCode===11128?`11128:上游返回业务码 11128(上游原文「Illegal API invocation from an unapproved channel」):本次请求的 system 提示命中了上游对第三方客户端模板的指纹校验。本服务已在转发前改写模板行,并在被拒时自动降级为中性提示重试一次,均未通过;请检查「客户端与密钥 → 提供商 → system 提示改写」是否被关闭,或把该请求的特征反馈给维护者。`:e.upstreamCode===11101?`11101:上游拒绝了非流式请求。本服务已强制改写为流式,出现此码说明上游协议变更。`:e.upstreamCode===11133?`11133:max_tokens 过小。已提升到下限后重试一次。`:Ne(e.note)?`上游访问密钥失效是这套方案唯一会让服务停摆的状态:所有客户端共用同一把上游访问密钥,它一失效即整体不可用。去「客户端与密钥 → 提供商」的「修改」里换新。`:null}var ze=[{displayName:`Hy4 preview`,id:`hy4-preview`,tag:`限时免费`,multiplier:0},{displayName:`Hy3`,id:`hy3`,tag:`限时免费`,multiplier:0},{displayName:`Space-Bunny`,id:`space-bunny`,tag:`限时折扣`,multiplier:.03},{displayName:`Deepseek-V4.1-Flash`,id:`deepseek-v4.1-flash`,tag:null,multiplier:.11},{displayName:`Deepseek-V4-Pro`,id:`deepseek-v4-pro`,tag:null,multiplier:.51},{displayName:`GLM-5.3`,id:`glm-5.3`,tag:`订阅优先`,multiplier:.79},{displayName:`GLM-5.3-Flash`,id:`glm-5.3-flash`,tag:`订阅优先`,multiplier:.06},{displayName:`GLM-5.3-FlashX`,id:`glm-5.3-flashx`,tag:`订阅优先`,multiplier:.14},{displayName:`GLM-5.2`,id:`glm-5.2`,tag:null,multiplier:.79},{displayName:`GLM-5.1`,id:`glm-5.1`,tag:null,multiplier:.79},{displayName:`GLM-5v-Turbo`,id:`glm-5v-turbo`,tag:null,multiplier:.71},{displayName:`MiniMax-M3`,id:`minimax-m3`,tag:null,multiplier:.25},{displayName:`Kimi-K3`,id:`kimi-k3`,tag:`订阅优先`,multiplier:1.62},{displayName:`Kimi-K2.8-Preview`,id:`kimi-k2.8-preview`,tag:`订阅优先`,multiplier:.77},{displayName:`Kimi-K2.7-Code`,id:`kimi-k2.7`,tag:null,multiplier:.57},{displayName:`Kimi-K2.6`,id:`kimi-k2.6`,tag:null,multiplier:.52},{displayName:`Step-5-Preview`,id:`step-5-preview`,tag:`订阅优先`,multiplier:.43},{displayName:`Kimi-K3-1`,id:`kimi-k3-1`,tag:`订阅优先`,multiplier:null}],Be=new Set([`kimi-k3-1`]),Ve=new Set([`step-5-preview`]);function He(e){return Be.has(e)?`upstream`:Ve.has(e)?`manual`:`seed`}var Ue={source:`seed`,fetchedAt:new Date(Date.now()-72e5).toISOString(),upstreamReachable:!0,models:ze.map(e=>({...e,family:e.id.split(`-`)[0],source:He(e.id),provider:e.id.startsWith(`MiniMax-`)||e.id.startsWith(`minimax-`)?`MiniMax Code`:`WorkBuddy`,verified:e.id===`glm-5.1`||e.id===`hy3`?0:1,enabled:!0,lastVerifiedAt:new Date(Date.now()-72e5).toISOString()}))},We=[{id:`k_8f21`,name:`Claude Code`},{id:`k_1b83`,name:`Cherry Studio`},{id:`k_9d02`,name:`Cursor`},{id:`k_c3a5`,name:`Cron Job`},{id:`k_77c1`,name:`手机端(临时)`},{id:`unidentified`,name:`未识别客户端`}];function Ge(){let e=Date.now(),t={ipWhitelist:[],maxIps:null,tokenQuota:null,usedIps:0,usedTokens:0};return[{...t,id:`k_8f21`,name:`Claude Code · 本机`,hint:`sk-waygate-4f9c…7a2e`,scope:{type:`all`},client:`Claude Code`,clients:[`Claude Code`],enabled:!0,expiresAt:null,createdAt:new Date(e-11232e5).toISOString(),lastSeenAt:new Date(e-4e4).toISOString(),requests24h:760},{...t,maxIps:3,tokenQuota:2e6,usedIps:2,usedTokens:1234567,id:`k_1b83`,name:`Cherry Studio`,hint:`sk-waygate-1b83…c40f`,scope:{type:`all`},client:`Cherry Studio`,clients:[`Cherry Studio`],enabled:!0,expiresAt:null,createdAt:new Date(e-9504e5).toISOString(),lastSeenAt:new Date(e-9e4).toISOString(),requests24h:324},{...t,id:`k_9d02`,name:`Cursor · 笔记本`,hint:`sk-waygate-9d02…3ee1`,scope:{type:`family`,value:`kimi`},client:`Cursor`,clients:[`Cursor`,`Claude Code`],enabled:!0,expiresAt:null,createdAt:new Date(e-7776e5).toISOString(),lastSeenAt:new Date(e-108e5).toISOString(),requests24h:154},{...t,id:`k_c3a5`,name:`Cron Job · 定时任务`,hint:`sk-waygate-c3a5…91d7`,scope:{type:`family`,value:`deepseek`},client:`Cron Job`,clients:[`Cron Job`],enabled:!0,expiresAt:null,createdAt:new Date(e-6912e5).toISOString(),lastSeenAt:new Date(e-3e5).toISOString(),requests24h:78},{...t,ipWhitelist:[`192.168.1.0/24`],id:`k_77c1`,name:`手机端(临时)`,hint:`sk-waygate-77c1…b8f0`,scope:{type:`all`},client:`手机端(临时)`,clients:[`手机端(临时)`],enabled:!1,expiresAt:null,createdAt:new Date(e-2592e6).toISOString(),lastSeenAt:new Date(e-2592e5).toISOString(),requests24h:0},{...t,id:`k_2e6b`,name:`测试脚本 · 本地`,hint:`sk-waygate-2e6b…0a13`,scope:{type:`tag`,value:`夜间折扣`},client:null,clients:[],enabled:!0,expiresAt:new Date(e-1728e5).toISOString(),createdAt:new Date(e-3456e6).toISOString(),lastSeenAt:new Date(e-10368e5).toISOString(),requests24h:0},{...t,id:`k_5d7f`,name:`家人共享 · 只读`,hint:`sk-waygate-5d7f…22c8`,scope:{type:`models`,value:[`glm-5.3`,`kimi-k2.7`]},client:null,clients:[],enabled:!1,expiresAt:null,createdAt:new Date(e-1728e6).toISOString(),lastSeenAt:new Date(e-432e6).toISOString(),requests24h:0}]}We.filter(e=>e.id!==`unidentified`).map(e=>e.name),Ge(),new Date().toISOString(),Date.now()+1728e6,Date.now()+22464e5,new Date().toISOString().slice(0,10),new Date(Date.now()-18e5).toISOString(),new Date(Date.now()-216e5).toISOString(),new Date(Date.now()+19008e5).toISOString(),new Date(Date.now()-24e5).toISOString(),Ue.models.map(e=>({...e}));function K(e){return{method:`POST`,body:JSON.stringify(e)}}var q={session(){return V(`/api/auth/session`)},login(e){return V(`/api/auth/login`,K({password:e}))},logout(){return V(`/api/auth/logout`,{method:`POST`})},overview(e){return H(`/api/overview${U({window:e})}`)},clients(e){return H(`/api/clients${U({window:e})}`)},requests(e){return H(`/api/requests${U({...e})}`)},requestDetail(e){return H(`/api/requests/${e}`)},keys(){return H(`/api/keys`).then(e=>e.items)},createKey(e){return H(`/api/keys`,K(e))},patchKey(e,t){return H(`/api/keys/${e}`,{method:`PATCH`,body:JSON.stringify(t)})},deleteKey(e){return H(`/api/keys/${e}`,{method:`DELETE`})},settings(){return H(`/api/settings`)},putSettings(e){return H(`/api/settings`,{method:`PUT`,body:JSON.stringify({settings:e})}).then(t=>(le(`settings`,n=>({...n,version:t.version,groups:n.groups.map(t=>({...t,items:t.items.map(t=>{let n=e.find(e=>e.key===t.key);return n?{...t,value:n.value}:t})}))})),t))},danger(e,t){return H(`/api/settings/danger`,K({action:e,confirm:t}))},putCredential(e){return H(`/api/settings/credential`,{method:`PUT`,body:JSON.stringify({key:e})})},resetAdminPassword(){return H(`/api/auth/password/reset`,{method:`POST`})},setAdminPassword(e){return H(`/api/auth/password`,{method:`PUT`,body:JSON.stringify({password:e})})},catalog(e){return H(`/api/models/catalog${e?`?provider=${encodeURIComponent(e)}`:``}`)},refreshCatalog(){return H(`/api/models/catalog`,{method:`POST`})},testCredential(e){return H(`/api/settings/credential/test`,K({key:e}))},setModelEnabled(e,t,n){return H(`/api/models/catalog/${encodeURIComponent(e)}${n?`?provider=${encodeURIComponent(n)}`:``}`,{method:`PATCH`,body:JSON.stringify({enabled:t})})},providerSignin(e){return H(`/api/providers/${encodeURIComponent(e)}/signin`)},providerOauthImport(e,t){return H(`/api/providers/${encodeURIComponent(e)}/oauth-import`,{method:`POST`,body:JSON.stringify(t)})},providerImportLocal(e){return H(`/api/providers/${encodeURIComponent(e)}/import-local`,{method:`POST`,body:`{}`})},providerImportDeviceStart(e){return H(`/api/providers/${encodeURIComponent(e)}/import-device/start`,{method:`POST`,body:`{}`})},providerImportDevicePoll(e){return H(`/api/providers/${encodeURIComponent(e)}/import-device/poll`,{method:`POST`,body:`{}`})},providerImportDeviceCancel(e){return H(`/api/providers/${encodeURIComponent(e)}/import-device/cancel`,{method:`POST`,body:`{}`})},providerGrowthRun(e){return H(`/api/providers/${encodeURIComponent(e)}/growth/run`,{method:`POST`})},providerGrowthPanel(e){return H(`/api/providers/${encodeURIComponent(e)}/growth`)},providerSigninNow(e){return H(`/api/providers/${encodeURIComponent(e)}/signin`,{method:`POST`})},providers(){return H(`/api/providers`)},createProvider(e){return H(`/api/providers`,{method:`POST`,body:JSON.stringify(e)})},patchProvider(e,t){return H(`/api/providers/${encodeURIComponent(e)}`,{method:`PATCH`,body:JSON.stringify(t)})},deactivateProvider(e){return H(`/api/providers/${encodeURIComponent(e)}/deactivate`,{method:`PUT`})},activateProvider(e){return H(`/api/providers/${encodeURIComponent(e)}/activate`,{method:`PUT`})},testProvider(e,t){return H(`/api/providers/${encodeURIComponent(e)}/test`,{method:`POST`,body:JSON.stringify(t?{credential:t}:{})})},deleteProvider(e){return H(`/api/providers/${encodeURIComponent(e)}`,{method:`DELETE`})}};function Ke(){let[e,t]=(0,x.useState)(`loading`),[n,r]=(0,x.useState)(null);(0,x.useEffect)(()=>{let e=!0;return q.session().then(n=>{e&&(t(n.authenticated?`authed`:`anon`),r(n.expiresAt))}).catch(()=>{e&&t(`anon`)}),()=>{e=!1}},[]);let i=(0,x.useRef)(!1);return(0,x.useEffect)(()=>re(()=>{i.current||(ce(),t(`anon`))}),[]),{status:e,expiresAt:n,login:(0,x.useCallback)(async e=>{let n=await q.login(e);ce(),t(`authed`),r(n.expiresAt)},[]),logout:(0,x.useCallback)(async()=>{i.current=!0;try{await q.logout()}catch(e){if(!(e instanceof R))throw i.current=!1,e}t(`anon`),r(null),window.location.assign(`/`)},[])}}var J=_();function Y({size:e=26}){return(0,J.jsxs)(`svg`,{width:e,height:e,viewBox:`0 0 160 160`,fill:`none`,role:`img`,"aria-label":`Waygate`,children:[(0,J.jsx)(`polygon`,{points:`80,8 148,48 128,125 50,151 12,78`,fill:`var(--brand-500)`,opacity:`.12`}),(0,J.jsx)(`polygon`,{points:`80,8 80,94 12,78`,fill:`var(--brand-400)`}),(0,J.jsx)(`polygon`,{points:`80,8 148,48 80,94`,fill:`var(--brand-500)`}),(0,J.jsx)(`polygon`,{points:`148,48 128,125 80,94`,fill:`var(--accent-blue)`}),(0,J.jsx)(`polygon`,{points:`12,78 80,94 50,151`,fill:`var(--brand-450)`,opacity:`.85`}),(0,J.jsx)(`polygon`,{points:`80,94 128,125 50,151`,fill:`var(--brand-450)`})]})}function qe(){return{...(0,x.useSyncExternalStore)(P,N,()=>({theme:`dark`,preference:`system`})),setPreference:te}}var Je=h(),X=12,Z=8,Ye=300;function Xe(e,t){typeof e==`function`?e(t):e&&(e.current=t)}function Ze({content:e,children:t,placement:n=`auto`,className:r}){let i=(0,x.useId)(),a=(0,x.useRef)(null),o=(0,x.useRef)(null),[s,c]=(0,x.useState)(!1),[l,u]=(0,x.useState)(null),d=t.props,f=d.disabled===!0,p=d.ref,m=typeof d[`aria-describedby`]==`string`?d[`aria-describedby`]:void 0,h=[m,s?i:void 0].filter(Boolean).join(` `)||void 0,g=typeof d.tabIndex==`number`?d.tabIndex:f?void 0:0,_=(0,x.useCallback)(()=>{let e=a.current,t=o.current;if(!e||!t)return;let r=e.getBoundingClientRect(),i=window.innerWidth,s=window.innerHeight,c=Math.min(Ye,Math.max(0,i-24)),l=Math.min(c,t.offsetWidth||c),d=t.offsetHeight;if(r.bottom<X||r.top>s-X){u(null);return}let f=r.top-X,p=s-r.bottom-X,m=f>=d+Z,h=p>=d+Z,g=n===`above`?m||!h?`above`:`below`:n===`below`?h||!m?`below`:`above`:m||!h?`above`:`below`,_=r.left+r.width/2,v=Math.max(X,Math.min(_-l/2,i-l-X)),y=Math.max(12,Math.min(_-v,l-12)),b=g===`above`?Math.max(X,r.top-d-Z):Math.max(X,Math.min(s-d-X,r.bottom+Z));u({left:v,top:b,placement:g,maxWidth:c,arrowLeft:y})},[n]),v=(0,x.useCallback)(()=>c(!0),[]),y=(0,x.useCallback)(()=>c(!1),[]);(0,x.useLayoutEffect)(()=>{if(!s){u(null);return}_()},[e,_,s]),(0,x.useLayoutEffect)(()=>{if(!s)return;let e=()=>_(),t=e=>{e.key===`Escape`&&(e.preventDefault(),e.stopPropagation(),y())},n=e=>{let t=e.target;t&&(a.current?.contains(t)||o.current?.contains(t))||y()};return window.addEventListener(`scroll`,e,!0),window.addEventListener(`resize`,e),window.visualViewport?.addEventListener(`resize`,e),window.visualViewport?.addEventListener(`scroll`,e),document.addEventListener(`keydown`,t,!0),document.addEventListener(`pointerdown`,n,!0),()=>{window.removeEventListener(`scroll`,e,!0),window.removeEventListener(`resize`,e),window.visualViewport?.removeEventListener(`resize`,e),window.visualViewport?.removeEventListener(`scroll`,e),document.removeEventListener(`keydown`,t,!0),document.removeEventListener(`pointerdown`,n,!0)}},[y,_,s]);let b=(0,x.useCallback)(e=>{a.current=e,Xe(p,e)},[p]),S=(0,x.useCallback)(e=>{Xe(p,e)},[p]),C=(0,x.useCallback)(e=>{a.current=e},[]),w=d.onBlur,T=(e,t)=>{let n=e.relatedTarget;n instanceof Node&&e.currentTarget.contains(n)||(t&&w?.(e),y())},E=typeof d.className==`string`&&r?`${d.className} ${r}`:r??d.className,D=(0,x.cloneElement)(t,{...E?{className:E}:{},ref:f?S:b,"aria-describedby":f?m:h,"data-tooltip-trigger":f?void 0:`true`,tabIndex:g,onMouseEnter:e=>{d.onMouseEnter?.(e),v()},onMouseLeave:e=>{d.onMouseLeave?.(e),y()},onFocus:e=>{d.onFocus?.(e),v()},onBlur:e=>T(e,!f)}),O=s&&typeof document<`u`?(0,Je.createPortal)((0,J.jsx)(`div`,{ref:o,id:i,role:`tooltip`,className:`tooltip-surface tooltip-${l?.placement??`measuring`}`,style:l?{left:l.left,top:l.top,maxWidth:l.maxWidth,"--tooltip-arrow-left":`${l.arrowLeft}px`}:{visibility:`hidden`,maxWidth:Math.min(Ye,Math.max(0,window.innerWidth-24))},children:e}),document.body):null;if(!f)return(0,J.jsxs)(J.Fragment,{children:[D,O]});let k=[m,s?i:void 0].filter(Boolean).join(` `)||void 0;return(0,J.jsxs)(J.Fragment,{children:[(0,J.jsx)(`span`,{ref:C,className:`tooltip-anchor${r?` ${r}`:``}`,"data-tooltip-trigger":`true`,tabIndex:0,"aria-describedby":k,"aria-disabled":`true`,onMouseEnter:v,onMouseLeave:y,onFocus:v,onBlur:e=>T(e,!1),children:D}),O]})}var Q=[{value:`system`,label:`跟随系统`,Icon:b},{value:`light`,label:`浅色`,Icon:g},{value:`dark`,label:`深色`,Icon:v}];function Qe(){let{preference:e,setPreference:t}=qe();return(0,J.jsx)(`div`,{className:`theme-seg`,role:`radiogroup`,"aria-label":`外观`,onKeyDown:n=>{if(n.key!==`ArrowLeft`&&n.key!==`ArrowRight`)return;n.preventDefault();let r=Q.findIndex(t=>t.value===e),i=n.key===`ArrowRight`?(r+1)%Q.length:(r-1+Q.length)%Q.length;t(Q[i].value)},children:Q.map(({value:n,label:r,Icon:i})=>{let a=e===n;return(0,J.jsx)(Ze,{content:r,children:(0,J.jsx)(`button`,{type:`button`,role:`radio`,"aria-checked":a,tabIndex:a?0:-1,className:`theme-seg-i${a?` on`:``}`,"aria-label":r,onClick:()=>t(n),children:(0,J.jsx)(i,{size:14})})},n)})})}var $e=`relay.console.route`;function et(e){try{window.sessionStorage.setItem($e,e)}catch{}}function tt(){try{let e=window.sessionStorage.getItem($e);if(e&&I.includes(e))return e}catch{}return`overview`}function nt(e){return`/console#/${e??tt()}`}var rt=[{route:`overview`,label:`概览`,icon:(0,J.jsx)(o,{size:18})},{route:`usage`,label:`积分与用量`,icon:(0,J.jsx)(c,{size:18})},{route:`clients`,label:`提供商管理`,icon:(0,J.jsx)(e,{size:18})},{route:`keys`,label:`API 密钥`,icon:(0,J.jsx)(t,{size:18})},{route:`requests`,label:`请求日志`,icon:(0,J.jsx)(d,{size:18})},{route:`settings`,label:`设置`,icon:(0,J.jsx)(u,{size:18})}];function it({route:e,navigate:t,expiresAt:n,onLogout:r,children:i}){(0,x.useEffect)(()=>{et(e)},[e]);let[a,o]=(0,x.useState)(null);(0,x.useEffect)(()=>{let e=!0;return(async()=>{try{let t=await fetch(`/healthz`,{headers:{Accept:`application/json`}});if(!t.ok)return;let n=await t.json();e&&typeof n.version==`string`&&n.version&&o(n.version)}catch{}})(),()=>{e=!1}},[]);let[s,c]=(0,x.useState)(!1),u=(0,x.useRef)(null),d=(0,x.useRef)(null),f=(0,x.useRef)(null);(0,x.useEffect)(()=>{if(s){f.current=document.activeElement instanceof HTMLElement?document.activeElement:null,(d.current?.querySelector(`a[href], button:not([disabled])`))?.focus({preventScroll:!0});return}f.current?.isConnected&&f.current.focus({preventScroll:!0}),f.current=null},[s]),(0,x.useEffect)(()=>{if(!s)return;let e=e=>{if(e.key===`Escape`){e.preventDefault(),c(!1);return}if(e.key!==`Tab`)return;let t=d.current?Array.from(d.current.querySelectorAll(`a[href], button:not([disabled])`)):[];if(t.length===0)return;let n=t[0],r=t[t.length-1];e.shiftKey&&document.activeElement===n?(e.preventDefault(),r.focus()):!e.shiftKey&&document.activeElement===r&&(e.preventDefault(),n.focus())};return window.addEventListener(`keydown`,e),()=>window.removeEventListener(`keydown`,e)},[s]),(0,x.useEffect)(()=>{let e=()=>{window.innerWidth>720&&c(!1)};return window.addEventListener(`resize`,e),()=>window.removeEventListener(`resize`,e)},[]);let p=e=>{c(!1),t(e)};return(0,J.jsxs)(`div`,{className:`app`,"data-view":e,"data-nav-open":s?`true`:`false`,children:[(0,J.jsxs)(`div`,{className:`scene`,"aria-hidden":`true`,children:[(0,J.jsxs)(`div`,{className:`lights`,children:[(0,J.jsx)(`div`,{className:`bloom l1`}),(0,J.jsx)(`div`,{className:`bloom l2`}),(0,J.jsx)(`div`,{className:`bloom l3`})]}),(0,J.jsx)(`div`,{className:`dimmer`}),(0,J.jsx)(`div`,{className:`noise`})]}),(0,J.jsx)(`button`,{ref:u,type:`button`,className:`nav-toggle`,"aria-label":`打开导航菜单`,"aria-controls":`console-sidebar`,"aria-expanded":s,onClick:()=>c(e=>!e),children:(0,J.jsx)(l,{size:20})}),(0,J.jsxs)(`aside`,{ref:d,className:`sidebar`,id:`console-sidebar`,"aria-label":`控制台导航`,children:[(0,J.jsxs)(`a`,{className:`sb-brand`,href:`/`,children:[(0,J.jsx)(Y,{size:26}),(0,J.jsx)(`span`,{children:`途关`}),(0,J.jsx)(`span`,{className:`brand-en`,children:`Waygate`}),(0,J.jsxs)(`span`,{className:`brand-ver`,children:[`v`,a??`1.6.16`]})]}),(0,J.jsx)(`div`,{className:`sb-group`,children:`工作台`}),rt.filter(e=>I.includes(e.route)).map(t=>(0,J.jsxs)(`button`,{type:`button`,className:`sb-item${e===t.route?` active`:``}`,onClick:()=>p(t.route),"aria-current":e===t.route?`page`:void 0,children:[t.icon,t.label]},t.route)),(0,J.jsx)(`div`,{className:`sb-spacer`}),(0,J.jsxs)(`div`,{className:`sb-tools`,children:[(0,J.jsx)(`span`,{className:`sb-tools-lb`,children:`外观`}),(0,J.jsx)(Qe,{})]}),(0,J.jsxs)(`div`,{className:`sb-account`,children:[(0,J.jsx)(`div`,{className:`avatar`,children:`管`}),(0,J.jsxs)(`div`,{className:`meta`,children:[(0,J.jsx)(`b`,{children:`管理员`}),(0,J.jsx)(`i`,{children:n?`会话有效 · ${ke(n)}到期`:`本机管理员`})]}),(0,J.jsx)(Ze,{content:`退出登录`,children:(0,J.jsx)(`button`,{type:`button`,className:`sb-logout`,onClick:r,"aria-label":`退出登录`,children:(0,J.jsx)(y,{size:16})})})]})]}),(0,J.jsx)(`div`,{className:`nav-backdrop`,"aria-hidden":`true`,onClick:()=>c(!1)}),(0,J.jsx)(`main`,{className:`main`,children:i})]})}var at={error:{icon:m},success:{icon:s},info:{icon:r},warn:{icon:m}};function ot({tone:e,children:t,actions:n}){let r=at[e].icon;return(0,J.jsxs)(`div`,{className:`banner banner-${e}`,role:e===`error`||e===`warn`?`alert`:`status`,children:[(0,J.jsx)(r,{className:`banner-ico`,size:15,"aria-hidden":`true`}),(0,J.jsx)(`div`,{className:`banner-body`,children:t}),n?(0,J.jsx)(`div`,{className:`banner-actions`,children:n}):null]})}function st(e){var t=e&&typeof e.querySelectorAll==`function`?e:document,n=document.documentElement,r={};function i(e,t){r[e]!==t&&(r[e]=t,n.style.setProperty(e,t))}var a=window.matchMedia(`(prefers-reduced-motion: reduce)`).matches,o=!0,s=[`x`,`y`,`z`,`rx`,`ry`,`rz`,`fog`,`dim`],c={x:0,y:0,z:0,rx:0,ry:0,rz:0,fog:.18,dim:1},l={x:`px`,y:`px`,z:`px`,rx:`deg`,ry:`deg`,rz:`deg`},u={x:`--cam-x`,y:`--cam-y`,z:`--cam-z`,rx:`--cam-rx`,ry:`--cam-ry`,rz:`--cam-rz`,fog:`--fog`,dim:`--scene-dim`};function d(e){return function(){e|=0,e=e+1831565813|0;var t=Math.imul(e^e>>>15,1|e);return t=t+Math.imul(t^t>>>7,61|t)^t,((t^t>>>14)>>>0)/4294967296}}var f=[{sel:`.dust.d3`,count:14,min:.9,max:1.5,seed:20261004},{sel:`.dust.d2`,count:10,min:1.3,max:2,seed:77110203},{sel:`.dust.d1`,count:6,min:1.8,max:2.8,seed:31415926}];function p(){f.forEach(function(e){for(var n=t.querySelectorAll(e.sel),r=0;r<n.length;r+=1){n[r].innerHTML=``;for(var i=d(e.seed),a=document.createDocumentFragment(),o=0;o<e.count;o+=1){var s=document.createElement(`i`),c=e.min+i()*(e.max-e.min);s.style.left=(i()*100).toFixed(2)+`%`,s.style.top=(i()*100).toFixed(2)+`%`,s.style.width=c.toFixed(2)+`px`,s.style.height=c.toFixed(2)+`px`,s.style.animationDelay=(i()*3200).toFixed(0)+`ms`,a.appendChild(s)}n[r].appendChild(a)}})}var m=[];function h(e){var t=e.getBoundingClientRect();return t.top+window.pageYOffset+t.height/2}function g(){m=[].slice.call(t.querySelectorAll(`[data-cam]`)).map(function(e){var t={},n=e.getAttribute(`data-cam`);if(n)try{t=JSON.parse(n)}catch{console.warn(`[scene] data-cam 不是合法 JSON,已忽略:`,e,n),t={}}return{at:h(e),cam:t}}),m.sort(function(e,t){return e.at-t.at})}function _(e){return e<.5?2*e*e:1-(-2*e+2)**2/2}function v(e){if(!m.length)return Object.assign({},c);for(var t=0;t<m.length-1&&e>m[t+1].at;)t+=1;var n=m[t],r=m[t+1],i=r?e<=n.at?0:(e-n.at)/(r.at-n.at):1;i=Math.max(0,Math.min(1,i));for(var a=_(i),o={},l=0;l<s.length;l+=1){var u=s[l],d=n.cam[u]===void 0?c[u]:n.cam[u];o[u]=d+((r&&r.cam[u]!==void 0?r.cam[u]:d)-d)*a}return o}var y=.16,b=null,x=null,S=0,C=0;function w(e){for(var t=0;t<s.length;t+=1){var n=s[t],r=l[n]||``;i(u[n],e[n].toFixed(3)+r)}}function T(e){var t=S?Math.min((e-S)/1e3,.12):.016;S=e,b||=Object.assign({},x);for(var n=a?1:1-Math.exp(-t/y),r=!0,i=0;i<s.length;i+=1){var o=s[i],c=x[o]-b[o];b[o]+=c*n;var l=Math.max(.0015,Math.abs(x[o])*.0012);Math.abs(c)>l&&(r=!1)}if(w(b),r){b=Object.assign({},x),w(x),C=0,S=0;return}C=requestAnimationFrame(T)}function E(){C||=(S=0,requestAnimationFrame(T))}function D(){if(o){var e=document.documentElement,t=Math.max(1,e.scrollHeight-window.innerHeight);i(`--scroll-p`,(window.pageYOffset/t).toFixed(4)),x=v(window.pageYOffset+window.innerHeight/2),E()}}var O={tx:0,ty:0,x:0,y:0},k=0,A=0,ee=window.matchMedia(`(hover: hover) and (pointer: fine)`).matches;function j(){i(`--look-x`,O.x.toFixed(4)),i(`--look-y`,O.y.toFixed(4))}function M(e){var t=A?Math.min((e-A)/1e3,.12):.016;A=e;var n=1-Math.exp(-t/y);O.x+=(O.tx-O.x)*n,O.y+=(O.ty-O.y)*n,j(),Math.abs(O.tx-O.x)>8e-4||Math.abs(O.ty-O.y)>8e-4?k=requestAnimationFrame(M):(O.x=O.tx,O.y=O.ty,j(),k=0,A=0)}function N(e){document.hidden||(O.tx=(e.clientX/window.innerWidth-.5)*2,O.ty=(e.clientY/window.innerHeight-.5)*2,k||=(A=0,requestAnimationFrame(M)))}function P(){O.tx=0,O.ty=0,k||=(A=0,requestAnimationFrame(M))}function te(){!a&&ee&&(window.addEventListener(`pointermove`,N,{passive:!0}),document.addEventListener(`pointerleave`,P))}var F=null,I=null,L=null;function ne(){if(p(),g(),!m.length){n.setAttribute(`data-scene-ready`,`static`);return}D(),te();var e=!1;F=function(){e||(e=!0,requestAnimationFrame(function(){e=!1,D()}))},I=function(){o&&(g(),D())},L=function(){o&&(g(),D())},window.addEventListener(`scroll`,F,{passive:!0}),window.addEventListener(`resize`,I),window.addEventListener(`load`,L),document.fonts&&document.fonts.ready&&document.fonts.ready.then(function(){o&&(g(),D())}),n.setAttribute(`data-scene-ready`,`1`)}function R(){o=!1,F&&window.removeEventListener(`scroll`,F),I&&window.removeEventListener(`resize`,I),L&&window.removeEventListener(`load`,L),window.removeEventListener(`pointermove`,N),document.removeEventListener(`pointerleave`,P),C&&cancelAnimationFrame(C),k&&cancelAnimationFrame(k),C=0,k=0,[].slice.call(t.querySelectorAll(`.dust`)).forEach(function(e){e.innerHTML=``}),Object.keys(u).forEach(function(e){n.style.removeProperty(u[e])}),n.style.removeProperty(`--scroll-p`),n.style.removeProperty(`--look-x`),n.style.removeProperty(`--look-y`),r={},n.removeAttribute(`data-scene-ready`)}return ne(),R}var ct=e=>e,lt=[{tint:`var(--iris)`,a:`0deg`,r:`430px`,y:`-40px`,w:`300px`,h:`520px`,z:`-18deg`,x:`16deg`,o:`.95`,e:`.70`,hot:`.26`,dof:`0px`,dur:`15s`,delay:`0s`},{tint:`var(--accent-cyan)`,a:`72deg`,r:`448px`,y:`10px`,w:`255px`,h:`470px`,z:`12deg`,x:`-22deg`,o:`.82`,e:`.18`,hot:`.05`,dof:`0px`,dur:`19s`,delay:`3s`},{tint:`var(--brand-500)`,a:`144deg`,r:`424px`,y:`-60px`,w:`325px`,h:`560px`,z:`-24deg`,x:`19deg`,o:`.90`,e:`.52`,hot:`.18`,dof:`0px`,dur:`17s`,delay:`6.5s`},{tint:`var(--brand-400)`,a:`216deg`,r:`456px`,y:`20px`,w:`270px`,h:`490px`,z:`16deg`,x:`-14deg`,o:`.76`,e:`.14`,hot:`.04`,dof:`0px`,dur:`21s`,delay:`10s`},{tint:`var(--accent-blue)`,a:`288deg`,r:`436px`,y:`-30px`,w:`310px`,h:`535px`,z:`-14deg`,x:`24deg`,o:`.88`,e:`.30`,hot:`.12`,dof:`0px`,dur:`18s`,delay:`13.5s`},{tint:`var(--brand-500)`,a:`36deg`,r:`860px`,y:`40px`,w:`400px`,h:`560px`,z:`-22deg`,x:`26deg`,o:`.62`,e:`.20`,hot:`.06`,dof:`2.6px`,dur:`26s`,delay:`2s`,soft:!0},{tint:`var(--accent-cyan)`,a:`126deg`,r:`900px`,y:`-20px`,w:`360px`,h:`520px`,z:`18deg`,x:`-28deg`,o:`.52`,e:`.10`,hot:`.03`,dof:`2.6px`,dur:`30s`,delay:`9s`,soft:!0},{tint:`var(--iris)`,a:`216deg`,r:`840px`,y:`60px`,w:`440px`,h:`620px`,z:`-28deg`,x:`20deg`,o:`.58`,e:`.30`,hot:`.09`,dof:`2.6px`,dur:`24s`,delay:`15s`,soft:!0},{tint:`var(--brand-400)`,a:`306deg`,r:`890px`,y:`-10px`,w:`380px`,h:`540px`,z:`14deg`,x:`-24deg`,o:`.48`,e:`.08`,hot:`.03`,dof:`2.6px`,dur:`33s`,delay:`19s`,soft:!0}];function ut(){return(0,J.jsxs)(`div`,{className:`scene`,"aria-hidden":`true`,children:[(0,J.jsxs)(`div`,{className:`rig`,children:[(0,J.jsx)(`div`,{className:`tilt`,children:(0,J.jsx)(`div`,{className:`stage`,children:lt.map((e,t)=>(0,J.jsx)(`i`,{className:e.soft?`pl soft`:`pl`,style:ct({"--tint":e.tint,"--a":e.a,"--r":e.r,"--y":e.y,"--w":e.w,"--h":e.h,"--z":e.z,"--x":e.x,"--o":e.o,"--e":e.e,"--hot":e.hot,"--dof":e.dof,"--sheen-dur":e.dur,"--sheen-delay":e.delay})},t))})}),(0,J.jsx)(`div`,{className:`dust d3`}),(0,J.jsx)(`div`,{className:`dust d2`}),(0,J.jsx)(`div`,{className:`dust d1`})]}),(0,J.jsx)(`div`,{className:`core`}),(0,J.jsx)(`div`,{className:`nucleus`}),(0,J.jsx)(`div`,{className:`beam b1`}),(0,J.jsx)(`div`,{className:`beam b2`}),(0,J.jsx)(`div`,{className:`fog`}),(0,J.jsx)(`div`,{className:`dimmer`}),(0,J.jsx)(`div`,{className:`vignette`}),(0,J.jsx)(`div`,{className:`noise`})]})}function dt(){return(0,x.useEffect)(()=>st(document),[]),(0,J.jsx)(ut,{})}function ft({session:e,mockHint:r}){let[o,s]=(0,x.useState)(``),[c,l]=(0,x.useState)(!1),[u,d]=(0,x.useState)(!1),[f,p]=(0,x.useState)(null),m=(0,x.useRef)(null);return(0,x.useEffect)(()=>{let e=m.current;if(!e||!window.matchMedia(`(hover: hover) and (pointer: fine)`).matches)return;let t=t=>{let n=e.getBoundingClientRect();e.style.setProperty(`--mx`,`${t.clientX-n.left}px`),e.style.setProperty(`--my`,`${t.clientY-n.top}px`)};return e.addEventListener(`pointermove`,t),()=>e.removeEventListener(`pointermove`,t)},[]),(0,J.jsxs)(`div`,{className:`login-wrap landing`,children:[(0,J.jsx)(dt,{}),(0,J.jsxs)(`div`,{className:`login-card`,ref:m,children:[(0,J.jsx)(`span`,{className:`login-glow`,"aria-hidden":`true`}),(0,J.jsxs)(`div`,{className:`login-brand`,children:[(0,J.jsx)(Y,{size:30}),(0,J.jsx)(`span`,{className:`b-name`,children:`途关`}),(0,J.jsx)(`span`,{className:`b-en`,children:`Waygate`})]}),(0,J.jsx)(`h1`,{children:`登录控制台`}),(0,J.jsx)(`p`,{className:`sub`,children:`这是自用工具,只有一个管理口令。口令校验在服务端完成,前端不保存明文。`}),(0,J.jsxs)(`form`,{className:`login-form`,onSubmit:async t=>{if(t.preventDefault(),!u){d(!0),p(null);try{await e.login(o)}catch(e){p(e instanceof R?e:new R(String(e),0,0)),d(!1)}}},children:[(0,J.jsxs)(`div`,{className:`login-field`,children:[(0,J.jsx)(`label`,{htmlFor:`pw`,children:`管理口令`}),(0,J.jsxs)(`div`,{className:`login-input`,children:[(0,J.jsx)(t,{size:15,color:`var(--text-faint)`,"aria-hidden":!0}),(0,J.jsx)(`input`,{id:`pw`,type:c?`text`:`password`,value:o,autoFocus:!0,autoComplete:`current-password`,placeholder:`输入管理口令`,onChange:e=>s(e.target.value)}),(0,J.jsx)(`button`,{type:`button`,className:`login-eye`,"aria-label":c?`隐藏口令`:`显示口令`,onClick:()=>l(e=>!e),children:c?(0,J.jsx)(n,{size:15}):(0,J.jsx)(i,{size:15})})]})]}),f?(0,J.jsx)(ot,{tone:`error`,children:f.message}):null,(0,J.jsxs)(`button`,{type:`submit`,className:`btn btn-primary login-submit`,disabled:u||!o,children:[u?(0,J.jsx)(a,{size:16}):null,u?`正在验证…`:`进入控制台`]})]}),(0,J.jsx)(`p`,{className:`login-hint`,children:r?`当前为 Mock 模式(npm run dev:mock),口令固定为 ${r}。`:`口令首次启动时若未配置 RELAY_ADMIN_PASSWORD_HASH,会打印到服务端 stdout 一次。`})]})]})}function pt(){return(0,J.jsx)(`div`,{className:`login-wrap`,children:(0,J.jsxs)(`div`,{style:{display:`flex`,flexDirection:`column`,alignItems:`center`,gap:16},children:[(0,J.jsx)(Y,{size:40}),(0,J.jsx)(`div`,{style:{fontSize:12.5,color:`var(--text-ghost)`},children:`正在确认会话…`})]})})}var mt=`modulepreload`,ht=function(e,t){return new URL(e,t).href},gt={},_t=function(e){return e.pathname.endsWith(`.css`)},$=function(e,t,n){let r=Promise.resolve();if(t&&t.length>0){let e,i=document.querySelector(`meta[property=csp-nonce]`),a=i?.nonce||i?.getAttribute(`nonce`);function o(e){return Promise.all(e.map(e=>Promise.resolve(e).then(e=>({status:`fulfilled`,value:e}),e=>({status:`rejected`,reason:e}))))}function s(e){return import.meta.resolve?new URL(import.meta.resolve(e)):new URL(e,import.meta.url)}r=o(t.map(t=>{t=ht(t,n);let r=s(t);if(r.href in gt)return;gt[r.href]=!0;let i=_t(r);if(e===void 0){e={all:new Set,styles:new Set};let t=document.getElementsByTagName(`link`);for(let n=t.length-1;n>=0;n--){let r=t[n];e.all.add(r.href),r.rel===`stylesheet`&&e.styles.add(r.href)}}if((i?e.styles:e.all).has(r.href))return;let o=document.createElement(`link`);if(o.rel=i?`stylesheet`:mt,i||(o.as=`script`),o.crossOrigin=``,o.href=r.href,a&&o.setAttribute(`nonce`,a),document.head.appendChild(o),i)return new Promise((e,t)=>{o.addEventListener(`load`,e),o.addEventListener(`error`,()=>t(Error(`Unable to preload CSS for ${r}`)))})}).filter(e=>e!==void 0))}function i(e){let t=new Event(`vite:preloadError`,{cancelable:!0});if(t.payload=e,window.dispatchEvent(t),!t.defaultPrevented)throw e}return r.then(t=>{for(let e of t||[])e.status===`rejected`&&i(e.reason);return e().catch(i)})},vt=(0,x.lazy)(()=>$(()=>import(`./LandingPage-P2QNDFaP.js`).then(e=>({default:e.LandingPage})),__vite__mapDeps([0,1,2,3]),import.meta.url)),yt=(0,x.lazy)(()=>$(()=>import(`./OverviewPage-BgBo_XhF.js`).then(e=>({default:e.OverviewPage})),__vite__mapDeps([4,1,5,6,7,8,9]),import.meta.url)),bt=(0,x.lazy)(()=>$(()=>import(`./UsagePage-cxZ-GnpO.js`).then(e=>({default:e.UsagePage})),__vite__mapDeps([10,1,5,6,7,8,9]),import.meta.url)),xt=(0,x.lazy)(()=>$(()=>import(`./ClientsPage-Dy68uQDl.js`).then(e=>({default:e.ClientsPage})),__vite__mapDeps([11,1,5,12,13,6,7,14,15]),import.meta.url)),St=(0,x.lazy)(()=>$(()=>import(`./ApiKeysPage-Ck0Gry6E.js`).then(e=>({default:e.ApiKeysPage})),__vite__mapDeps([16,1,5,12,13,6]),import.meta.url)),Ct=(0,x.lazy)(()=>$(()=>import(`./RequestsPage-CVB0wpCH.js`).then(e=>({default:e.RequestsPage})),__vite__mapDeps([17,1,5,6,14,13,8]),import.meta.url)),wt=(0,x.lazy)(()=>$(()=>import(`./SettingsPage-B4Mew-7b.js`).then(e=>({default:e.SettingsPage})),__vite__mapDeps([18,1,2,5,12,13,14,15]),import.meta.url));function Tt(){let[e,t]=(0,x.useState)(()=>window.location.pathname);return(0,x.useEffect)(()=>{let e=()=>t(window.location.pathname);return window.addEventListener(`popstate`,e),()=>window.removeEventListener(`popstate`,e)},[]),e}var Et=`Waygate — 控制台`;function Dt(){return(0,J.jsx)(`div`,{style:{display:`flex`,alignItems:`center`,justifyContent:`center`,minHeight:`50vh`,fontSize:12.5,color:`var(--text-ghost)`},children:`加载中…`})}function Ot(){let{route:e,navigate:t}=ne(),n=Ke();return(0,x.useEffect)(()=>{document.title=Et},[]),(0,x.useEffect)(()=>{window.location.hash||(window.location.hash=`#/overview`)},[]),n.status===`loading`?(0,J.jsx)(pt,{}):n.status===`anon`?(0,J.jsx)(ft,{session:n,mockHint:null}):(0,J.jsx)(it,{route:e,navigate:t,expiresAt:n.expiresAt,onLogout:()=>void n.logout(),children:(0,J.jsxs)(x.Suspense,{fallback:(0,J.jsx)(Dt,{}),children:[e===`overview`?(0,J.jsx)(yt,{navigate:t}):null,e===`usage`?(0,J.jsx)(bt,{}):null,e===`clients`?(0,J.jsx)(xt,{}):null,e===`keys`?(0,J.jsx)(St,{}):null,e===`requests`?(0,J.jsx)(Ct,{}):null,e===`settings`?(0,J.jsx)(wt,{}):null]})})}function kt(){let e=Tt(),t=C(e)===`console`;return(0,x.useEffect)(()=>{F()},[e]),t?(0,J.jsx)(Ot,{}):(0,J.jsx)(x.Suspense,{fallback:null,children:(0,J.jsx)(vt,{})})}var At=(0,x.createContext)(null),jt={error:{icon:m,defaultMs:8e3},warn:{icon:m,defaultMs:8e3},success:{icon:s,defaultMs:5e3},info:{icon:r,defaultMs:5e3}};function Mt({children:e}){let[t,n]=(0,x.useState)([]),r=(0,x.useRef)(1),i=(0,x.useCallback)(e=>{n(t=>t.filter(t=>t.id!==e))},[]),a=(0,x.useCallback)(e=>{let t=r.current++;return n(n=>[...n,{...e,id:t}].slice(-4)),t},[]),o=(0,x.useMemo)(()=>({push:a,dismiss:i}),[a,i]);return(0,J.jsxs)(At.Provider,{value:o,children:[e,typeof document<`u`?(0,Je.createPortal)((0,J.jsx)(`div`,{className:`toast-stack`,"aria-live":`polite`,"aria-atomic":`false`,children:t.map(e=>(0,J.jsx)(Nt,{item:e,onDismiss:i},e.id))}),document.body):null]})}function Nt({item:e,onDismiss:t}){let{icon:n,defaultMs:r}=jt[e.tone],i=e.durationMs??r,[a,o]=(0,x.useState)(!1),[s,c]=(0,x.useState)(i);return(0,x.useEffect)(()=>{if(a)return;let n=Date.now(),r=window.setInterval(()=>{let a=i-(Date.now()-n);a<=0?(window.clearInterval(r),t(e.id)):c(a)},100);return()=>window.clearInterval(r)},[a,i,e.id,t]),(0,J.jsxs)(`div`,{className:`toast toast-${e.tone}`,role:e.tone===`error`||e.tone===`warn`?`alert`:`status`,onMouseEnter:()=>o(!0),onMouseLeave:()=>o(!1),onFocus:()=>o(!0),onBlur:()=>o(!1),children:[(0,J.jsx)(n,{className:`toast-ico`,size:15,"aria-hidden":`true`}),(0,J.jsx)(`div`,{className:`toast-body`,children:e.message}),(0,J.jsx)(`button`,{type:`button`,className:`toast-close`,"aria-label":`关闭提示`,onClick:()=>t(e.id),children:`×`}),(0,J.jsx)(`span`,{className:`toast-progress${a?` paused`:``}`,style:{animationDuration:`${i}ms`},"aria-hidden":`true`})]})}function Pt(){return(0,x.useContext)(At)??{push:()=>0,dismiss:()=>{}}}w(),T(),F();for(let e of[`icon`,`apple-touch-icon`]){let t=document.createElement(`link`);t.rel=e,t.type=`image/svg+xml`,t.href=`/icon.svg?v=2`,document.head.appendChild(t)}var Ft=document.getElementById(`root`);if(!Ft)throw Error(`#root 未找到 —— index.html 被改坏了`);(0,S.createRoot)(Ft).render((0,J.jsx)(x.StrictMode,{children:(0,J.jsx)(Mt,{children:(0,J.jsx)(kt,{})})}));export{me as A,Le as C,he as D,Re as E,R as M,fe as O,Ie as S,Pe as T,be as _,Ze as a,Ee as b,q as c,xe as d,De as f,ve as g,we as h,nt as i,de as j,pe as k,Me as l,Oe as m,dt as n,Y as o,ye as p,ot as r,Ke as s,Pt as t,Ae as u,ke as v,Te as w,Ce as x,je as y};
1
+ const __vite__mapDeps=(i,m=__vite__mapDeps,d=(m.f||(m.f=["./LandingPage-Bv4IWIsz.js","./vendor-befEYGHM.js","./accessUrl-DbL5DLDz.js","./LandingPage-Bx7xbIg8.css","./OverviewPage-Dus_pE-a.js","./Select-Bfquh0d_.js","./PageSkeleton-DG-Dj4_9.js","./sharedWindow-FDfq75PI.js","./useFx-xcrp_LHB.js","./ClientMetricTip-BqIkh3DO.js","./UsagePage-dnOsX2C4.js","./ClientsPage-BfXxV7sc.js","./Modal-B-rIrvXS.js","./useFocusTrap-Cj84bnpH.js","./Drawer-CleQGhRU.js","./Switch-0KA1AbiV.js","./ApiKeysPage-DutxhNxx.js","./RequestsPage-B7Lt3DYE.js","./SettingsPage-BPLnBLQJ.js"])))=>i.map(i=>d[i]);
2
+ import{$ as e,D as t,F as n,O as r,P as i,S as a,T as o,U as s,Y as c,b as l,c as u,d,it as f,nt as p,r as m,rt as h,s as g,tt as _,v,x as y,y as b}from"./vendor-befEYGHM.js";(function(){let e=document.createElement(`link`).relList;if(e&&e.supports&&e.supports(`modulepreload`))return;for(let e of document.querySelectorAll(`link[rel="modulepreload"]`))n(e);new MutationObserver(e=>{for(let t of e)if(t.type===`childList`)for(let e of t.addedNodes)e.tagName===`LINK`&&e.rel===`modulepreload`&&n(e)}).observe(document,{childList:!0,subtree:!0});function t(e){let t={};return e.integrity&&(t.integrity=e.integrity),e.referrerPolicy&&(t.referrerPolicy=e.referrerPolicy),t.credentials=e.crossOrigin===`use-credentials`?`include`:e.crossOrigin===`anonymous`?`omit`:`same-origin`,t}function n(e){if(e.ep)return;e.ep=!0;let n=t(e);fetch(e.href,n)}})();var x=f(),S=p();function C(e=window.location.pathname){let t=e.replace(/\/+$/,``)||`/`;return t===`/console`||t.startsWith(`/console/`)?`console`:`landing`}function w(e=!1){let{pathname:t,hash:n}=window.location;if(C(t)===`console`||!n.startsWith(`#/`))return;let r=`/console${n}`;e?window.location.replace(r):window.history.replaceState(null,``,r)}function T(){window.addEventListener(`hashchange`,()=>w(!0))}var E=`relay.theme`,D=`system`;function O(){try{return window.matchMedia?.(`(prefers-color-scheme: light)`).matches?`light`:`dark`}catch{return`dark`}}function k(e,t=window.location.pathname,n=window.location.hash){return e===`system`?O():e}function A(){try{let e=window.localStorage.getItem(E);return e===`light`||e===`dark`||e===`system`?e:D}catch{return D}}function ee(e){document.documentElement.dataset.theme=e}var j=null,M=new Set;function N(){if(j===null){let e=document.documentElement.dataset.theme,t=A();j={theme:e===`light`||e===`dark`?e:k(t),preference:t}}return j}function P(e){return M.add(e),()=>M.delete(e)}function te(e){try{window.localStorage.setItem(E,e)}catch{}F()}function F(){let e=A(),t=k(e);ee(t),j={theme:t,preference:e},M.forEach(e=>e())}typeof window<`u`&&(window.matchMedia?.(`(prefers-color-scheme: light)`).addEventListener?.(`change`,()=>{A()===`system`&&F()}),window.addEventListener(`storage`,e=>{(e.key===null||e.key===E)&&F()}));var I=[`overview`,`usage`,`clients`,`keys`,`requests`,`settings`];function L(e){let t=e.replace(/^#\/?/,``).split(`?`)[0];return I.includes(t)?t:`overview`}function ne(){let[e,t]=(0,x.useState)(()=>L(window.location.hash));return(0,x.useEffect)(()=>{let e=()=>t(L(window.location.hash));return window.addEventListener(`hashchange`,e),()=>window.removeEventListener(`hashchange`,e)},[]),{route:e,navigate:e=>{window.location.hash=`#/${e}`}}}var R=class extends Error{code;status;retryAfterSeconds;constructor(e,t,n,r){super(e),this.name=`ApiError`,this.code=t,this.status=n,this.retryAfterSeconds=r}get isSessionExpired(){return this.code===40102}},z=new Set;function re(e){return z.add(e),()=>z.delete(e)}function ie(e){z.forEach(t=>t(e))}async function ae(e){let t=await e.text(),n=null;try{n=t?JSON.parse(t):null}catch{throw new R(`服务端返回了非 JSON 响应(HTTP ${e.status})`,0,e.status)}if(!n||typeof n.code!=`number`)throw new R(`响应缺少统一信封(HTTP ${e.status})`,0,e.status);if(n.code===0)return n.data;let r=n.data?.retryAfterSeconds;throw new R(n.message||`请求失败(code ${n.code})`,n.code,e.status,r)}var B=2e4;function oe(e,t){let n=new AbortController,r=!1,i=()=>n.abort(e?.reason);e&&(e.aborted?n.abort(e.reason):e.addEventListener(`abort`,i,{once:!0}));let a=t===null?void 0:setTimeout(()=>{r=!0,n.abort()},t);return{signal:n.signal,isTimedOut:()=>r,dispose:()=>{a!==void 0&&clearTimeout(a),e?.removeEventListener(`abort`,i)}}}function se(e){return e instanceof DOMException&&e.name===`AbortError`}async function V(e,t){let n=(t?.method??`GET`).toUpperCase(),r=oe(t?.signal,n===`GET`?B:null),i=new Headers(t?.headers);i.has(`accept`)||i.set(`Accept`,`application/json`),t?.body&&!i.has(`content-type`)&&i.set(`Content-Type`,`application/json`);let a;try{a=await fetch(e,{...t,signal:r.signal,credentials:`same-origin`,headers:i})}catch(e){throw r.dispose(),r.isTimedOut()?new R(`请求超时(${B/1e3}s 无响应),稍后重试。`,0,0):se(e)?e:new R(`连不上本机服务。确认后端已在 127.0.0.1:8787 启动。`,0,0)}try{let e=await ae(a);if(!a.ok)throw new R(`请求失败(HTTP ${a.status})`,0,a.status);return e}catch(e){throw r.isTimedOut()?new R(`请求超时(${B/1e3}s 无响应),稍后重试。`,0,0):e}finally{r.dispose()}}async function H(e,t){try{return await V(e,t)}catch(e){throw e instanceof R&&e.isSessionExpired&&ie(e),e}}function U(e){let t=new URLSearchParams;Object.entries(e).forEach(([e,n])=>{n!=null&&n!==``&&t.set(e,String(n))});let n=t.toString();return n?`?${n}`:``}var W=new Map,G=new Map;function ce(){W.clear(),G.clear()}function le(e,t){W.has(e)&&W.set(e,t(W.get(e)))}function ue(e,t,n){let r=G.get(e);if(r&&!n)return r;let i=t().then(t=>(G.get(e)===i&&W.set(e,t),t));return G.set(e,i),i.finally(()=>{G.get(e)===i&&G.delete(e)}).catch(()=>{}),i}function de(e,t,n={}){let r=n.enabled??!0,i=n.cacheKey,a=r&&i!==void 0&&W.has(i),[o,s]=(0,x.useState)(()=>a?W.get(i):null),[c,l]=(0,x.useState)(null),[u,d]=(0,x.useState)(r),[f,p]=(0,x.useState)(!a),m=(0,x.useRef)(0),h=(0,x.useRef)(e);h.current=e;let g=(0,x.useRef)(i);g.current=i;let _=(0,x.useCallback)(e=>{let t=++m.current,n=g.current;d(!0),(n===void 0?h.current():ue(n,()=>h.current(),e)).then(e=>{t===m.current&&(s(e),l(null),d(!1),p(!1))},e=>{t!==m.current||se(e)||(l(e instanceof R?e:new R(String(e),0,0)),d(!1),p(!1))})},[]);return(0,x.useEffect)(()=>{if(!r){m.current+=1,s(null),l(null),d(!1),p(!0);return}i!==void 0&&W.has(i)&&(s(W.get(i)),l(null),p(!1)),_(!1)},[r,i,...t]),{data:o,error:c,loading:u,initial:f,reload:(0,x.useCallback)(()=>_(!0),[_])}}var fe={today:`今日`,"1h":`最近 1 小时`,"24h":`最近 24 小时`,"7d":`最近 7 天`,"30d":`最近 30 天`},pe=Object.keys(fe).map(e=>({value:e,label:fe[e]}));function me(e,t){return t&&new Date(t).getTime()<Date.now()?`exp`:e?`live`:`off`}var he={live:`启用`,off:`已停用`,exp:`已过期`},ge=new Intl.NumberFormat(`zh-CN`),_e=new Intl.NumberFormat(`zh-CN`,{minimumFractionDigits:2,maximumFractionDigits:2});function ve(e){return e==null||Number.isNaN(e)?`--`:ge.format(Math.round(e))}function ye(e){return e==null||Number.isNaN(e)?`--`:_e.format(e)}function be(e,t=1){return e==null||Number.isNaN(e)?`--`:`${(e*100).toFixed(t)}%`}function xe(e,t=1){return`${((Number.isFinite(e)?Math.max(0,Math.min(1,e)):0)*100).toFixed(t)}%`}var Se=[{limit:0x38d7ea4c68000,div:0x38d7ea4c68000,digits:2,suffix:`Q`},{limit:0xe8d4a51000,div:0xe8d4a51000,digits:2,suffix:`T`},{limit:1e9,div:1e9,digits:2,suffix:`B`},{limit:1e6,div:1e6,digits:2,suffix:`M`},{limit:1e3,div:1e3,digits:1,suffix:`K`}];function Ce(e){if(e==null||Number.isNaN(e))return`--`;let t=Math.round(e),n=Se.find(e=>Math.abs(t)>=e.limit);return n?`${(t/n.div).toFixed(n.digits)}${n.suffix}`:String(t)}function we(e){return e==null||Number.isNaN(e)?`--`:e<1e3?`${Math.round(e)}ms`:e<6e4?`${(e/1e3).toFixed(1)}s`:`${Math.floor(e/6e4)}m${Math.round(e%6e4/1e3)}s`}function Te(e,t,n){let r=e??0;if(r<=0||t==null||t<=0)return null;let i=n==null?t:t-n;return i<=0?null:r/(i/1e3)}function Ee(e){return e==null||Number.isNaN(e)?`--`:`${e.toFixed(1)} t/s`}function De(e){if(!e)return`--`;let t=new Date(e);return Number.isNaN(t.getTime())?`--`:t.toLocaleTimeString(`zh-CN`,{hour12:!1})}function Oe(e){if(!e)return`--`;let t=new Date(e);return Number.isNaN(t.getTime())?`--`:`${t.toLocaleDateString(`zh-CN`)} ${t.toLocaleTimeString(`zh-CN`,{hour12:!1})}`}function ke(e){if(!e)return`--`;let t=new Date(e).getTime();if(Number.isNaN(t))return`--`;let n=Date.now()-t;if(n<0){let e=-n;return e<6e4?`马上`:e<36e5?`${Math.floor(e/6e4)} 分钟后`:e<864e5?`${Math.floor(e/36e5)} 小时后`:`${Math.floor(e/864e5)} 天后`}let r=Math.floor(n/6e4);if(r<1)return`刚刚`;if(r<60)return`${r} 分钟前`;let i=Math.floor(r/60);if(i<24)return`${i} 小时前`;let a=Math.floor(i/24);return a<30?`${a} 天前`:`${Math.floor(a/30)} 个月前`}function Ae(e){let t=e.match(/^(\d{4})-(\d{2})-(\d{2})(?:T(\d{2}))?/);if(!t)return e.slice(5,10);let n=`${Number(t[2])}/${Number(t[3])}`;return t[4]===void 0?n:`${n} ${Number(t[4])}时`}function je(e){switch(e.type){case`all`:return`全部模型`;case`family`:return`仅 ${e.value} 系`;case`tag`:return`仅 ${e.value}`;case`models`:return`指定 ${e.value.length} 个模型`;default:return`未知范围`}}var Me=`upstream_credential_invalid`;function Ne(e,t=Me){return e.split(`,`).includes(t)}function Pe(e,t=``){return Ne(t)||e===401?`fatal`:e>=400?`warn`:`live`}var Fe={[Me]:`上游访问密钥失效`,"upstream unreachable":`上游不可达`,"upstream empty body":`上游返回空响应`,upstream_error:`上游错误`,"bad request body":`请求体不合法`,"model not permitted":`模型未授权`,"model not found":`模型不存在`,"concurrency limit":`本机并发上限`,"rate limited":`命中上游限流`,rate_limited:`命中上游限流`,"upstream timeout":`上游超时`,model_not_available:`账号未开通此模型`,invalid_max_tokens:`max_tokens 不合法`,context_length_exceeded:`上下文超限`,upstream_11101:`上游要求强制流式`,upstream_11128:`上游渠道校验拒绝(提示指纹)`,retried:`已自动重试`,"cache hit":`命中缓存`,system_injected:`已补 system`,developer_role_normalized:`已规范 developer 角色`,stream_options_stripped:`已移除 stream_options`,sysprompt_degraded_retry:`命中渠道校验,已降级重试`,stream_aborted:`流式中断`,client_detached:`客户端已断开`,usage_missing:`上游未返回用量`,"minimax tokens unavailable":`MiniMax token 不可用`,"token refresh failed":`上游 token 刷新失败`,"missing credential":`缺少上游访问凭证`,"wb oauth unavailable":`WorkBuddy 授权服务不可用`,"missing wb oauth credential":`WorkBuddy 未导入授权`,"wb token refresh failed":`WorkBuddy 授权刷新失败`,"qoder credential invalid":`Qoder 凭证无效`,"multiplier-unknown":`倍率未知(历史:积分按中性估算)`,cache_discounted:`缓存命中已按折扣计(历史)`,credits_from_upstream:`上游实扣积分`,credits_unknown:`上游未回报积分`,credits_recalibrated:`历史积分已重算`,estimate_voided:`历史估算已作废(上游未回报)`};function Ie(e){if(!e)return`-`;let t=e.split(`,`)[0];return Fe[t]??t}function Le(e){return e?e.split(`,`).map(e=>e.trim()).filter(Boolean).map(e=>Fe[e]??e):[]}function Re(e){return e.upstreamCode===11102?`11102:当前账号未开通该模型。该项已在模型表标为未验证,不会自动删除——订阅变动后可能再开。`:e.upstreamCode===11128?`11128:上游返回业务码 11128(上游原文「Illegal API invocation from an unapproved channel」):本次请求的 system 提示命中了上游对第三方客户端模板的指纹校验。本服务已在转发前改写模板行,并在被拒时自动降级为中性提示重试一次,均未通过;请检查「客户端与密钥 → 提供商 → system 提示改写」是否被关闭,或把该请求的特征反馈给维护者。`:e.upstreamCode===11101?`11101:上游拒绝了非流式请求。本服务已强制改写为流式,出现此码说明上游协议变更。`:e.upstreamCode===11133?`11133:max_tokens 过小。已提升到下限后重试一次。`:Ne(e.note)?`上游访问密钥失效是这套方案唯一会让服务停摆的状态:所有客户端共用同一把上游访问密钥,它一失效即整体不可用。去「客户端与密钥 → 提供商」的「修改」里换新。`:null}var ze=[{displayName:`Hy4 preview`,id:`hy4-preview`,tag:`限时免费`,multiplier:0},{displayName:`Hy3`,id:`hy3`,tag:`限时免费`,multiplier:0},{displayName:`Space-Bunny`,id:`space-bunny`,tag:`限时折扣`,multiplier:.03},{displayName:`Deepseek-V4.1-Flash`,id:`deepseek-v4.1-flash`,tag:null,multiplier:.11},{displayName:`Deepseek-V4-Pro`,id:`deepseek-v4-pro`,tag:null,multiplier:.51},{displayName:`GLM-5.3`,id:`glm-5.3`,tag:`订阅优先`,multiplier:.79},{displayName:`GLM-5.3-Flash`,id:`glm-5.3-flash`,tag:`订阅优先`,multiplier:.06},{displayName:`GLM-5.3-FlashX`,id:`glm-5.3-flashx`,tag:`订阅优先`,multiplier:.14},{displayName:`GLM-5.2`,id:`glm-5.2`,tag:null,multiplier:.79},{displayName:`GLM-5.1`,id:`glm-5.1`,tag:null,multiplier:.79},{displayName:`GLM-5v-Turbo`,id:`glm-5v-turbo`,tag:null,multiplier:.71},{displayName:`MiniMax-M3`,id:`minimax-m3`,tag:null,multiplier:.25},{displayName:`Kimi-K3`,id:`kimi-k3`,tag:`订阅优先`,multiplier:1.62},{displayName:`Kimi-K2.8-Preview`,id:`kimi-k2.8-preview`,tag:`订阅优先`,multiplier:.77},{displayName:`Kimi-K2.7-Code`,id:`kimi-k2.7`,tag:null,multiplier:.57},{displayName:`Kimi-K2.6`,id:`kimi-k2.6`,tag:null,multiplier:.52},{displayName:`Step-5-Preview`,id:`step-5-preview`,tag:`订阅优先`,multiplier:.43},{displayName:`Kimi-K3-1`,id:`kimi-k3-1`,tag:`订阅优先`,multiplier:null}],Be=new Set([`kimi-k3-1`]),Ve=new Set([`step-5-preview`]);function He(e){return Be.has(e)?`upstream`:Ve.has(e)?`manual`:`seed`}var Ue={source:`seed`,fetchedAt:new Date(Date.now()-72e5).toISOString(),upstreamReachable:!0,models:ze.map(e=>({...e,family:e.id.split(`-`)[0],source:He(e.id),provider:e.id.startsWith(`MiniMax-`)||e.id.startsWith(`minimax-`)?`MiniMax Code`:`WorkBuddy`,verified:e.id===`glm-5.1`||e.id===`hy3`?0:1,enabled:!0,lastVerifiedAt:new Date(Date.now()-72e5).toISOString()}))},We=[{id:`k_8f21`,name:`Claude Code`},{id:`k_1b83`,name:`Cherry Studio`},{id:`k_9d02`,name:`Cursor`},{id:`k_c3a5`,name:`Cron Job`},{id:`k_77c1`,name:`手机端(临时)`},{id:`unidentified`,name:`未识别客户端`}];function Ge(){let e=Date.now(),t={ipWhitelist:[],maxIps:null,tokenQuota:null,usedIps:0,usedTokens:0};return[{...t,id:`k_8f21`,name:`Claude Code · 本机`,hint:`sk-waygate-4f9c…7a2e`,scope:{type:`all`},client:`Claude Code`,clients:[`Claude Code`],enabled:!0,expiresAt:null,createdAt:new Date(e-11232e5).toISOString(),lastSeenAt:new Date(e-4e4).toISOString(),requests24h:760},{...t,maxIps:3,tokenQuota:2e6,usedIps:2,usedTokens:1234567,id:`k_1b83`,name:`Cherry Studio`,hint:`sk-waygate-1b83…c40f`,scope:{type:`all`},client:`Cherry Studio`,clients:[`Cherry Studio`],enabled:!0,expiresAt:null,createdAt:new Date(e-9504e5).toISOString(),lastSeenAt:new Date(e-9e4).toISOString(),requests24h:324},{...t,id:`k_9d02`,name:`Cursor · 笔记本`,hint:`sk-waygate-9d02…3ee1`,scope:{type:`family`,value:`kimi`},client:`Cursor`,clients:[`Cursor`,`Claude Code`],enabled:!0,expiresAt:null,createdAt:new Date(e-7776e5).toISOString(),lastSeenAt:new Date(e-108e5).toISOString(),requests24h:154},{...t,id:`k_c3a5`,name:`Cron Job · 定时任务`,hint:`sk-waygate-c3a5…91d7`,scope:{type:`family`,value:`deepseek`},client:`Cron Job`,clients:[`Cron Job`],enabled:!0,expiresAt:null,createdAt:new Date(e-6912e5).toISOString(),lastSeenAt:new Date(e-3e5).toISOString(),requests24h:78},{...t,ipWhitelist:[`192.168.1.0/24`],id:`k_77c1`,name:`手机端(临时)`,hint:`sk-waygate-77c1…b8f0`,scope:{type:`all`},client:`手机端(临时)`,clients:[`手机端(临时)`],enabled:!1,expiresAt:null,createdAt:new Date(e-2592e6).toISOString(),lastSeenAt:new Date(e-2592e5).toISOString(),requests24h:0},{...t,id:`k_2e6b`,name:`测试脚本 · 本地`,hint:`sk-waygate-2e6b…0a13`,scope:{type:`tag`,value:`夜间折扣`},client:null,clients:[],enabled:!0,expiresAt:new Date(e-1728e5).toISOString(),createdAt:new Date(e-3456e6).toISOString(),lastSeenAt:new Date(e-10368e5).toISOString(),requests24h:0},{...t,id:`k_5d7f`,name:`家人共享 · 只读`,hint:`sk-waygate-5d7f…22c8`,scope:{type:`models`,value:[`glm-5.3`,`kimi-k2.7`]},client:null,clients:[],enabled:!1,expiresAt:null,createdAt:new Date(e-1728e6).toISOString(),lastSeenAt:new Date(e-432e6).toISOString(),requests24h:0}]}We.filter(e=>e.id!==`unidentified`).map(e=>e.name),Ge(),new Date().toISOString(),Date.now()+1728e6,Date.now()+22464e5,new Date().toISOString().slice(0,10),new Date(Date.now()-18e5).toISOString(),new Date(Date.now()-216e5).toISOString(),new Date(Date.now()+19008e5).toISOString(),new Date(Date.now()-24e5).toISOString(),Ue.models.map(e=>({...e}));function K(e){return{method:`POST`,body:JSON.stringify(e)}}var q={session(){return V(`/api/auth/session`)},login(e){return V(`/api/auth/login`,K({password:e}))},logout(){return V(`/api/auth/logout`,{method:`POST`})},overview(e){return H(`/api/overview${U({window:e})}`)},clients(e){return H(`/api/clients${U({window:e})}`)},requests(e){return H(`/api/requests${U({...e})}`)},requestDetail(e){return H(`/api/requests/${e}`)},keys(){return H(`/api/keys`).then(e=>e.items)},createKey(e){return H(`/api/keys`,K(e))},patchKey(e,t){return H(`/api/keys/${e}`,{method:`PATCH`,body:JSON.stringify(t)})},deleteKey(e){return H(`/api/keys/${e}`,{method:`DELETE`})},settings(){return H(`/api/settings`)},putSettings(e){return H(`/api/settings`,{method:`PUT`,body:JSON.stringify({settings:e})}).then(t=>(le(`settings`,n=>({...n,version:t.version,groups:n.groups.map(t=>({...t,items:t.items.map(t=>{let n=e.find(e=>e.key===t.key);return n?{...t,value:n.value}:t})}))})),t))},danger(e,t){return H(`/api/settings/danger`,K({action:e,confirm:t}))},putCredential(e){return H(`/api/settings/credential`,{method:`PUT`,body:JSON.stringify({key:e})})},resetAdminPassword(){return H(`/api/auth/password/reset`,{method:`POST`})},setAdminPassword(e){return H(`/api/auth/password`,{method:`PUT`,body:JSON.stringify({password:e})})},catalog(e){return H(`/api/models/catalog${e?`?provider=${encodeURIComponent(e)}`:``}`)},refreshCatalog(){return H(`/api/models/catalog`,{method:`POST`})},testCredential(e){return H(`/api/settings/credential/test`,K({key:e}))},setModelEnabled(e,t,n){return H(`/api/models/catalog/${encodeURIComponent(e)}${n?`?provider=${encodeURIComponent(n)}`:``}`,{method:`PATCH`,body:JSON.stringify({enabled:t})})},providerSignin(e){return H(`/api/providers/${encodeURIComponent(e)}/signin`)},providerOauthImport(e,t){return H(`/api/providers/${encodeURIComponent(e)}/oauth-import`,{method:`POST`,body:JSON.stringify(t)})},providerImportLocal(e){return H(`/api/providers/${encodeURIComponent(e)}/import-local`,{method:`POST`,body:`{}`})},providerImportDeviceStart(e){return H(`/api/providers/${encodeURIComponent(e)}/import-device/start`,{method:`POST`,body:`{}`})},providerImportDevicePoll(e){return H(`/api/providers/${encodeURIComponent(e)}/import-device/poll`,{method:`POST`,body:`{}`})},providerImportDeviceCancel(e){return H(`/api/providers/${encodeURIComponent(e)}/import-device/cancel`,{method:`POST`,body:`{}`})},providerGrowthRun(e){return H(`/api/providers/${encodeURIComponent(e)}/growth/run`,{method:`POST`})},providerGrowthPanel(e){return H(`/api/providers/${encodeURIComponent(e)}/growth`)},providerSigninNow(e){return H(`/api/providers/${encodeURIComponent(e)}/signin`,{method:`POST`})},providers(){return H(`/api/providers`)},createProvider(e){return H(`/api/providers`,{method:`POST`,body:JSON.stringify(e)})},patchProvider(e,t){return H(`/api/providers/${encodeURIComponent(e)}`,{method:`PATCH`,body:JSON.stringify(t)})},deactivateProvider(e){return H(`/api/providers/${encodeURIComponent(e)}/deactivate`,{method:`PUT`})},activateProvider(e){return H(`/api/providers/${encodeURIComponent(e)}/activate`,{method:`PUT`})},testProvider(e,t){return H(`/api/providers/${encodeURIComponent(e)}/test`,{method:`POST`,body:JSON.stringify(t?{credential:t}:{})})},deleteProvider(e){return H(`/api/providers/${encodeURIComponent(e)}`,{method:`DELETE`})}};function Ke(){let[e,t]=(0,x.useState)(`loading`),[n,r]=(0,x.useState)(null);(0,x.useEffect)(()=>{let e=!0;return q.session().then(n=>{e&&(t(n.authenticated?`authed`:`anon`),r(n.expiresAt))}).catch(()=>{e&&t(`anon`)}),()=>{e=!1}},[]);let i=(0,x.useRef)(!1);return(0,x.useEffect)(()=>re(()=>{i.current||(ce(),t(`anon`))}),[]),{status:e,expiresAt:n,login:(0,x.useCallback)(async e=>{let n=await q.login(e);ce(),t(`authed`),r(n.expiresAt)},[]),logout:(0,x.useCallback)(async()=>{i.current=!0;try{await q.logout()}catch(e){if(!(e instanceof R))throw i.current=!1,e}t(`anon`),r(null),window.location.assign(`/`)},[])}}var J=_();function Y({size:e=26}){return(0,J.jsxs)(`svg`,{width:e,height:e,viewBox:`0 0 160 160`,fill:`none`,role:`img`,"aria-label":`Waygate`,children:[(0,J.jsx)(`polygon`,{points:`80,8 148,48 128,125 50,151 12,78`,fill:`var(--brand-500)`,opacity:`.12`}),(0,J.jsx)(`polygon`,{points:`80,8 80,94 12,78`,fill:`var(--brand-400)`}),(0,J.jsx)(`polygon`,{points:`80,8 148,48 80,94`,fill:`var(--brand-500)`}),(0,J.jsx)(`polygon`,{points:`148,48 128,125 80,94`,fill:`var(--accent-blue)`}),(0,J.jsx)(`polygon`,{points:`12,78 80,94 50,151`,fill:`var(--brand-450)`,opacity:`.85`}),(0,J.jsx)(`polygon`,{points:`80,94 128,125 50,151`,fill:`var(--brand-450)`})]})}function qe(){return{...(0,x.useSyncExternalStore)(P,N,()=>({theme:`dark`,preference:`system`})),setPreference:te}}var Je=h(),X=12,Z=8,Ye=300;function Xe(e,t){typeof e==`function`?e(t):e&&(e.current=t)}function Ze({content:e,children:t,placement:n=`auto`,className:r}){let i=(0,x.useId)(),a=(0,x.useRef)(null),o=(0,x.useRef)(null),[s,c]=(0,x.useState)(!1),[l,u]=(0,x.useState)(null),d=t.props,f=d.disabled===!0,p=d.ref,m=typeof d[`aria-describedby`]==`string`?d[`aria-describedby`]:void 0,h=[m,s?i:void 0].filter(Boolean).join(` `)||void 0,g=typeof d.tabIndex==`number`?d.tabIndex:f?void 0:0,_=(0,x.useCallback)(()=>{let e=a.current,t=o.current;if(!e||!t)return;let r=e.getBoundingClientRect(),i=window.innerWidth,s=window.innerHeight,c=Math.min(Ye,Math.max(0,i-24)),l=Math.min(c,t.offsetWidth||c),d=t.offsetHeight;if(r.bottom<X||r.top>s-X){u(null);return}let f=r.top-X,p=s-r.bottom-X,m=f>=d+Z,h=p>=d+Z,g=n===`above`?m||!h?`above`:`below`:n===`below`?h||!m?`below`:`above`:m||!h?`above`:`below`,_=r.left+r.width/2,v=Math.max(X,Math.min(_-l/2,i-l-X)),y=Math.max(12,Math.min(_-v,l-12)),b=g===`above`?Math.max(X,r.top-d-Z):Math.max(X,Math.min(s-d-X,r.bottom+Z));u({left:v,top:b,placement:g,maxWidth:c,arrowLeft:y})},[n]),v=(0,x.useCallback)(()=>c(!0),[]),y=(0,x.useCallback)(()=>c(!1),[]);(0,x.useLayoutEffect)(()=>{if(!s){u(null);return}_()},[e,_,s]),(0,x.useLayoutEffect)(()=>{if(!s)return;let e=()=>_(),t=e=>{e.key===`Escape`&&(e.preventDefault(),e.stopPropagation(),y())},n=e=>{let t=e.target;t&&(a.current?.contains(t)||o.current?.contains(t))||y()};return window.addEventListener(`scroll`,e,!0),window.addEventListener(`resize`,e),window.visualViewport?.addEventListener(`resize`,e),window.visualViewport?.addEventListener(`scroll`,e),document.addEventListener(`keydown`,t,!0),document.addEventListener(`pointerdown`,n,!0),()=>{window.removeEventListener(`scroll`,e,!0),window.removeEventListener(`resize`,e),window.visualViewport?.removeEventListener(`resize`,e),window.visualViewport?.removeEventListener(`scroll`,e),document.removeEventListener(`keydown`,t,!0),document.removeEventListener(`pointerdown`,n,!0)}},[y,_,s]);let b=(0,x.useCallback)(e=>{a.current=e,Xe(p,e)},[p]),S=(0,x.useCallback)(e=>{Xe(p,e)},[p]),C=(0,x.useCallback)(e=>{a.current=e},[]),w=d.onBlur,T=(e,t)=>{let n=e.relatedTarget;n instanceof Node&&e.currentTarget.contains(n)||(t&&w?.(e),y())},E=typeof d.className==`string`&&r?`${d.className} ${r}`:r??d.className,D=(0,x.cloneElement)(t,{...E?{className:E}:{},ref:f?S:b,"aria-describedby":f?m:h,"data-tooltip-trigger":f?void 0:`true`,tabIndex:g,onMouseEnter:e=>{d.onMouseEnter?.(e),v()},onMouseLeave:e=>{d.onMouseLeave?.(e),y()},onFocus:e=>{d.onFocus?.(e),v()},onBlur:e=>T(e,!f)}),O=s&&typeof document<`u`?(0,Je.createPortal)((0,J.jsx)(`div`,{ref:o,id:i,role:`tooltip`,className:`tooltip-surface tooltip-${l?.placement??`measuring`}`,style:l?{left:l.left,top:l.top,maxWidth:l.maxWidth,"--tooltip-arrow-left":`${l.arrowLeft}px`}:{visibility:`hidden`,maxWidth:Math.min(Ye,Math.max(0,window.innerWidth-24))},children:e}),document.body):null;if(!f)return(0,J.jsxs)(J.Fragment,{children:[D,O]});let k=[m,s?i:void 0].filter(Boolean).join(` `)||void 0;return(0,J.jsxs)(J.Fragment,{children:[(0,J.jsx)(`span`,{ref:C,className:`tooltip-anchor${r?` ${r}`:``}`,"data-tooltip-trigger":`true`,tabIndex:0,"aria-describedby":k,"aria-disabled":`true`,onMouseEnter:v,onMouseLeave:y,onFocus:v,onBlur:e=>T(e,!1),children:D}),O]})}var Q=[{value:`system`,label:`跟随系统`,Icon:b},{value:`light`,label:`浅色`,Icon:g},{value:`dark`,label:`深色`,Icon:v}];function Qe(){let{preference:e,setPreference:t}=qe();return(0,J.jsx)(`div`,{className:`theme-seg`,role:`radiogroup`,"aria-label":`外观`,onKeyDown:n=>{if(n.key!==`ArrowLeft`&&n.key!==`ArrowRight`)return;n.preventDefault();let r=Q.findIndex(t=>t.value===e),i=n.key===`ArrowRight`?(r+1)%Q.length:(r-1+Q.length)%Q.length;t(Q[i].value)},children:Q.map(({value:n,label:r,Icon:i})=>{let a=e===n;return(0,J.jsx)(Ze,{content:r,children:(0,J.jsx)(`button`,{type:`button`,role:`radio`,"aria-checked":a,tabIndex:a?0:-1,className:`theme-seg-i${a?` on`:``}`,"aria-label":r,onClick:()=>t(n),children:(0,J.jsx)(i,{size:14})})},n)})})}var $e=`relay.console.route`;function et(e){try{window.sessionStorage.setItem($e,e)}catch{}}function tt(){try{let e=window.sessionStorage.getItem($e);if(e&&I.includes(e))return e}catch{}return`overview`}function nt(e){return`/console#/${e??tt()}`}var rt=[{route:`overview`,label:`概览`,icon:(0,J.jsx)(o,{size:18})},{route:`usage`,label:`积分与用量`,icon:(0,J.jsx)(c,{size:18})},{route:`clients`,label:`提供商管理`,icon:(0,J.jsx)(e,{size:18})},{route:`keys`,label:`API 密钥`,icon:(0,J.jsx)(t,{size:18})},{route:`requests`,label:`请求日志`,icon:(0,J.jsx)(d,{size:18})},{route:`settings`,label:`设置`,icon:(0,J.jsx)(u,{size:18})}];function it({route:e,navigate:t,expiresAt:n,onLogout:r,children:i}){(0,x.useEffect)(()=>{et(e)},[e]);let[a,o]=(0,x.useState)(null);(0,x.useEffect)(()=>{let e=!0;return(async()=>{try{let t=await fetch(`/healthz`,{headers:{Accept:`application/json`}});if(!t.ok)return;let n=await t.json();e&&typeof n.version==`string`&&n.version&&o(n.version)}catch{}})(),()=>{e=!1}},[]);let[s,c]=(0,x.useState)(!1),u=(0,x.useRef)(null),d=(0,x.useRef)(null),f=(0,x.useRef)(null);(0,x.useEffect)(()=>{if(s){f.current=document.activeElement instanceof HTMLElement?document.activeElement:null,(d.current?.querySelector(`a[href], button:not([disabled])`))?.focus({preventScroll:!0});return}f.current?.isConnected&&f.current.focus({preventScroll:!0}),f.current=null},[s]),(0,x.useEffect)(()=>{if(!s)return;let e=e=>{if(e.key===`Escape`){e.preventDefault(),c(!1);return}if(e.key!==`Tab`)return;let t=d.current?Array.from(d.current.querySelectorAll(`a[href], button:not([disabled])`)):[];if(t.length===0)return;let n=t[0],r=t[t.length-1];e.shiftKey&&document.activeElement===n?(e.preventDefault(),r.focus()):!e.shiftKey&&document.activeElement===r&&(e.preventDefault(),n.focus())};return window.addEventListener(`keydown`,e),()=>window.removeEventListener(`keydown`,e)},[s]),(0,x.useEffect)(()=>{let e=()=>{window.innerWidth>720&&c(!1)};return window.addEventListener(`resize`,e),()=>window.removeEventListener(`resize`,e)},[]);let p=e=>{c(!1),t(e)};return(0,J.jsxs)(`div`,{className:`app`,"data-view":e,"data-nav-open":s?`true`:`false`,children:[(0,J.jsxs)(`div`,{className:`scene`,"aria-hidden":`true`,children:[(0,J.jsxs)(`div`,{className:`lights`,children:[(0,J.jsx)(`div`,{className:`bloom l1`}),(0,J.jsx)(`div`,{className:`bloom l2`}),(0,J.jsx)(`div`,{className:`bloom l3`})]}),(0,J.jsx)(`div`,{className:`dimmer`}),(0,J.jsx)(`div`,{className:`noise`})]}),(0,J.jsx)(`button`,{ref:u,type:`button`,className:`nav-toggle`,"aria-label":`打开导航菜单`,"aria-controls":`console-sidebar`,"aria-expanded":s,onClick:()=>c(e=>!e),children:(0,J.jsx)(l,{size:20})}),(0,J.jsxs)(`aside`,{ref:d,className:`sidebar`,id:`console-sidebar`,"aria-label":`控制台导航`,children:[(0,J.jsxs)(`a`,{className:`sb-brand`,href:`/`,children:[(0,J.jsx)(Y,{size:26}),(0,J.jsx)(`span`,{children:`途关`}),(0,J.jsx)(`span`,{className:`brand-en`,children:`Waygate`}),(0,J.jsxs)(`span`,{className:`brand-ver`,children:[`v`,a??`1.6.18`]})]}),(0,J.jsx)(`div`,{className:`sb-group`,children:`工作台`}),rt.filter(e=>I.includes(e.route)).map(t=>(0,J.jsxs)(`button`,{type:`button`,className:`sb-item${e===t.route?` active`:``}`,onClick:()=>p(t.route),"aria-current":e===t.route?`page`:void 0,children:[t.icon,t.label]},t.route)),(0,J.jsx)(`div`,{className:`sb-spacer`}),(0,J.jsxs)(`div`,{className:`sb-tools`,children:[(0,J.jsx)(`span`,{className:`sb-tools-lb`,children:`外观`}),(0,J.jsx)(Qe,{})]}),(0,J.jsxs)(`div`,{className:`sb-account`,children:[(0,J.jsx)(`div`,{className:`avatar`,children:`管`}),(0,J.jsxs)(`div`,{className:`meta`,children:[(0,J.jsx)(`b`,{children:`管理员`}),(0,J.jsx)(`i`,{children:n?`会话有效 · ${ke(n)}到期`:`本机管理员`})]}),(0,J.jsx)(Ze,{content:`退出登录`,children:(0,J.jsx)(`button`,{type:`button`,className:`sb-logout`,onClick:r,"aria-label":`退出登录`,children:(0,J.jsx)(y,{size:16})})})]})]}),(0,J.jsx)(`div`,{className:`nav-backdrop`,"aria-hidden":`true`,onClick:()=>c(!1)}),(0,J.jsx)(`main`,{className:`main`,children:i})]})}var at={error:{icon:m},success:{icon:s},info:{icon:r},warn:{icon:m}};function ot({tone:e,children:t,actions:n}){let r=at[e].icon;return(0,J.jsxs)(`div`,{className:`banner banner-${e}`,role:e===`error`||e===`warn`?`alert`:`status`,children:[(0,J.jsx)(r,{className:`banner-ico`,size:15,"aria-hidden":`true`}),(0,J.jsx)(`div`,{className:`banner-body`,children:t}),n?(0,J.jsx)(`div`,{className:`banner-actions`,children:n}):null]})}function st(e){var t=e&&typeof e.querySelectorAll==`function`?e:document,n=document.documentElement,r={};function i(e,t){r[e]!==t&&(r[e]=t,n.style.setProperty(e,t))}var a=window.matchMedia(`(prefers-reduced-motion: reduce)`).matches,o=!0,s=[`x`,`y`,`z`,`rx`,`ry`,`rz`,`fog`,`dim`],c={x:0,y:0,z:0,rx:0,ry:0,rz:0,fog:.18,dim:1},l={x:`px`,y:`px`,z:`px`,rx:`deg`,ry:`deg`,rz:`deg`},u={x:`--cam-x`,y:`--cam-y`,z:`--cam-z`,rx:`--cam-rx`,ry:`--cam-ry`,rz:`--cam-rz`,fog:`--fog`,dim:`--scene-dim`};function d(e){return function(){e|=0,e=e+1831565813|0;var t=Math.imul(e^e>>>15,1|e);return t=t+Math.imul(t^t>>>7,61|t)^t,((t^t>>>14)>>>0)/4294967296}}var f=[{sel:`.dust.d3`,count:14,min:.9,max:1.5,seed:20261004},{sel:`.dust.d2`,count:10,min:1.3,max:2,seed:77110203},{sel:`.dust.d1`,count:6,min:1.8,max:2.8,seed:31415926}];function p(){f.forEach(function(e){for(var n=t.querySelectorAll(e.sel),r=0;r<n.length;r+=1){n[r].innerHTML=``;for(var i=d(e.seed),a=document.createDocumentFragment(),o=0;o<e.count;o+=1){var s=document.createElement(`i`),c=e.min+i()*(e.max-e.min);s.style.left=(i()*100).toFixed(2)+`%`,s.style.top=(i()*100).toFixed(2)+`%`,s.style.width=c.toFixed(2)+`px`,s.style.height=c.toFixed(2)+`px`,s.style.animationDelay=(i()*3200).toFixed(0)+`ms`,a.appendChild(s)}n[r].appendChild(a)}})}var m=[];function h(e){var t=e.getBoundingClientRect();return t.top+window.pageYOffset+t.height/2}function g(){m=[].slice.call(t.querySelectorAll(`[data-cam]`)).map(function(e){var t={},n=e.getAttribute(`data-cam`);if(n)try{t=JSON.parse(n)}catch{console.warn(`[scene] data-cam 不是合法 JSON,已忽略:`,e,n),t={}}return{at:h(e),cam:t}}),m.sort(function(e,t){return e.at-t.at})}function _(e){return e<.5?2*e*e:1-(-2*e+2)**2/2}function v(e){if(!m.length)return Object.assign({},c);for(var t=0;t<m.length-1&&e>m[t+1].at;)t+=1;var n=m[t],r=m[t+1],i=r?e<=n.at?0:(e-n.at)/(r.at-n.at):1;i=Math.max(0,Math.min(1,i));for(var a=_(i),o={},l=0;l<s.length;l+=1){var u=s[l],d=n.cam[u]===void 0?c[u]:n.cam[u];o[u]=d+((r&&r.cam[u]!==void 0?r.cam[u]:d)-d)*a}return o}var y=.16,b=null,x=null,S=0,C=0;function w(e){for(var t=0;t<s.length;t+=1){var n=s[t],r=l[n]||``;i(u[n],e[n].toFixed(3)+r)}}function T(e){var t=S?Math.min((e-S)/1e3,.12):.016;S=e,b||=Object.assign({},x);for(var n=a?1:1-Math.exp(-t/y),r=!0,i=0;i<s.length;i+=1){var o=s[i],c=x[o]-b[o];b[o]+=c*n;var l=Math.max(.0015,Math.abs(x[o])*.0012);Math.abs(c)>l&&(r=!1)}if(w(b),r){b=Object.assign({},x),w(x),C=0,S=0;return}C=requestAnimationFrame(T)}function E(){C||=(S=0,requestAnimationFrame(T))}function D(){if(o){var e=document.documentElement,t=Math.max(1,e.scrollHeight-window.innerHeight);i(`--scroll-p`,(window.pageYOffset/t).toFixed(4)),x=v(window.pageYOffset+window.innerHeight/2),E()}}var O={tx:0,ty:0,x:0,y:0},k=0,A=0,ee=window.matchMedia(`(hover: hover) and (pointer: fine)`).matches;function j(){i(`--look-x`,O.x.toFixed(4)),i(`--look-y`,O.y.toFixed(4))}function M(e){var t=A?Math.min((e-A)/1e3,.12):.016;A=e;var n=1-Math.exp(-t/y);O.x+=(O.tx-O.x)*n,O.y+=(O.ty-O.y)*n,j(),Math.abs(O.tx-O.x)>8e-4||Math.abs(O.ty-O.y)>8e-4?k=requestAnimationFrame(M):(O.x=O.tx,O.y=O.ty,j(),k=0,A=0)}function N(e){document.hidden||(O.tx=(e.clientX/window.innerWidth-.5)*2,O.ty=(e.clientY/window.innerHeight-.5)*2,k||=(A=0,requestAnimationFrame(M)))}function P(){O.tx=0,O.ty=0,k||=(A=0,requestAnimationFrame(M))}function te(){!a&&ee&&(window.addEventListener(`pointermove`,N,{passive:!0}),document.addEventListener(`pointerleave`,P))}var F=null,I=null,L=null;function ne(){if(p(),g(),!m.length){n.setAttribute(`data-scene-ready`,`static`);return}D(),te();var e=!1;F=function(){e||(e=!0,requestAnimationFrame(function(){e=!1,D()}))},I=function(){o&&(g(),D())},L=function(){o&&(g(),D())},window.addEventListener(`scroll`,F,{passive:!0}),window.addEventListener(`resize`,I),window.addEventListener(`load`,L),document.fonts&&document.fonts.ready&&document.fonts.ready.then(function(){o&&(g(),D())}),n.setAttribute(`data-scene-ready`,`1`)}function R(){o=!1,F&&window.removeEventListener(`scroll`,F),I&&window.removeEventListener(`resize`,I),L&&window.removeEventListener(`load`,L),window.removeEventListener(`pointermove`,N),document.removeEventListener(`pointerleave`,P),C&&cancelAnimationFrame(C),k&&cancelAnimationFrame(k),C=0,k=0,[].slice.call(t.querySelectorAll(`.dust`)).forEach(function(e){e.innerHTML=``}),Object.keys(u).forEach(function(e){n.style.removeProperty(u[e])}),n.style.removeProperty(`--scroll-p`),n.style.removeProperty(`--look-x`),n.style.removeProperty(`--look-y`),r={},n.removeAttribute(`data-scene-ready`)}return ne(),R}var ct=e=>e,lt=[{tint:`var(--iris)`,a:`0deg`,r:`430px`,y:`-40px`,w:`300px`,h:`520px`,z:`-18deg`,x:`16deg`,o:`.95`,e:`.70`,hot:`.26`,dof:`0px`,dur:`15s`,delay:`0s`},{tint:`var(--accent-cyan)`,a:`72deg`,r:`448px`,y:`10px`,w:`255px`,h:`470px`,z:`12deg`,x:`-22deg`,o:`.82`,e:`.18`,hot:`.05`,dof:`0px`,dur:`19s`,delay:`3s`},{tint:`var(--brand-500)`,a:`144deg`,r:`424px`,y:`-60px`,w:`325px`,h:`560px`,z:`-24deg`,x:`19deg`,o:`.90`,e:`.52`,hot:`.18`,dof:`0px`,dur:`17s`,delay:`6.5s`},{tint:`var(--brand-400)`,a:`216deg`,r:`456px`,y:`20px`,w:`270px`,h:`490px`,z:`16deg`,x:`-14deg`,o:`.76`,e:`.14`,hot:`.04`,dof:`0px`,dur:`21s`,delay:`10s`},{tint:`var(--accent-blue)`,a:`288deg`,r:`436px`,y:`-30px`,w:`310px`,h:`535px`,z:`-14deg`,x:`24deg`,o:`.88`,e:`.30`,hot:`.12`,dof:`0px`,dur:`18s`,delay:`13.5s`},{tint:`var(--brand-500)`,a:`36deg`,r:`860px`,y:`40px`,w:`400px`,h:`560px`,z:`-22deg`,x:`26deg`,o:`.62`,e:`.20`,hot:`.06`,dof:`2.6px`,dur:`26s`,delay:`2s`,soft:!0},{tint:`var(--accent-cyan)`,a:`126deg`,r:`900px`,y:`-20px`,w:`360px`,h:`520px`,z:`18deg`,x:`-28deg`,o:`.52`,e:`.10`,hot:`.03`,dof:`2.6px`,dur:`30s`,delay:`9s`,soft:!0},{tint:`var(--iris)`,a:`216deg`,r:`840px`,y:`60px`,w:`440px`,h:`620px`,z:`-28deg`,x:`20deg`,o:`.58`,e:`.30`,hot:`.09`,dof:`2.6px`,dur:`24s`,delay:`15s`,soft:!0},{tint:`var(--brand-400)`,a:`306deg`,r:`890px`,y:`-10px`,w:`380px`,h:`540px`,z:`14deg`,x:`-24deg`,o:`.48`,e:`.08`,hot:`.03`,dof:`2.6px`,dur:`33s`,delay:`19s`,soft:!0}];function ut(){return(0,J.jsxs)(`div`,{className:`scene`,"aria-hidden":`true`,children:[(0,J.jsxs)(`div`,{className:`rig`,children:[(0,J.jsx)(`div`,{className:`tilt`,children:(0,J.jsx)(`div`,{className:`stage`,children:lt.map((e,t)=>(0,J.jsx)(`i`,{className:e.soft?`pl soft`:`pl`,style:ct({"--tint":e.tint,"--a":e.a,"--r":e.r,"--y":e.y,"--w":e.w,"--h":e.h,"--z":e.z,"--x":e.x,"--o":e.o,"--e":e.e,"--hot":e.hot,"--dof":e.dof,"--sheen-dur":e.dur,"--sheen-delay":e.delay})},t))})}),(0,J.jsx)(`div`,{className:`dust d3`}),(0,J.jsx)(`div`,{className:`dust d2`}),(0,J.jsx)(`div`,{className:`dust d1`})]}),(0,J.jsx)(`div`,{className:`core`}),(0,J.jsx)(`div`,{className:`nucleus`}),(0,J.jsx)(`div`,{className:`beam b1`}),(0,J.jsx)(`div`,{className:`beam b2`}),(0,J.jsx)(`div`,{className:`fog`}),(0,J.jsx)(`div`,{className:`dimmer`}),(0,J.jsx)(`div`,{className:`vignette`}),(0,J.jsx)(`div`,{className:`noise`})]})}function dt(){return(0,x.useEffect)(()=>st(document),[]),(0,J.jsx)(ut,{})}function ft({session:e,mockHint:r}){let[o,s]=(0,x.useState)(``),[c,l]=(0,x.useState)(!1),[u,d]=(0,x.useState)(!1),[f,p]=(0,x.useState)(null),m=(0,x.useRef)(null);return(0,x.useEffect)(()=>{let e=m.current;if(!e||!window.matchMedia(`(hover: hover) and (pointer: fine)`).matches)return;let t=t=>{let n=e.getBoundingClientRect();e.style.setProperty(`--mx`,`${t.clientX-n.left}px`),e.style.setProperty(`--my`,`${t.clientY-n.top}px`)};return e.addEventListener(`pointermove`,t),()=>e.removeEventListener(`pointermove`,t)},[]),(0,J.jsxs)(`div`,{className:`login-wrap landing`,children:[(0,J.jsx)(dt,{}),(0,J.jsxs)(`div`,{className:`login-card`,ref:m,children:[(0,J.jsx)(`span`,{className:`login-glow`,"aria-hidden":`true`}),(0,J.jsxs)(`div`,{className:`login-brand`,children:[(0,J.jsx)(Y,{size:30}),(0,J.jsx)(`span`,{className:`b-name`,children:`途关`}),(0,J.jsx)(`span`,{className:`b-en`,children:`Waygate`})]}),(0,J.jsx)(`h1`,{children:`登录控制台`}),(0,J.jsx)(`p`,{className:`sub`,children:`这是自用工具,只有一个管理口令。口令校验在服务端完成,前端不保存明文。`}),(0,J.jsxs)(`form`,{className:`login-form`,onSubmit:async t=>{if(t.preventDefault(),!u){d(!0),p(null);try{await e.login(o)}catch(e){p(e instanceof R?e:new R(String(e),0,0)),d(!1)}}},children:[(0,J.jsxs)(`div`,{className:`login-field`,children:[(0,J.jsx)(`label`,{htmlFor:`pw`,children:`管理口令`}),(0,J.jsxs)(`div`,{className:`login-input`,children:[(0,J.jsx)(t,{size:15,color:`var(--text-faint)`,"aria-hidden":!0}),(0,J.jsx)(`input`,{id:`pw`,type:c?`text`:`password`,value:o,autoFocus:!0,autoComplete:`current-password`,placeholder:`输入管理口令`,onChange:e=>s(e.target.value)}),(0,J.jsx)(`button`,{type:`button`,className:`login-eye`,"aria-label":c?`隐藏口令`:`显示口令`,onClick:()=>l(e=>!e),children:c?(0,J.jsx)(n,{size:15}):(0,J.jsx)(i,{size:15})})]})]}),f?(0,J.jsx)(ot,{tone:`error`,children:f.message}):null,(0,J.jsxs)(`button`,{type:`submit`,className:`btn btn-primary login-submit`,disabled:u||!o,children:[u?(0,J.jsx)(a,{size:16}):null,u?`正在验证…`:`进入控制台`]})]}),(0,J.jsx)(`p`,{className:`login-hint`,children:r?`当前为 Mock 模式(npm run dev:mock),口令固定为 ${r}。`:`口令首次启动时若未配置 RELAY_ADMIN_PASSWORD_HASH,会打印到服务端 stdout 一次。`})]})]})}function pt(){return(0,J.jsx)(`div`,{className:`login-wrap`,children:(0,J.jsxs)(`div`,{style:{display:`flex`,flexDirection:`column`,alignItems:`center`,gap:16},children:[(0,J.jsx)(Y,{size:40}),(0,J.jsx)(`div`,{style:{fontSize:12.5,color:`var(--text-ghost)`},children:`正在确认会话…`})]})})}var mt=`modulepreload`,ht=function(e,t){return new URL(e,t).href},gt={},_t=function(e){return e.pathname.endsWith(`.css`)},$=function(e,t,n){let r=Promise.resolve();if(t&&t.length>0){let e,i=document.querySelector(`meta[property=csp-nonce]`),a=i?.nonce||i?.getAttribute(`nonce`);function o(e){return Promise.all(e.map(e=>Promise.resolve(e).then(e=>({status:`fulfilled`,value:e}),e=>({status:`rejected`,reason:e}))))}function s(e){return import.meta.resolve?new URL(import.meta.resolve(e)):new URL(e,import.meta.url)}r=o(t.map(t=>{t=ht(t,n);let r=s(t);if(r.href in gt)return;gt[r.href]=!0;let i=_t(r);if(e===void 0){e={all:new Set,styles:new Set};let t=document.getElementsByTagName(`link`);for(let n=t.length-1;n>=0;n--){let r=t[n];e.all.add(r.href),r.rel===`stylesheet`&&e.styles.add(r.href)}}if((i?e.styles:e.all).has(r.href))return;let o=document.createElement(`link`);if(o.rel=i?`stylesheet`:mt,i||(o.as=`script`),o.crossOrigin=``,o.href=r.href,a&&o.setAttribute(`nonce`,a),document.head.appendChild(o),i)return new Promise((e,t)=>{o.addEventListener(`load`,e),o.addEventListener(`error`,()=>t(Error(`Unable to preload CSS for ${r}`)))})}).filter(e=>e!==void 0))}function i(e){let t=new Event(`vite:preloadError`,{cancelable:!0});if(t.payload=e,window.dispatchEvent(t),!t.defaultPrevented)throw e}return r.then(t=>{for(let e of t||[])e.status===`rejected`&&i(e.reason);return e().catch(i)})},vt=(0,x.lazy)(()=>$(()=>import(`./LandingPage-Bv4IWIsz.js`).then(e=>({default:e.LandingPage})),__vite__mapDeps([0,1,2,3]),import.meta.url)),yt=(0,x.lazy)(()=>$(()=>import(`./OverviewPage-Dus_pE-a.js`).then(e=>({default:e.OverviewPage})),__vite__mapDeps([4,1,5,6,7,8,9]),import.meta.url)),bt=(0,x.lazy)(()=>$(()=>import(`./UsagePage-dnOsX2C4.js`).then(e=>({default:e.UsagePage})),__vite__mapDeps([10,1,5,6,7,8,9]),import.meta.url)),xt=(0,x.lazy)(()=>$(()=>import(`./ClientsPage-BfXxV7sc.js`).then(e=>({default:e.ClientsPage})),__vite__mapDeps([11,1,5,12,13,6,7,14,15]),import.meta.url)),St=(0,x.lazy)(()=>$(()=>import(`./ApiKeysPage-DutxhNxx.js`).then(e=>({default:e.ApiKeysPage})),__vite__mapDeps([16,1,5,12,13,6]),import.meta.url)),Ct=(0,x.lazy)(()=>$(()=>import(`./RequestsPage-B7Lt3DYE.js`).then(e=>({default:e.RequestsPage})),__vite__mapDeps([17,1,5,6,14,13,8]),import.meta.url)),wt=(0,x.lazy)(()=>$(()=>import(`./SettingsPage-BPLnBLQJ.js`).then(e=>({default:e.SettingsPage})),__vite__mapDeps([18,1,2,5,12,13,14,15]),import.meta.url));function Tt(){let[e,t]=(0,x.useState)(()=>window.location.pathname);return(0,x.useEffect)(()=>{let e=()=>t(window.location.pathname);return window.addEventListener(`popstate`,e),()=>window.removeEventListener(`popstate`,e)},[]),e}var Et=`Waygate — 控制台`;function Dt(){return(0,J.jsx)(`div`,{style:{display:`flex`,alignItems:`center`,justifyContent:`center`,minHeight:`50vh`,fontSize:12.5,color:`var(--text-ghost)`},children:`加载中…`})}function Ot(){let{route:e,navigate:t}=ne(),n=Ke();return(0,x.useEffect)(()=>{document.title=Et},[]),(0,x.useEffect)(()=>{window.location.hash||(window.location.hash=`#/overview`)},[]),n.status===`loading`?(0,J.jsx)(pt,{}):n.status===`anon`?(0,J.jsx)(ft,{session:n,mockHint:null}):(0,J.jsx)(it,{route:e,navigate:t,expiresAt:n.expiresAt,onLogout:()=>void n.logout(),children:(0,J.jsxs)(x.Suspense,{fallback:(0,J.jsx)(Dt,{}),children:[e===`overview`?(0,J.jsx)(yt,{navigate:t}):null,e===`usage`?(0,J.jsx)(bt,{}):null,e===`clients`?(0,J.jsx)(xt,{}):null,e===`keys`?(0,J.jsx)(St,{}):null,e===`requests`?(0,J.jsx)(Ct,{}):null,e===`settings`?(0,J.jsx)(wt,{}):null]})})}function kt(){let e=Tt(),t=C(e)===`console`;return(0,x.useEffect)(()=>{F()},[e]),t?(0,J.jsx)(Ot,{}):(0,J.jsx)(x.Suspense,{fallback:null,children:(0,J.jsx)(vt,{})})}var At=(0,x.createContext)(null),jt={error:{icon:m,defaultMs:8e3},warn:{icon:m,defaultMs:8e3},success:{icon:s,defaultMs:5e3},info:{icon:r,defaultMs:5e3}};function Mt({children:e}){let[t,n]=(0,x.useState)([]),r=(0,x.useRef)(1),i=(0,x.useCallback)(e=>{n(t=>t.filter(t=>t.id!==e))},[]),a=(0,x.useCallback)(e=>{let t=r.current++;return n(n=>[...n,{...e,id:t}].slice(-4)),t},[]),o=(0,x.useMemo)(()=>({push:a,dismiss:i}),[a,i]);return(0,J.jsxs)(At.Provider,{value:o,children:[e,typeof document<`u`?(0,Je.createPortal)((0,J.jsx)(`div`,{className:`toast-stack`,"aria-live":`polite`,"aria-atomic":`false`,children:t.map(e=>(0,J.jsx)(Nt,{item:e,onDismiss:i},e.id))}),document.body):null]})}function Nt({item:e,onDismiss:t}){let{icon:n,defaultMs:r}=jt[e.tone],i=e.durationMs??r,[a,o]=(0,x.useState)(!1),[s,c]=(0,x.useState)(i);return(0,x.useEffect)(()=>{if(a)return;let n=Date.now(),r=window.setInterval(()=>{let a=i-(Date.now()-n);a<=0?(window.clearInterval(r),t(e.id)):c(a)},100);return()=>window.clearInterval(r)},[a,i,e.id,t]),(0,J.jsxs)(`div`,{className:`toast toast-${e.tone}`,role:e.tone===`error`||e.tone===`warn`?`alert`:`status`,onMouseEnter:()=>o(!0),onMouseLeave:()=>o(!1),onFocus:()=>o(!0),onBlur:()=>o(!1),children:[(0,J.jsx)(n,{className:`toast-ico`,size:15,"aria-hidden":`true`}),(0,J.jsx)(`div`,{className:`toast-body`,children:e.message}),(0,J.jsx)(`button`,{type:`button`,className:`toast-close`,"aria-label":`关闭提示`,onClick:()=>t(e.id),children:`×`}),(0,J.jsx)(`span`,{className:`toast-progress${a?` paused`:``}`,style:{animationDuration:`${i}ms`},"aria-hidden":`true`})]})}function Pt(){return(0,x.useContext)(At)??{push:()=>0,dismiss:()=>{}}}w(),T(),F();for(let e of[`icon`,`apple-touch-icon`]){let t=document.createElement(`link`);t.rel=e,t.type=`image/svg+xml`,t.href=`/icon.svg?v=2`,document.head.appendChild(t)}var Ft=document.getElementById(`root`);if(!Ft)throw Error(`#root 未找到 —— index.html 被改坏了`);(0,S.createRoot)(Ft).render((0,J.jsx)(x.StrictMode,{children:(0,J.jsx)(Mt,{children:(0,J.jsx)(kt,{})})}));export{me as A,Le as C,he as D,Re as E,R as M,fe as O,Ie as S,Pe as T,be as _,Ze as a,Ee as b,q as c,xe as d,De as f,ve as g,we as h,nt as i,de as j,pe as k,Me as l,Oe as m,dt as n,Y as o,ye as p,ot as r,Ke as s,Pt as t,Ae as u,ke as v,Te as w,Ce as x,je as y};