@jingyi0605/codingns4dsh 0.2.1-rc.6 → 0.2.1-rc.7
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.
- package/README.en.md +3 -3
- package/README.md +3 -3
- package/data/build/dist/client/bundle.js +1412 -103
- package/data/build/dist/client/bundle.js.map +1 -1
- package/data/build/dist/client/client.native-workspace-store.js +1 -1
- package/data/build/dist/client/client.native-workspace-store.js.map +1 -1
- package/data/build/dist/client/client.transport.js +202 -0
- package/data/build/dist/client/client.transport.js.map +1 -1
- package/data/build/dist/client/desktop-assistant.js +202 -0
- package/data/build/dist/client/features/index.d.ts +2 -1
- package/data/build/dist/client/features/index.d.ts.map +1 -1
- package/data/build/dist/client/features/index.js +3 -1
- package/data/build/dist/client/features/index.js.map +1 -1
- package/data/build/dist/client/features/magpie-management-page.d.ts +7 -3
- package/data/build/dist/client/features/magpie-management-page.d.ts.map +1 -1
- package/data/build/dist/client/features/magpie-management-page.js +142 -8
- package/data/build/dist/client/features/magpie-management-page.js.map +1 -1
- package/data/build/dist/client/features/workspace-mcp.d.ts +3 -0
- package/data/build/dist/client/features/workspace-mcp.d.ts.map +1 -0
- package/data/build/dist/client/features/workspace-mcp.js +320 -0
- package/data/build/dist/client/features/workspace-mcp.js.map +1 -0
- package/data/build/dist/client/locale.d.ts.map +1 -1
- package/data/build/dist/client/locale.js +176 -0
- package/data/build/dist/client/locale.js.map +1 -1
- package/data/build/dist/client/locales/magpie.d.ts.map +1 -1
- package/data/build/dist/client/locales/magpie.js +12 -0
- package/data/build/dist/client/locales/magpie.js.map +1 -1
- package/data/build/dist/client/locales/usage.d.ts.map +1 -1
- package/data/build/dist/client/locales/usage.js +14 -0
- package/data/build/dist/client/locales/usage.js.map +1 -1
- package/data/build/dist/client/subscription-slot.d.ts.map +1 -1
- package/data/build/dist/client/subscription-slot.js +104 -11
- package/data/build/dist/client/subscription-slot.js.map +1 -1
- package/data/build/dist/dsh-capabilities/host/workspace-approval-adapter.d.ts +18 -0
- package/data/build/dist/dsh-capabilities/host/workspace-approval-adapter.d.ts.map +1 -0
- package/data/build/dist/dsh-capabilities/host/workspace-approval-adapter.js +172 -0
- package/data/build/dist/dsh-capabilities/host/workspace-approval-adapter.js.map +1 -0
- package/data/build/dist/dsh-capabilities/host/workspace-pending-questions-adapter.d.ts +28 -0
- package/data/build/dist/dsh-capabilities/host/workspace-pending-questions-adapter.d.ts.map +1 -0
- package/data/build/dist/dsh-capabilities/host/workspace-pending-questions-adapter.js +103 -0
- package/data/build/dist/dsh-capabilities/host/workspace-pending-questions-adapter.js.map +1 -0
- package/data/build/dist/dsh-capabilities/host/workspace-session-control-adapter.d.ts +26 -0
- package/data/build/dist/dsh-capabilities/host/workspace-session-control-adapter.d.ts.map +1 -0
- package/data/build/dist/dsh-capabilities/host/workspace-session-control-adapter.js +86 -0
- package/data/build/dist/dsh-capabilities/host/workspace-session-control-adapter.js.map +1 -0
- package/data/build/dist/dsh-capabilities/matrix.d.ts.map +1 -1
- package/data/build/dist/dsh-capabilities/matrix.js +3 -0
- package/data/build/dist/dsh-capabilities/matrix.js.map +1 -1
- package/data/build/dist/dsh-capabilities/routes.d.ts.map +1 -1
- package/data/build/dist/dsh-capabilities/routes.js +9 -0
- package/data/build/dist/dsh-capabilities/routes.js.map +1 -1
- package/data/build/dist/dsh-capabilities/types.d.ts +1 -1
- package/data/build/dist/dsh-capabilities/types.d.ts.map +1 -1
- package/data/build/dist/dsh-capabilities/types.js.map +1 -1
- package/data/build/dist/host/cli-adapters/claude-model-options.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/claude-model-options.js +13 -2
- package/data/build/dist/host/cli-adapters/claude-model-options.js.map +1 -1
- package/data/build/dist/host/cli-adapters/dsh-message-projector.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/dsh-message-projector.js +1 -0
- package/data/build/dist/host/cli-adapters/dsh-message-projector.js.map +1 -1
- package/data/build/dist/host/cli-adapters/feature.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/feature.js +5 -1
- package/data/build/dist/host/cli-adapters/feature.js.map +1 -1
- package/data/build/dist/host/cli-adapters/magpie-usage.d.ts +13 -2
- package/data/build/dist/host/cli-adapters/magpie-usage.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/magpie-usage.js +180 -13
- package/data/build/dist/host/cli-adapters/magpie-usage.js.map +1 -1
- package/data/build/dist/host/features/index.d.ts +1 -0
- package/data/build/dist/host/features/index.d.ts.map +1 -1
- package/data/build/dist/host/features/index.js +3 -0
- package/data/build/dist/host/features/index.js.map +1 -1
- package/data/build/dist/host/features/workspace-mcp.d.ts +9 -0
- package/data/build/dist/host/features/workspace-mcp.d.ts.map +1 -0
- package/data/build/dist/host/features/workspace-mcp.js +197 -0
- package/data/build/dist/host/features/workspace-mcp.js.map +1 -0
- package/data/build/dist/host/index.d.ts.map +1 -1
- package/data/build/dist/host/index.js +6 -2
- package/data/build/dist/host/index.js.map +1 -1
- package/data/build/dist/host/native-session-bridge.d.ts +2 -0
- package/data/build/dist/host/native-session-bridge.d.ts.map +1 -1
- package/data/build/dist/host/native-session-bridge.js +30 -0
- package/data/build/dist/host/native-session-bridge.js.map +1 -1
- package/data/build/dist/host/rpc.d.ts +4 -1
- package/data/build/dist/host/rpc.d.ts.map +1 -1
- package/data/build/dist/host/rpc.js +57 -9
- package/data/build/dist/host/rpc.js.map +1 -1
- package/data/build/dist/host/session-handle-eviction.d.ts +4 -2
- package/data/build/dist/host/session-handle-eviction.d.ts.map +1 -1
- package/data/build/dist/host/session-handle-eviction.js +10 -9
- package/data/build/dist/host/session-handle-eviction.js.map +1 -1
- package/data/build/dist/host/terminal/terminal-process-service.d.ts +22 -0
- package/data/build/dist/host/terminal/terminal-process-service.d.ts.map +1 -1
- package/data/build/dist/host/terminal/terminal-process-service.js +102 -0
- package/data/build/dist/host/terminal/terminal-process-service.js.map +1 -1
- package/data/build/dist/host/terminal/terminal-service.d.ts +5 -1
- package/data/build/dist/host/terminal/terminal-service.d.ts.map +1 -1
- package/data/build/dist/host/terminal/terminal-service.js +32 -0
- package/data/build/dist/host/terminal/terminal-service.js.map +1 -1
- package/data/build/dist/host/workspace-mcp/api-key-store.d.ts +16 -0
- package/data/build/dist/host/workspace-mcp/api-key-store.d.ts.map +1 -0
- package/data/build/dist/host/workspace-mcp/api-key-store.js +65 -0
- package/data/build/dist/host/workspace-mcp/api-key-store.js.map +1 -0
- package/data/build/dist/host/workspace-mcp/tools.d.ts +54 -0
- package/data/build/dist/host/workspace-mcp/tools.d.ts.map +1 -0
- package/data/build/dist/host/workspace-mcp/tools.js +800 -0
- package/data/build/dist/host/workspace-mcp/tools.js.map +1 -0
- package/data/build/dist/host/workspace-mcp/transport.d.ts +35 -0
- package/data/build/dist/host/workspace-mcp/transport.d.ts.map +1 -0
- package/data/build/dist/host/workspace-mcp/transport.js +575 -0
- package/data/build/dist/host/workspace-mcp/transport.js.map +1 -0
- package/data/build/dist/shared/contracts/magpie-management.d.ts +15 -1
- package/data/build/dist/shared/contracts/magpie-management.d.ts.map +1 -1
- package/data/build/dist/shared/contracts/subscription.d.ts +7 -0
- package/data/build/dist/shared/contracts/subscription.d.ts.map +1 -1
- package/data/build/dist/shared/contracts/subscription.js.map +1 -1
- package/data/build/dist/shared/contracts/terminal.d.ts +2 -0
- package/data/build/dist/shared/contracts/terminal.d.ts.map +1 -1
- package/data/build/dist/shared/contracts/version.d.ts +1 -1
- package/data/build/dist/shared/contracts/version.js +1 -1
- package/package.json +1 -1
- package/profile/README.md +2 -2
- package/profile/package.json +2 -2
- package/profile/version.json +1 -1
- package/version.json +1 -1
|
@@ -92,6 +92,12 @@ export function MagpieManagementPage({ rpc, locale, initialPageTab = 'overview',
|
|
|
92
92
|
const [dashboardLoading, setDashboardLoading] = useState(true);
|
|
93
93
|
const [dashboardError, setDashboardError] = useState(false);
|
|
94
94
|
const [dashboardIssue, setDashboardIssue] = useState(null);
|
|
95
|
+
const [quotaPolicyPending, setQuotaPolicyPending] = useState(null);
|
|
96
|
+
const [quotaPolicyFailed, setQuotaPolicyFailed] = useState(false);
|
|
97
|
+
const [quotaResetTarget, setQuotaResetTarget] = useState(null);
|
|
98
|
+
const [quotaResetPending, setQuotaResetPending] = useState(false);
|
|
99
|
+
const [quotaResetResult, setQuotaResetResult] = useState(null);
|
|
100
|
+
const [quotaResetFailed, setQuotaResetFailed] = useState(false);
|
|
95
101
|
const [chartMetric, setChartMetric] = useState('calls');
|
|
96
102
|
const [sessionSearch, setSessionSearch] = useState('');
|
|
97
103
|
const [selectedSession, setSelectedSession] = useState(null);
|
|
@@ -114,14 +120,14 @@ export function MagpieManagementPage({ rpc, locale, initialPageTab = 'overview',
|
|
|
114
120
|
const dashboardSequence = useRef(0);
|
|
115
121
|
const requestSequence = useRef(0);
|
|
116
122
|
const managementSequence = useRef(0);
|
|
117
|
-
const loadDashboard = useCallback(async (signal) => {
|
|
123
|
+
const loadDashboard = useCallback(async (signal, force = false) => {
|
|
118
124
|
const sequence = dashboardSequence.current + 1;
|
|
119
125
|
dashboardSequence.current = sequence;
|
|
120
126
|
setDashboardLoading(true);
|
|
121
127
|
setDashboardError(false);
|
|
122
128
|
setDashboardIssue(null);
|
|
123
129
|
try {
|
|
124
|
-
const next = await callMagpieRpc(rpc, 'usage/dashboard', { period }, signal);
|
|
130
|
+
const next = await callMagpieRpc(rpc, 'usage/dashboard', { period, ...(force ? { force: true } : {}) }, signal);
|
|
125
131
|
if (signal.aborted || sequence !== dashboardSequence.current)
|
|
126
132
|
return;
|
|
127
133
|
setDashboard(next);
|
|
@@ -141,6 +147,47 @@ export function MagpieManagementPage({ rpc, locale, initialPageTab = 'overview',
|
|
|
141
147
|
setDashboardLoading(false);
|
|
142
148
|
}
|
|
143
149
|
}, [period, rpc]);
|
|
150
|
+
const updateQuotaPolicy = useCallback(async (user, policy, enabled) => {
|
|
151
|
+
if (quotaPolicyPending !== null)
|
|
152
|
+
return;
|
|
153
|
+
setQuotaPolicyPending(`${user}:${policy}`);
|
|
154
|
+
setQuotaPolicyFailed(false);
|
|
155
|
+
try {
|
|
156
|
+
await callMagpieRpc(rpc, 'usage/account/update', { user, policy, enabled });
|
|
157
|
+
await loadDashboard(new AbortController().signal, true);
|
|
158
|
+
}
|
|
159
|
+
catch {
|
|
160
|
+
setQuotaPolicyFailed(true);
|
|
161
|
+
}
|
|
162
|
+
finally {
|
|
163
|
+
setQuotaPolicyPending(null);
|
|
164
|
+
}
|
|
165
|
+
}, [loadDashboard, quotaPolicyPending, rpc]);
|
|
166
|
+
const closeQuotaReset = () => {
|
|
167
|
+
if (quotaResetPending)
|
|
168
|
+
return;
|
|
169
|
+
setQuotaResetTarget(null);
|
|
170
|
+
setQuotaResetResult(null);
|
|
171
|
+
setQuotaResetFailed(false);
|
|
172
|
+
};
|
|
173
|
+
const confirmQuotaReset = async () => {
|
|
174
|
+
const target = quotaResetTarget;
|
|
175
|
+
if (target === null || quotaResetPending)
|
|
176
|
+
return;
|
|
177
|
+
setQuotaResetPending(true);
|
|
178
|
+
setQuotaResetFailed(false);
|
|
179
|
+
try {
|
|
180
|
+
const result = await callMagpieRpc(rpc, 'usage/reset', { user: target.user });
|
|
181
|
+
setQuotaResetResult(result.outcome);
|
|
182
|
+
await loadDashboard(new AbortController().signal, true);
|
|
183
|
+
}
|
|
184
|
+
catch {
|
|
185
|
+
setQuotaResetFailed(true);
|
|
186
|
+
}
|
|
187
|
+
finally {
|
|
188
|
+
setQuotaResetPending(false);
|
|
189
|
+
}
|
|
190
|
+
};
|
|
144
191
|
useEffect(() => {
|
|
145
192
|
const controller = new AbortController();
|
|
146
193
|
void loadDashboard(controller.signal);
|
|
@@ -456,7 +503,28 @@ export function MagpieManagementPage({ rpc, locale, initialPageTab = 'overview',
|
|
|
456
503
|
? createElement(SessionsPage, { dashboard, sessions: filteredSessions, search: sessionSearch, onSearch: setSessionSearch, onOpenSession: openSession, t })
|
|
457
504
|
: section === 'requests'
|
|
458
505
|
? createElement(RequestsPage, { page: requestPage, loading: requestLoading, error: requestError, selectedSession, offset: requestOffset, onOffsetChange: setRequestOffset, onClearSession: clearSession, t })
|
|
459
|
-
: createElement(QuotasPage, {
|
|
506
|
+
: createElement(QuotasPage, {
|
|
507
|
+
dashboard, loading: dashboardLoading, quotaView, t,
|
|
508
|
+
policyPending: quotaPolicyPending,
|
|
509
|
+
policyFailed: quotaPolicyFailed,
|
|
510
|
+
onPolicyChange: updateQuotaPolicy,
|
|
511
|
+
onResetRequest: (quota) => {
|
|
512
|
+
if (quota.user === null || quota.resets?.count === null || quota.resets?.count === undefined || quota.resets.count <= 0)
|
|
513
|
+
return;
|
|
514
|
+
setQuotaResetTarget({ user: quota.user, account: quota.alias ?? quota.name, count: quota.resets.count });
|
|
515
|
+
setQuotaResetResult(null);
|
|
516
|
+
setQuotaResetFailed(false);
|
|
517
|
+
},
|
|
518
|
+
})), quotaResetTarget !== null && createElement(MagpieQuotaResetDialog, {
|
|
519
|
+
target: quotaResetTarget,
|
|
520
|
+
pending: quotaResetPending,
|
|
521
|
+
result: quotaResetResult,
|
|
522
|
+
failed: quotaResetFailed,
|
|
523
|
+
t,
|
|
524
|
+
onCancel: closeQuotaReset,
|
|
525
|
+
onConfirm: confirmQuotaReset,
|
|
526
|
+
onClose: closeQuotaReset,
|
|
527
|
+
}));
|
|
460
528
|
}
|
|
461
529
|
export function OverviewPage({ dashboard, loading, error, chartMetric, onChartMetricChange, t, onOpenSession }) {
|
|
462
530
|
const [modelBreakdownMode, setModelBreakdownMode] = useState('aggregate');
|
|
@@ -761,7 +829,7 @@ function QuotaViewIcon() {
|
|
|
761
829
|
className: 'codingns-magpie-quota-view-icon-svg',
|
|
762
830
|
}, createElement('circle', { cx: 8, cy: 8, r: 6.25, stroke: 'currentColor', strokeWidth: 1.5, opacity: 0.45 }), createElement('path', { d: 'M8 1.75a6.25 6.25 0 0 1 0 12.5z', fill: 'currentColor' }));
|
|
763
831
|
}
|
|
764
|
-
export function QuotasPage({ dashboard, loading, quotaView = DEFAULT_SUBSCRIPTION_REPORT_SETTINGS.quotaView, t }) {
|
|
832
|
+
export function QuotasPage({ dashboard, loading, quotaView = DEFAULT_SUBSCRIPTION_REPORT_SETTINGS.quotaView, t, policyPending = null, policyFailed = false, onPolicyChange = () => undefined, onResetRequest = () => undefined }) {
|
|
765
833
|
const quotaUnavailable = dashboard?.quotaStatus !== 'available';
|
|
766
834
|
const quotas = dashboard?.quotas ?? [];
|
|
767
835
|
const quotaHistory = dashboard?.quotaHistory ?? [];
|
|
@@ -769,7 +837,9 @@ export function QuotasPage({ dashboard, loading, quotaView = DEFAULT_SUBSCRIPTIO
|
|
|
769
837
|
? createElement(EmptyState, { message: t(dashboard === null && loading ? 'magpie.loading' : 'magpie.quotaUnavailable'), loading: dashboard === null && loading })
|
|
770
838
|
: quotas.length === 0
|
|
771
839
|
? createElement(EmptyState, { message: t('magpie.noQuotas') })
|
|
772
|
-
: createElement('div', { className: 'codingns-magpie-quota-grid' }, ...groupQuotaRowsByProvider(quotas).map((group) => createElement(QuotaGroupCard, {
|
|
840
|
+
: createElement('div', { className: 'codingns-magpie-quota-grid' }, ...groupQuotaRowsByProvider(quotas).map((group) => createElement(QuotaGroupCard, {
|
|
841
|
+
key: group.provider, group, quotaView, t, policyPending, policyFailed, onPolicyChange, onResetRequest,
|
|
842
|
+
}))), createElement('section', { className: 'codingns-magpie-panel codingns-magpie-history-panel' }, createElement('div', { className: 'codingns-magpie-panel-head' }, createElement('div', undefined, createElement('h2', undefined, t('magpie.quotaHistory')), createElement('p', undefined, t('magpie.quotaHistoryNote')))), quotaHistory.length === 0
|
|
773
843
|
? createElement('div', { className: 'codingns-magpie-inline-empty' }, t(dashboard === null && loading ? 'magpie.loading' : dashboard?.quotaHistoryStatus === 'available' ? 'magpie.noHistory' : 'magpie.historyUnavailable'))
|
|
774
844
|
: createElement('div', { className: 'codingns-magpie-history-grid' }, ...quotaHistory.map((history) => createElement(QuotaHistoryCard, { key: `${history.provider}:${history.user ?? ''}`, history })))));
|
|
775
845
|
}
|
|
@@ -815,7 +885,7 @@ function ProgressSection({ title, rows, t, onOpen, header, limit = 8 }) {
|
|
|
815
885
|
* 同一厂商的多个账号(如 WorkBuddy 的 4 个)共用一张卡,避免每个账号各占一张卡导致
|
|
816
886
|
* 同类账号被拆散在网格各处;单账号厂商的读法与改造前一致。
|
|
817
887
|
*/
|
|
818
|
-
function QuotaGroupCard({ group, quotaView = DEFAULT_SUBSCRIPTION_REPORT_SETTINGS.quotaView, t }) {
|
|
888
|
+
function QuotaGroupCard({ group, quotaView = DEFAULT_SUBSCRIPTION_REPORT_SETTINGS.quotaView, t, policyPending, policyFailed, onPolicyChange, onResetRequest }) {
|
|
819
889
|
const first = group.accounts[0];
|
|
820
890
|
// 默认展开:只有用户主动收起后才是折叠态。
|
|
821
891
|
const [collapsed, setCollapsed] = useState(false);
|
|
@@ -835,6 +905,10 @@ function QuotaGroupCard({ group, quotaView = DEFAULT_SUBSCRIPTION_REPORT_SETTING
|
|
|
835
905
|
quota,
|
|
836
906
|
quotaView,
|
|
837
907
|
t,
|
|
908
|
+
policyPending,
|
|
909
|
+
policyFailed,
|
|
910
|
+
onPolicyChange,
|
|
911
|
+
onResetRequest,
|
|
838
912
|
// 单账号时不重复显示账号段头,保持与改造前一致的读法。
|
|
839
913
|
showHeading: multi,
|
|
840
914
|
})));
|
|
@@ -846,13 +920,15 @@ function QuotaGroupCard({ group, quotaView = DEFAULT_SUBSCRIPTION_REPORT_SETTING
|
|
|
846
920
|
* Sub2api 的钱包余额、按积分计量的 WorkBuddy)单独显示余额行,与 Magpie 原生卡片
|
|
847
921
|
* 一致——过去这些账号只剩一条空进度条,余额被完全藏起来。
|
|
848
922
|
*/
|
|
849
|
-
function QuotaAccountSection({ quota, quotaView = DEFAULT_SUBSCRIPTION_REPORT_SETTINGS.quotaView, t, showHeading }) {
|
|
923
|
+
function QuotaAccountSection({ quota, quotaView = DEFAULT_SUBSCRIPTION_REPORT_SETTINGS.quotaView, t, showHeading, policyPending, policyFailed, onPolicyChange, onResetRequest }) {
|
|
850
924
|
// `daily` 现在带 `since`,按日点位于 `days` 里。
|
|
851
925
|
const dailyValues = quota.daily.days.map((point) => point.used).filter((value) => value !== null);
|
|
852
926
|
const balance = resolveQuotaAccountBalance(quota);
|
|
853
927
|
// 只有真正带百分比的窗口才画进度条;纯金额窗口在余额行里已经有完整读法。
|
|
854
928
|
const percentWindows = quota.windows.filter((window) => window.usedPercent !== null || window.remainingPercent !== null);
|
|
855
|
-
return createElement('div', { className: 'codingns-magpie-quota-account-block' }, showHeading && createElement('div', { className: 'codingns-magpie-quota-account-head' }, createElement('strong', undefined, quota.alias ?? quota.name), quota.user !== null && createElement('span', undefined, t('magpie.account', { account: quota.user })), quota.plan !== null && createElement('small', undefined, quota.plan)), !showHeading && quota.user !== null && createElement('div', { className: 'codingns-magpie-quota-account' }, t('magpie.account', { account: quota.user })),
|
|
929
|
+
return createElement('div', { className: 'codingns-magpie-quota-account-block' }, showHeading && createElement('div', { className: 'codingns-magpie-quota-account-head' }, createElement('strong', undefined, quota.alias ?? quota.name), quota.user !== null && createElement('span', undefined, t('magpie.account', { account: quota.user })), quota.plan !== null && createElement('small', undefined, quota.plan)), !showHeading && quota.user !== null && createElement('div', { className: 'codingns-magpie-quota-account' }, t('magpie.account', { account: quota.user })), quota.provider.toLocaleLowerCase() === 'codex' && createElement(MagpieQuotaControls, {
|
|
930
|
+
quota, t, policyPending, policyFailed, onPolicyChange, onResetRequest,
|
|
931
|
+
}), balance !== null && createElement('div', { className: 'codingns-magpie-quota-balance' }, createElement('span', { className: 'codingns-magpie-quota-balance-label' }, t('magpie.balance')), createElement('strong', { className: balance.money ? 'codingns-magpie-quota-balance-value is-money' : 'codingns-magpie-quota-balance-value', title: balance.raw }, balance.text)), quota.windows.length === 0
|
|
856
932
|
? balance === null && createElement('div', { className: 'codingns-magpie-inline-empty' }, t('magpie.noLimit'))
|
|
857
933
|
: percentWindows.length > 0 && percentWindows.map((window) => {
|
|
858
934
|
const used = window.usedPercent ?? (window.remainingPercent === null ? null : 100 - window.remainingPercent);
|
|
@@ -870,6 +946,57 @@ function QuotaAccountSection({ quota, quotaView = DEFAULT_SUBSCRIPTION_REPORT_SE
|
|
|
870
946
|
// 有余额但没有百分比的账号,把重置时间单独留在余额下面。
|
|
871
947
|
balance !== null && percentWindows.length === 0 && quota.windows.some((window) => window.resetsAt !== null) && createElement('div', { className: 'codingns-magpie-quota-foot' }, ...quota.windows.filter((window) => window.resetsAt !== null).map((window) => createElement('span', { key: window.name }, t('magpie.resets', { time: formatTimestamp(window.resetsAt) })))), quota.daily.days.length > 1 && createElement('div', { className: 'codingns-magpie-daily-chart' }, createElement(Sparkline, { values: dailyValues }), createElement('small', undefined, t('magpie.dailyUsage'))));
|
|
872
948
|
}
|
|
949
|
+
function MagpieQuotaControls({ quota, t, policyPending, policyFailed, onPolicyChange, onResetRequest }) {
|
|
950
|
+
const user = quota.user;
|
|
951
|
+
const resetCount = quota.resets?.count;
|
|
952
|
+
const policyUnavailable = user === null || quota.policyStatus === 'unavailable'
|
|
953
|
+
|| quota.autoReset === undefined || quota.useCredits === undefined;
|
|
954
|
+
return createElement('div', { className: 'codingns-magpie-codex-controls' }, createElement('div', { className: 'codingns-magpie-codex-reset-count' }, createElement('span', undefined, t('usage.magpieResetCountLabel')), createElement('strong', undefined, resetCount === null || resetCount === undefined ? '—' : t('usage.magpieResetCount', { count: resetCount }))), policyUnavailable
|
|
955
|
+
? createElement('div', { className: 'codingns-magpie-codex-unavailable', role: 'status' }, t('magpie.codexPolicyUnavailable'))
|
|
956
|
+
: quota.autoReset !== undefined && createElement(MagpieQuotaPolicySwitch, {
|
|
957
|
+
label: t('usage.magpieResetWhenWeek'), checked: quota.autoReset.week,
|
|
958
|
+
pending: policyPending === `${user}:week`, disabled: policyPending !== null,
|
|
959
|
+
onChange: (enabled) => onPolicyChange(user, 'week', enabled),
|
|
960
|
+
}), !policyUnavailable && quota.autoReset !== undefined && createElement(MagpieQuotaPolicySwitch, {
|
|
961
|
+
label: t('usage.magpieResetBeforeExpiry'), checked: quota.autoReset.expiring,
|
|
962
|
+
pending: policyPending === `${user}:expiring`, disabled: policyPending !== null,
|
|
963
|
+
onChange: (enabled) => onPolicyChange(user, 'expiring', enabled),
|
|
964
|
+
}), !policyUnavailable && quota.useCredits !== undefined && createElement(MagpieQuotaPolicySwitch, {
|
|
965
|
+
label: t('usage.magpieUseCredits'), checked: quota.useCredits,
|
|
966
|
+
pending: policyPending === `${user}:credits`, disabled: policyPending !== null,
|
|
967
|
+
onChange: (enabled) => onPolicyChange(user, 'credits', enabled),
|
|
968
|
+
}), policyFailed && createElement('div', { className: 'codingns-magpie-codex-error', role: 'alert' }, t('magpie.codexPolicyFailed')), user !== null && resetCount !== null && resetCount !== undefined && createElement('button', {
|
|
969
|
+
type: 'button',
|
|
970
|
+
className: 'codingns-magpie-codex-reset-button',
|
|
971
|
+
disabled: resetCount <= 0,
|
|
972
|
+
onClick: () => onResetRequest(quota),
|
|
973
|
+
}, t('usage.magpieUseReset')));
|
|
974
|
+
}
|
|
975
|
+
function MagpieQuotaPolicySwitch({ label, checked, pending, disabled, onChange }) {
|
|
976
|
+
return createElement('button', {
|
|
977
|
+
type: 'button', role: 'switch', 'aria-checked': checked, disabled,
|
|
978
|
+
'aria-busy': pending,
|
|
979
|
+
className: 'codingns-magpie-codex-policy',
|
|
980
|
+
onClick: () => onChange(!checked),
|
|
981
|
+
}, createElement('span', undefined, label), createElement('span', { className: `codingns-magpie-codex-switch${checked ? ' is-on' : ''}` }, createElement('span')));
|
|
982
|
+
}
|
|
983
|
+
function MagpieQuotaResetDialog({ target, pending, result, failed, t, onCancel, onConfirm, onClose }) {
|
|
984
|
+
const finished = result !== null || failed;
|
|
985
|
+
const outcomeKeys = {
|
|
986
|
+
reset: 'usage.resetOutcomeReset',
|
|
987
|
+
alreadyRedeemed: 'usage.resetOutcomeAlreadyRedeemed',
|
|
988
|
+
nothingToReset: 'usage.resetOutcomeNothingToReset',
|
|
989
|
+
noCredit: 'usage.resetOutcomeNoCredit',
|
|
990
|
+
};
|
|
991
|
+
const outcomeMessage = result === null ? null : t(outcomeKeys[result]);
|
|
992
|
+
return createElement('div', {
|
|
993
|
+
className: 'codingns-magpie-codex-reset-overlay', role: 'presentation',
|
|
994
|
+
onMouseDown: (event) => { if (event.target === event.currentTarget && !pending)
|
|
995
|
+
onCancel(); },
|
|
996
|
+
}, createElement('div', { className: 'codingns-magpie-codex-reset-dialog', role: 'dialog', 'aria-modal': true, 'aria-label': t('usage.resetDialogTitle') }, createElement('strong', undefined, t('usage.resetDialogTitle')), createElement('span', undefined, t('magpie.resetDialogAccount', { account: target.account })), createElement('span', { className: failed ? 'is-error' : result === 'reset' || result === 'alreadyRedeemed' ? 'is-success' : '' }, pending ? t('usage.resetDialogPending') : failed ? t('magpie.codexResetFailed') : outcomeMessage ?? t('magpie.resetDialogBody', { count: target.count })), createElement('div', { className: 'codingns-magpie-codex-reset-actions' }, finished
|
|
997
|
+
? createElement('button', { type: 'button', onClick: onClose }, t('usage.resetDialogClose'))
|
|
998
|
+
: createElement('button', { type: 'button', disabled: pending, onClick: onCancel }, t('usage.resetDialogCancel')), !finished && createElement('button', { type: 'button', disabled: pending, onClick: onConfirm }, t('usage.resetDialogConfirm')))));
|
|
999
|
+
}
|
|
873
1000
|
function QuotaHistoryCard({ history }) {
|
|
874
1001
|
return createElement('div', { className: 'codingns-magpie-history-card' }, createElement('div', { className: 'codingns-magpie-provider-inline' }, createElement(MagpieProviderLogo, { identities: [history.provider], size: 22, className: 'codingns-magpie-provider-logo codingns-magpie-provider-logo-compact', fallback: 'none' }), createElement('strong', undefined, history.provider)), history.user !== null && createElement('small', undefined, history.user), ...history.lines.map((line) => createElement('div', { key: line.name, className: 'codingns-magpie-history-line' }, createElement('div', { className: 'codingns-magpie-history-line-head' }, createElement('span', undefined, line.name), createElement('span', undefined, line.points.at(-1)?.left === null || line.points.at(-1)?.left === undefined ? '—' : formatValue(line.points.at(-1).left))), createElement(Sparkline, { values: line.points.map((point) => point.left).filter((value) => value !== null) }))));
|
|
875
1002
|
}
|
|
@@ -1137,6 +1264,13 @@ const MAGPIE_PAGE_CSS = `
|
|
|
1137
1264
|
.codingns-magpie-quota-balance-label{flex:0 0 auto;color:var(--mp-muted);font-size:${uiFontSize(13)}}
|
|
1138
1265
|
.codingns-magpie-quota-balance-value{min-width:0;overflow:hidden;color:var(--mp-ink);font-size:${uiFontSize(15)};font-weight:600;font-variant-numeric:tabular-nums;text-overflow:ellipsis;white-space:nowrap}
|
|
1139
1266
|
.codingns-magpie-quota-balance-value.is-money{font-size:${uiFontSize(17)};letter-spacing:-.01em}
|
|
1267
|
+
.codingns-magpie-codex-controls{display:grid;gap:2px;margin:9px 0 10px;padding:8px 10px;border-top:.5px solid var(--mp-line);border-bottom:.5px solid var(--mp-line);background:color-mix(in srgb,var(--mp-layer) 45%,transparent)}
|
|
1268
|
+
.codingns-magpie-codex-reset-count{display:flex;align-items:center;justify-content:space-between;gap:8px;min-width:0;padding:2px 0 5px;color:var(--mp-muted);font-size:${uiFontSize(12)}}.codingns-magpie-codex-reset-count strong{color:var(--mp-ink);font-size:${uiFontSize(13)};font-variant-numeric:tabular-nums}
|
|
1269
|
+
.codingns-magpie-codex-policy{display:flex;align-items:center;justify-content:space-between;gap:12px;width:100%;min-width:0;min-height:32px;padding:4px 0;border:0;background:transparent;color:var(--mp-muted);font:inherit;font-size:${uiFontSize(12)};text-align:left;cursor:pointer}.codingns-magpie-codex-policy>span:first-child{min-width:0;line-height:1.4;overflow-wrap:anywhere}.codingns-magpie-codex-policy:disabled{opacity:.58;cursor:wait}.codingns-magpie-codex-policy:focus-visible,.codingns-magpie-codex-reset-button:focus-visible{outline:2px solid color-mix(in srgb,var(--mp-accent) 60%,transparent);outline-offset:2px}
|
|
1270
|
+
.codingns-magpie-codex-switch{display:grid;place-items:center;flex:0 0 34px;width:34px;height:20px;padding:2px;border-radius:999px;background:var(--mp-line-strong);transition:background .15s}.codingns-magpie-codex-switch>span{justify-self:start;width:16px;height:16px;border-radius:50%;background:var(--mp-surface);box-shadow:0 1px 2px rgba(0,0,0,.18);transition:transform .15s}.codingns-magpie-codex-switch.is-on{background:var(--mp-accent)}.codingns-magpie-codex-switch.is-on>span{transform:translateX(14px)}
|
|
1271
|
+
.codingns-magpie-codex-unavailable,.codingns-magpie-codex-error{padding:5px 0;color:var(--mp-caption);font-size:${uiFontSize(12)}}.codingns-magpie-codex-error{color:var(--dsw-alias-state-error-primary,#c54b4b)}
|
|
1272
|
+
.codingns-magpie-codex-reset-button{justify-self:start;min-height:27px;margin-top:4px;padding:0 9px;border:.5px solid var(--mp-line-strong);border-radius:var(--dsw-radius-sm,6px);background:transparent;color:var(--mp-ink);font:inherit;font-size:${uiFontSize(12)};cursor:pointer}.codingns-magpie-codex-reset-button:hover:not(:disabled){border-color:var(--mp-accent);color:var(--mp-accent)}.codingns-magpie-codex-reset-button:disabled{opacity:.45;cursor:not-allowed}
|
|
1273
|
+
.codingns-magpie-codex-reset-overlay{position:absolute;inset:0;z-index:30;display:flex;align-items:center;justify-content:center;overflow:auto;padding:20px;background:color-mix(in srgb,var(--mp-surface) 70%,rgba(0,0,0,.3));backdrop-filter:blur(2px)}.codingns-magpie-codex-reset-dialog{display:grid;gap:10px;width:min(420px,100%);padding:16px;border:.5px solid var(--mp-line-strong);border-radius:var(--mp-radius);background:var(--mp-surface);box-shadow:var(--dsw-elevation-prominent,0 16px 44px rgba(0,0,0,.2));font-size:${uiFontSize(13)};line-height:1.5}.codingns-magpie-codex-reset-dialog>strong{font-size:${uiFontSize(14)}}.codingns-magpie-codex-reset-dialog>span{color:var(--mp-muted);overflow-wrap:anywhere}.codingns-magpie-codex-reset-dialog>span.is-error{color:var(--dsw-alias-state-error-primary,#c54b4b)}.codingns-magpie-codex-reset-dialog>span.is-success{color:var(--dsw-alias-state-success-primary,#3f9d6b)}.codingns-magpie-codex-reset-actions{display:flex;justify-content:flex-end;gap:8px;padding-top:3px}.codingns-magpie-codex-reset-actions button{min-height:30px;padding:0 11px;border:.5px solid var(--mp-line-strong);border-radius:var(--dsw-radius-sm,6px);background:transparent;color:var(--mp-ink);font:inherit;font-size:${uiFontSize(12)};cursor:pointer}.codingns-magpie-codex-reset-actions button:last-child{border-color:var(--mp-accent);background:var(--mp-accent);color:var(--dsw-alias-label-primary-foreground,#fff)}.codingns-magpie-codex-reset-actions button:disabled{opacity:.5;cursor:wait}
|
|
1140
1274
|
.codingns-magpie-quota-window{padding:11px 0;border-top:.5px solid var(--mp-line)}.codingns-magpie-quota-window-head,.codingns-magpie-quota-foot,.codingns-magpie-history-line-head{display:flex;align-items:center;justify-content:space-between;gap:9px}.codingns-magpie-quota-window-head{font-size:${uiFontSize(13)};font-weight:500}.codingns-magpie-quota-window-head span{color:var(--mp-muted);font-variant-numeric:tabular-nums}.quota-track{height:6px}.quota-track span{background:linear-gradient(90deg,var(--mp-accent),color-mix(in srgb,var(--mp-accent) 55%,transparent))}.codingns-magpie-quota-foot{color:var(--mp-caption);font-size:${uiFontSize(12)}}
|
|
1141
1275
|
.codingns-magpie-daily-chart{display:grid;grid-template-columns:1fr auto;align-items:center;gap:9px;margin-top:4px;padding-top:10px;border-top:.5px solid var(--mp-line);color:var(--mp-muted);font-size:${uiFontSize(12)}}.codingns-magpie-sparkline{width:100%;height:30px;overflow:visible}.codingns-magpie-sparkline polyline{stroke:var(--mp-accent);stroke-width:2;vector-effect:non-scaling-stroke}
|
|
1142
1276
|
.codingns-magpie-history-panel{padding:17px;margin-top:14px}.codingns-magpie-history-grid{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:9px}.codingns-magpie-history-card{padding:12px;border:1px solid var(--mp-line);border-radius:9px;background:var(--mp-card)}.codingns-magpie-history-card>strong,.codingns-magpie-history-card>small{display:block}.codingns-magpie-history-card>strong{font-size:${uiFontSize(13)};font-weight:600}.codingns-magpie-history-card>small{margin-top:3px;color:var(--mp-caption);font-size:${uiFontSize(12)}}.codingns-magpie-history-line{margin-top:10px}.codingns-magpie-history-line-head{font-size:${uiFontSize(12)}}.codingns-magpie-history-line-head span:last-child{font-variant-numeric:tabular-nums;font-weight:650}
|