@jingyi0605/codingns4dsh 0.2.0-beta.2 → 0.2.0-rc.3
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 +4 -4
- package/README.md +18 -7
- package/assets/provider-icons/antigravity.svg +39 -0
- package/assets/provider-icons/codebuddy.svg +37 -0
- package/assets/provider-icons/cursor-cli.svg +1 -0
- package/assets/provider-icons/kiro-cli.svg +11 -0
- package/assets/provider-icons/minimax-code.svg +4 -0
- package/assets/provider-icons/qoder-cn.svg +5 -0
- package/assets/provider-icons/qoder.svg +5 -0
- package/assets/provider-icons/workbuddy.svg +29 -0
- package/assets/provider-icons/zcode.svg +14 -0
- package/data/build/dist/bootstrap/dsh-peer-host-preboot-shim.d.ts.map +1 -1
- package/data/build/dist/bootstrap/dsh-peer-host-preboot-shim.js +78 -1
- package/data/build/dist/bootstrap/dsh-peer-host-preboot-shim.js.map +1 -1
- package/data/build/dist/client/account-bar.d.ts +2 -1
- package/data/build/dist/client/account-bar.d.ts.map +1 -1
- package/data/build/dist/client/account-bar.js +21 -16
- package/data/build/dist/client/account-bar.js.map +1 -1
- package/data/build/dist/client/bundle.js +8147 -2158
- package/data/build/dist/client/bundle.js.map +1 -1
- package/data/build/dist/client/cli-catalog.d.ts +1 -1
- package/data/build/dist/client/cli-catalog.d.ts.map +1 -1
- package/data/build/dist/client/cli-catalog.js +11 -5
- package/data/build/dist/client/cli-catalog.js.map +1 -1
- package/data/build/dist/client/cli-slots.d.ts.map +1 -1
- package/data/build/dist/client/cli-slots.js +127 -21
- package/data/build/dist/client/cli-slots.js.map +1 -1
- package/data/build/dist/client/debug/ui.d.ts +2 -1
- package/data/build/dist/client/debug/ui.d.ts.map +1 -1
- package/data/build/dist/client/debug/ui.js +41 -34
- package/data/build/dist/client/debug/ui.js.map +1 -1
- package/data/build/dist/client/delegate-command.d.ts +17 -0
- package/data/build/dist/client/delegate-command.d.ts.map +1 -0
- package/data/build/dist/client/delegate-command.js +597 -0
- package/data/build/dist/client/delegate-command.js.map +1 -0
- package/data/build/dist/client/delegate-plan.d.ts +40 -0
- package/data/build/dist/client/delegate-plan.d.ts.map +1 -0
- package/data/build/dist/client/delegate-plan.js +63 -0
- package/data/build/dist/client/delegate-plan.js.map +1 -0
- package/data/build/dist/client/delegate-ui-dom.d.ts +86 -0
- package/data/build/dist/client/delegate-ui-dom.d.ts.map +1 -0
- package/data/build/dist/client/delegate-ui-dom.js +647 -0
- package/data/build/dist/client/delegate-ui-dom.js.map +1 -0
- package/data/build/dist/client/external-tool-stream.d.ts.map +1 -1
- package/data/build/dist/client/external-tool-stream.js +44 -36
- package/data/build/dist/client/external-tool-stream.js.map +1 -1
- package/data/build/dist/client/features/cli-adapters.d.ts +7 -2
- package/data/build/dist/client/features/cli-adapters.d.ts.map +1 -1
- package/data/build/dist/client/features/cli-adapters.js +153 -95
- package/data/build/dist/client/features/cli-adapters.js.map +1 -1
- package/data/build/dist/client/features/debug.d.ts.map +1 -1
- package/data/build/dist/client/features/debug.js +5 -3
- package/data/build/dist/client/features/debug.js.map +1 -1
- package/data/build/dist/client/features/file-management.d.ts.map +1 -1
- package/data/build/dist/client/features/file-management.js +7 -4
- package/data/build/dist/client/features/file-management.js.map +1 -1
- package/data/build/dist/client/features/lan-access-panel.js +10 -10
- package/data/build/dist/client/features/lan-access-panel.js.map +1 -1
- package/data/build/dist/client/features/lan-access.d.ts.map +1 -1
- package/data/build/dist/client/features/lan-access.js +8 -3
- package/data/build/dist/client/features/lan-access.js.map +1 -1
- package/data/build/dist/client/features/login-protection-panel.d.ts.map +1 -1
- package/data/build/dist/client/features/login-protection-panel.js +9 -7
- package/data/build/dist/client/features/login-protection-panel.js.map +1 -1
- package/data/build/dist/client/features/login-protection.js +2 -2
- package/data/build/dist/client/features/login-protection.js.map +1 -1
- package/data/build/dist/client/features/mobile-access-panel.d.ts.map +1 -1
- package/data/build/dist/client/features/mobile-access-panel.js +8 -7
- package/data/build/dist/client/features/mobile-access-panel.js.map +1 -1
- package/data/build/dist/client/features/mobile-access.d.ts.map +1 -1
- package/data/build/dist/client/features/mobile-access.js +6 -2
- package/data/build/dist/client/features/mobile-access.js.map +1 -1
- package/data/build/dist/client/features/peer-host.d.ts +6 -4
- package/data/build/dist/client/features/peer-host.d.ts.map +1 -1
- package/data/build/dist/client/features/peer-host.js +459 -27
- package/data/build/dist/client/features/peer-host.js.map +1 -1
- package/data/build/dist/client/features/reverse-proxy.js +2 -2
- package/data/build/dist/client/features/reverse-proxy.js.map +1 -1
- package/data/build/dist/client/features/terminal-enhancement.js +2 -2
- package/data/build/dist/client/features/terminal-enhancement.js.map +1 -1
- package/data/build/dist/client/features/workspace-session-enhancement-panel.js +1 -1
- package/data/build/dist/client/features/workspace-session-enhancement-panel.js.map +1 -1
- package/data/build/dist/client/features/workspace-session-enhancement.d.ts.map +1 -1
- package/data/build/dist/client/features/workspace-session-enhancement.js +8 -3
- package/data/build/dist/client/features/workspace-session-enhancement.js.map +1 -1
- package/data/build/dist/client/file-management-dom.d.ts +3 -0
- package/data/build/dist/client/file-management-dom.d.ts.map +1 -1
- package/data/build/dist/client/file-management-dom.js +41 -30
- package/data/build/dist/client/file-management-dom.js.map +1 -1
- package/data/build/dist/client/git-history-graph.d.ts +2 -2
- package/data/build/dist/client/git-history-graph.d.ts.map +1 -1
- package/data/build/dist/client/git-history-graph.js +2 -2
- package/data/build/dist/client/git-history-graph.js.map +1 -1
- package/data/build/dist/client/git-management.d.ts +2 -0
- package/data/build/dist/client/git-management.d.ts.map +1 -1
- package/data/build/dist/client/git-management.js +103 -75
- package/data/build/dist/client/git-management.js.map +1 -1
- package/data/build/dist/client/git-workspace-events.d.ts +7 -0
- package/data/build/dist/client/git-workspace-events.d.ts.map +1 -0
- package/data/build/dist/client/git-workspace-events.js +32 -0
- package/data/build/dist/client/git-workspace-events.js.map +1 -0
- package/data/build/dist/client/index.d.ts +2 -0
- package/data/build/dist/client/index.d.ts.map +1 -1
- package/data/build/dist/client/index.js +6 -5
- package/data/build/dist/client/index.js.map +1 -1
- package/data/build/dist/client/locale.d.ts +7 -0
- package/data/build/dist/client/locale.d.ts.map +1 -1
- package/data/build/dist/client/locale.js +140 -42
- package/data/build/dist/client/locale.js.map +1 -1
- package/data/build/dist/client/locales/debug.d.ts +9 -0
- package/data/build/dist/client/locales/debug.d.ts.map +1 -0
- package/data/build/dist/client/locales/debug.js +163 -0
- package/data/build/dist/client/locales/debug.js.map +1 -0
- package/data/build/dist/client/locales/fileWorkspace.d.ts +9 -0
- package/data/build/dist/client/locales/fileWorkspace.d.ts.map +1 -0
- package/data/build/dist/client/locales/fileWorkspace.js +139 -0
- package/data/build/dist/client/locales/fileWorkspace.js.map +1 -0
- package/data/build/dist/client/locales/git.d.ts +9 -0
- package/data/build/dist/client/locales/git.d.ts.map +1 -0
- package/data/build/dist/client/locales/git.js +223 -0
- package/data/build/dist/client/locales/git.js.map +1 -0
- package/data/build/dist/client/locales/panels.d.ts +9 -0
- package/data/build/dist/client/locales/panels.d.ts.map +1 -0
- package/data/build/dist/client/locales/panels.js +33 -0
- package/data/build/dist/client/locales/panels.js.map +1 -0
- package/data/build/dist/client/locales/peerHost.d.ts +9 -0
- package/data/build/dist/client/locales/peerHost.d.ts.map +1 -0
- package/data/build/dist/client/locales/peerHost.js +153 -0
- package/data/build/dist/client/locales/peerHost.js.map +1 -0
- package/data/build/dist/client/locales/peerHostWorkspace.d.ts +9 -0
- package/data/build/dist/client/locales/peerHostWorkspace.d.ts.map +1 -0
- package/data/build/dist/client/locales/peerHostWorkspace.js +69 -0
- package/data/build/dist/client/locales/peerHostWorkspace.js.map +1 -0
- package/data/build/dist/client/locales/terminalAuth.d.ts +9 -0
- package/data/build/dist/client/locales/terminalAuth.d.ts.map +1 -0
- package/data/build/dist/client/locales/terminalAuth.js +71 -0
- package/data/build/dist/client/locales/terminalAuth.js.map +1 -0
- package/data/build/dist/client/locales/usage.d.ts +9 -0
- package/data/build/dist/client/locales/usage.d.ts.map +1 -0
- package/data/build/dist/client/locales/usage.js +215 -0
- package/data/build/dist/client/locales/usage.js.map +1 -0
- package/data/build/dist/client/mobile-session-interaction.d.ts +44 -0
- package/data/build/dist/client/mobile-session-interaction.d.ts.map +1 -0
- package/data/build/dist/client/mobile-session-interaction.js +308 -0
- package/data/build/dist/client/mobile-session-interaction.js.map +1 -0
- package/data/build/dist/client/mobile-sidebar-gestures.d.ts +55 -7
- package/data/build/dist/client/mobile-sidebar-gestures.d.ts.map +1 -1
- package/data/build/dist/client/mobile-sidebar-gestures.js +339 -40
- package/data/build/dist/client/mobile-sidebar-gestures.js.map +1 -1
- package/data/build/dist/client/mobile-sidebar-rail-dom.d.ts +10 -2
- package/data/build/dist/client/mobile-sidebar-rail-dom.d.ts.map +1 -1
- package/data/build/dist/client/mobile-sidebar-rail-dom.js +14 -6
- package/data/build/dist/client/mobile-sidebar-rail-dom.js.map +1 -1
- package/data/build/dist/client/model-catalog-cache.d.ts +5 -0
- package/data/build/dist/client/model-catalog-cache.d.ts.map +1 -0
- package/data/build/dist/client/model-catalog-cache.js +58 -0
- package/data/build/dist/client/model-catalog-cache.js.map +1 -0
- package/data/build/dist/client/peer-host-aggregate-refresh.d.ts +7 -0
- package/data/build/dist/client/peer-host-aggregate-refresh.d.ts.map +1 -1
- package/data/build/dist/client/peer-host-aggregate-refresh.js +13 -1
- package/data/build/dist/client/peer-host-aggregate-refresh.js.map +1 -1
- package/data/build/dist/client/peer-host-connection-button.d.ts +14 -1
- package/data/build/dist/client/peer-host-connection-button.d.ts.map +1 -1
- package/data/build/dist/client/peer-host-connection-button.js +12 -4
- package/data/build/dist/client/peer-host-connection-button.js.map +1 -1
- package/data/build/dist/client/peer-host-management-panel.d.ts +3 -0
- package/data/build/dist/client/peer-host-management-panel.d.ts.map +1 -1
- package/data/build/dist/client/peer-host-management-panel.js +83 -79
- package/data/build/dist/client/peer-host-management-panel.js.map +1 -1
- package/data/build/dist/client/peer-host-native-projection.d.ts +17 -1
- package/data/build/dist/client/peer-host-native-projection.d.ts.map +1 -1
- package/data/build/dist/client/peer-host-native-projection.js +54 -8
- package/data/build/dist/client/peer-host-native-projection.js.map +1 -1
- package/data/build/dist/client/peer-host-native-store-projection.d.ts +6 -2
- package/data/build/dist/client/peer-host-native-store-projection.d.ts.map +1 -1
- package/data/build/dist/client/peer-host-native-store-projection.js +308 -10
- package/data/build/dist/client/peer-host-native-store-projection.js.map +1 -1
- package/data/build/dist/client/peer-host-scoped-client.js +5 -5
- package/data/build/dist/client/peer-host-scoped-client.js.map +1 -1
- package/data/build/dist/client/peer-host-workspace-tab.d.ts +8 -0
- package/data/build/dist/client/peer-host-workspace-tab.d.ts.map +1 -1
- package/data/build/dist/client/peer-host-workspace-tab.js +48 -28
- package/data/build/dist/client/peer-host-workspace-tab.js.map +1 -1
- package/data/build/dist/client/provider-icon-assets.js +18 -0
- package/data/build/dist/client/provider-icon-assets.js.map +1 -1
- package/data/build/dist/client/provider-icons.d.ts +8 -2
- package/data/build/dist/client/provider-icons.d.ts.map +1 -1
- package/data/build/dist/client/provider-icons.js +28 -7
- package/data/build/dist/client/provider-icons.js.map +1 -1
- package/data/build/dist/client/pwa-install-prompt.d.ts +4 -1
- package/data/build/dist/client/pwa-install-prompt.d.ts.map +1 -1
- package/data/build/dist/client/pwa-install-prompt.js +8 -7
- package/data/build/dist/client/pwa-install-prompt.js.map +1 -1
- package/data/build/dist/client/quick-phrase-layout.d.ts +11 -0
- package/data/build/dist/client/quick-phrase-layout.d.ts.map +1 -1
- package/data/build/dist/client/quick-phrase-layout.js +20 -0
- package/data/build/dist/client/quick-phrase-layout.js.map +1 -1
- package/data/build/dist/client/quick-phrase-slot.d.ts.map +1 -1
- package/data/build/dist/client/quick-phrase-slot.js +20 -8
- package/data/build/dist/client/quick-phrase-slot.js.map +1 -1
- package/data/build/dist/client/remote-web-context.js +10 -6
- package/data/build/dist/client/remote-web-context.js.map +1 -1
- package/data/build/dist/client/service-tier.d.ts +54 -0
- package/data/build/dist/client/service-tier.d.ts.map +1 -0
- package/data/build/dist/client/service-tier.js +78 -0
- package/data/build/dist/client/service-tier.js.map +1 -0
- package/data/build/dist/client/session-changed-files-view.d.ts +8 -1
- package/data/build/dist/client/session-changed-files-view.d.ts.map +1 -1
- package/data/build/dist/client/session-changed-files-view.js +71 -28
- package/data/build/dist/client/session-changed-files-view.js.map +1 -1
- package/data/build/dist/client/settings-anchor.d.ts +9 -3
- package/data/build/dist/client/settings-anchor.d.ts.map +1 -1
- package/data/build/dist/client/settings-anchor.js +8 -2
- package/data/build/dist/client/settings-anchor.js.map +1 -1
- package/data/build/dist/client/settings-promo-styles.d.ts +28 -0
- package/data/build/dist/client/settings-promo-styles.d.ts.map +1 -0
- package/data/build/dist/client/settings-promo-styles.js +58 -0
- package/data/build/dist/client/settings-promo-styles.js.map +1 -0
- package/data/build/dist/client/settings-promo.d.ts +14 -0
- package/data/build/dist/client/settings-promo.d.ts.map +1 -0
- package/data/build/dist/client/settings-promo.js +68 -0
- package/data/build/dist/client/settings-promo.js.map +1 -0
- package/data/build/dist/client/settings-section.d.ts +2 -1
- package/data/build/dist/client/settings-section.d.ts.map +1 -1
- package/data/build/dist/client/settings-section.js +10 -7
- package/data/build/dist/client/settings-section.js.map +1 -1
- package/data/build/dist/client/subscription-slot.d.ts +4 -1
- package/data/build/dist/client/subscription-slot.d.ts.map +1 -1
- package/data/build/dist/client/subscription-slot.js +497 -56
- package/data/build/dist/client/subscription-slot.js.map +1 -1
- package/data/build/dist/client/terminal/model.d.ts +94 -4
- package/data/build/dist/client/terminal/model.d.ts.map +1 -1
- package/data/build/dist/client/terminal/model.js +392 -33
- package/data/build/dist/client/terminal/model.js.map +1 -1
- package/data/build/dist/client/terminal/recovery.d.ts +16 -1
- package/data/build/dist/client/terminal/recovery.d.ts.map +1 -1
- package/data/build/dist/client/terminal/recovery.js +101 -39
- package/data/build/dist/client/terminal/recovery.js.map +1 -1
- package/data/build/dist/client/terminal/styles.d.ts +10 -0
- package/data/build/dist/client/terminal/styles.d.ts.map +1 -1
- package/data/build/dist/client/terminal/styles.js +27 -3
- package/data/build/dist/client/terminal/styles.js.map +1 -1
- package/data/build/dist/client/terminal/ui.d.ts +3 -2
- package/data/build/dist/client/terminal/ui.d.ts.map +1 -1
- package/data/build/dist/client/terminal/ui.js +216 -103
- package/data/build/dist/client/terminal/ui.js.map +1 -1
- package/data/build/dist/client/terminal/xterm-view.d.ts +8 -1
- package/data/build/dist/client/terminal/xterm-view.d.ts.map +1 -1
- package/data/build/dist/client/terminal/xterm-view.js +394 -34
- package/data/build/dist/client/terminal/xterm-view.js.map +1 -1
- package/data/build/dist/client/workspace-session-archive-dom.d.ts +3 -0
- package/data/build/dist/client/workspace-session-archive-dom.d.ts.map +1 -1
- package/data/build/dist/client/workspace-session-archive-dom.js +131 -45
- package/data/build/dist/client/workspace-session-archive-dom.js.map +1 -1
- package/data/build/dist/client/workspace-session-logo-dom.d.ts +3 -0
- package/data/build/dist/client/workspace-session-logo-dom.d.ts.map +1 -1
- package/data/build/dist/client/workspace-session-logo-dom.js +3 -1
- package/data/build/dist/client/workspace-session-logo-dom.js.map +1 -1
- package/data/build/dist/client/workspace-session-visibility-dom.d.ts +3 -0
- package/data/build/dist/client/workspace-session-visibility-dom.d.ts.map +1 -1
- package/data/build/dist/client/workspace-session-visibility-dom.js +46 -17
- package/data/build/dist/client/workspace-session-visibility-dom.js.map +1 -1
- package/data/build/dist/dsh-capabilities/client/primitives-adapter.d.ts +10 -0
- package/data/build/dist/dsh-capabilities/client/primitives-adapter.d.ts.map +1 -1
- package/data/build/dist/dsh-capabilities/client/primitives-adapter.js +20 -0
- package/data/build/dist/dsh-capabilities/client/primitives-adapter.js.map +1 -1
- package/data/build/dist/host/browser-text.d.ts +30 -0
- package/data/build/dist/host/browser-text.d.ts.map +1 -0
- package/data/build/dist/host/browser-text.js +105 -0
- package/data/build/dist/host/browser-text.js.map +1 -0
- package/data/build/dist/host/cli-adapters/acp-cli-driver.d.ts +58 -0
- package/data/build/dist/host/cli-adapters/acp-cli-driver.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/acp-cli-driver.js +271 -0
- package/data/build/dist/host/cli-adapters/acp-cli-driver.js.map +1 -0
- package/data/build/dist/host/cli-adapters/antigravity-driver.d.ts +30 -0
- package/data/build/dist/host/cli-adapters/antigravity-driver.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/antigravity-driver.js +210 -0
- package/data/build/dist/host/cli-adapters/antigravity-driver.js.map +1 -0
- package/data/build/dist/host/cli-adapters/claude-driver.d.ts +28 -2
- package/data/build/dist/host/cli-adapters/claude-driver.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/claude-driver.js +74 -4
- package/data/build/dist/host/cli-adapters/claude-driver.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 +22 -9
- package/data/build/dist/host/cli-adapters/claude-model-options.js.map +1 -1
- package/data/build/dist/host/cli-adapters/codebuddy-driver.d.ts +139 -0
- package/data/build/dist/host/cli-adapters/codebuddy-driver.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/codebuddy-driver.js +1721 -0
- package/data/build/dist/host/cli-adapters/codebuddy-driver.js.map +1 -0
- package/data/build/dist/host/cli-adapters/codebuddy-subscription.d.ts +53 -0
- package/data/build/dist/host/cli-adapters/codebuddy-subscription.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/codebuddy-subscription.js +778 -0
- package/data/build/dist/host/cli-adapters/codebuddy-subscription.js.map +1 -0
- package/data/build/dist/host/cli-adapters/codex-driver.d.ts +22 -0
- package/data/build/dist/host/cli-adapters/codex-driver.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/codex-driver.js +254 -7
- package/data/build/dist/host/cli-adapters/codex-driver.js.map +1 -1
- package/data/build/dist/host/cli-adapters/command-code-driver.d.ts +43 -3
- package/data/build/dist/host/cli-adapters/command-code-driver.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/command-code-driver.js +681 -74
- package/data/build/dist/host/cli-adapters/command-code-driver.js.map +1 -1
- package/data/build/dist/host/cli-adapters/command-code-history.d.ts +147 -0
- package/data/build/dist/host/cli-adapters/command-code-history.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/command-code-history.js +659 -0
- package/data/build/dist/host/cli-adapters/command-code-history.js.map +1 -0
- package/data/build/dist/host/cli-adapters/cursor-driver.d.ts +12 -0
- package/data/build/dist/host/cli-adapters/cursor-driver.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/cursor-driver.js +20 -0
- package/data/build/dist/host/cli-adapters/cursor-driver.js.map +1 -0
- package/data/build/dist/host/cli-adapters/custom-upstream-classifier.d.ts +67 -0
- package/data/build/dist/host/cli-adapters/custom-upstream-classifier.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/custom-upstream-classifier.js +169 -0
- package/data/build/dist/host/cli-adapters/custom-upstream-classifier.js.map +1 -0
- package/data/build/dist/host/cli-adapters/delegate-dispatch.d.ts +48 -0
- package/data/build/dist/host/cli-adapters/delegate-dispatch.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/delegate-dispatch.js +111 -0
- package/data/build/dist/host/cli-adapters/delegate-dispatch.js.map +1 -0
- package/data/build/dist/host/cli-adapters/delegation-authorization.d.ts +19 -0
- package/data/build/dist/host/cli-adapters/delegation-authorization.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/delegation-authorization.js +49 -0
- package/data/build/dist/host/cli-adapters/delegation-authorization.js.map +1 -0
- package/data/build/dist/host/cli-adapters/delegation-mention-rewrite.d.ts +34 -0
- package/data/build/dist/host/cli-adapters/delegation-mention-rewrite.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/delegation-mention-rewrite.js +121 -0
- package/data/build/dist/host/cli-adapters/delegation-mention-rewrite.js.map +1 -0
- package/data/build/dist/host/cli-adapters/desktop-app-runtime.d.ts +32 -0
- package/data/build/dist/host/cli-adapters/desktop-app-runtime.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/desktop-app-runtime.js +121 -0
- package/data/build/dist/host/cli-adapters/desktop-app-runtime.js.map +1 -0
- package/data/build/dist/host/cli-adapters/driver.d.ts +6 -0
- package/data/build/dist/host/cli-adapters/driver.d.ts.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 +5 -4
- package/data/build/dist/host/cli-adapters/dsh-message-projector.js.map +1 -1
- package/data/build/dist/host/cli-adapters/dsh-virtual-providers.d.ts +16 -0
- package/data/build/dist/host/cli-adapters/dsh-virtual-providers.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/dsh-virtual-providers.js +73 -0
- package/data/build/dist/host/cli-adapters/dsh-virtual-providers.js.map +1 -0
- package/data/build/dist/host/cli-adapters/feature.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/feature.js +459 -26
- package/data/build/dist/host/cli-adapters/feature.js.map +1 -1
- package/data/build/dist/host/cli-adapters/gemini-driver.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/gemini-driver.js +21 -5
- package/data/build/dist/host/cli-adapters/gemini-driver.js.map +1 -1
- package/data/build/dist/host/cli-adapters/grok-driver.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/grok-driver.js +24 -7
- package/data/build/dist/host/cli-adapters/grok-driver.js.map +1 -1
- package/data/build/dist/host/cli-adapters/json-rpc-process.d.ts +22 -6
- package/data/build/dist/host/cli-adapters/json-rpc-process.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/json-rpc-process.js +118 -21
- package/data/build/dist/host/cli-adapters/json-rpc-process.js.map +1 -1
- package/data/build/dist/host/cli-adapters/kimi-driver.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/kimi-driver.js +25 -4
- package/data/build/dist/host/cli-adapters/kimi-driver.js.map +1 -1
- package/data/build/dist/host/cli-adapters/kiro-driver.d.ts +12 -0
- package/data/build/dist/host/cli-adapters/kiro-driver.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/kiro-driver.js +18 -0
- package/data/build/dist/host/cli-adapters/kiro-driver.js.map +1 -0
- package/data/build/dist/host/cli-adapters/legacy-session-adapter.d.ts +11 -2
- package/data/build/dist/host/cli-adapters/legacy-session-adapter.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/legacy-session-adapter.js +26 -6
- package/data/build/dist/host/cli-adapters/legacy-session-adapter.js.map +1 -1
- package/data/build/dist/host/cli-adapters/mcode-catalog.d.ts +23 -0
- package/data/build/dist/host/cli-adapters/mcode-catalog.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/mcode-catalog.js +120 -0
- package/data/build/dist/host/cli-adapters/mcode-catalog.js.map +1 -0
- package/data/build/dist/host/cli-adapters/mcode-driver.d.ts +56 -0
- package/data/build/dist/host/cli-adapters/mcode-driver.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/mcode-driver.js +544 -0
- package/data/build/dist/host/cli-adapters/mcode-driver.js.map +1 -0
- package/data/build/dist/host/cli-adapters/model-catalog.d.ts +35 -5
- package/data/build/dist/host/cli-adapters/model-catalog.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/model-catalog.js +213 -8
- package/data/build/dist/host/cli-adapters/model-catalog.js.map +1 -1
- package/data/build/dist/host/cli-adapters/native-subagent-dispatch.d.ts +81 -0
- package/data/build/dist/host/cli-adapters/native-subagent-dispatch.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/native-subagent-dispatch.js +299 -0
- package/data/build/dist/host/cli-adapters/native-subagent-dispatch.js.map +1 -0
- package/data/build/dist/host/cli-adapters/native-subagent-holder.d.ts +4 -0
- package/data/build/dist/host/cli-adapters/native-subagent-holder.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/native-subagent-holder.js +4 -0
- package/data/build/dist/host/cli-adapters/native-subagent-holder.js.map +1 -0
- package/data/build/dist/host/cli-adapters/native-team-proxy.js +18 -15
- package/data/build/dist/host/cli-adapters/native-team-proxy.js.map +1 -1
- package/data/build/dist/host/cli-adapters/native-team-subagent.d.ts +57 -0
- package/data/build/dist/host/cli-adapters/native-team-subagent.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/native-team-subagent.js +126 -0
- package/data/build/dist/host/cli-adapters/native-team-subagent.js.map +1 -0
- package/data/build/dist/host/cli-adapters/new-api-subscription.d.ts +75 -0
- package/data/build/dist/host/cli-adapters/new-api-subscription.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/new-api-subscription.js +959 -0
- package/data/build/dist/host/cli-adapters/new-api-subscription.js.map +1 -0
- package/data/build/dist/host/cli-adapters/opencode-driver.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/opencode-driver.js +22 -10
- package/data/build/dist/host/cli-adapters/opencode-driver.js.map +1 -1
- package/data/build/dist/host/cli-adapters/pi-driver.js +24 -7
- package/data/build/dist/host/cli-adapters/pi-driver.js.map +1 -1
- package/data/build/dist/host/cli-adapters/provider-subscription.d.ts +41 -4
- package/data/build/dist/host/cli-adapters/provider-subscription.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/provider-subscription.js +254 -40
- package/data/build/dist/host/cli-adapters/provider-subscription.js.map +1 -1
- package/data/build/dist/host/cli-adapters/qoder-driver.d.ts +71 -0
- package/data/build/dist/host/cli-adapters/qoder-driver.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/qoder-driver.js +553 -0
- package/data/build/dist/host/cli-adapters/qoder-driver.js.map +1 -0
- package/data/build/dist/host/cli-adapters/qoder-subscription.d.ts +31 -0
- package/data/build/dist/host/cli-adapters/qoder-subscription.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/qoder-subscription.js +178 -0
- package/data/build/dist/host/cli-adapters/qoder-subscription.js.map +1 -0
- package/data/build/dist/host/cli-adapters/registry-holder.d.ts +4 -0
- package/data/build/dist/host/cli-adapters/registry-holder.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/registry-holder.js +9 -0
- package/data/build/dist/host/cli-adapters/registry-holder.js.map +1 -0
- package/data/build/dist/host/cli-adapters/registry.d.ts +54 -2
- package/data/build/dist/host/cli-adapters/registry.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/registry.js +224 -18
- package/data/build/dist/host/cli-adapters/registry.js.map +1 -1
- package/data/build/dist/host/cli-adapters/session-store.d.ts +10 -1
- package/data/build/dist/host/cli-adapters/session-store.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/session-store.js +60 -6
- package/data/build/dist/host/cli-adapters/session-store.js.map +1 -1
- package/data/build/dist/host/cli-adapters/standard-stream-driver.d.ts +16 -1
- package/data/build/dist/host/cli-adapters/standard-stream-driver.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/standard-stream-driver.js +150 -26
- package/data/build/dist/host/cli-adapters/standard-stream-driver.js.map +1 -1
- package/data/build/dist/host/cli-adapters/stream-normalizer.d.ts +10 -1
- package/data/build/dist/host/cli-adapters/stream-normalizer.d.ts.map +1 -1
- package/data/build/dist/host/cli-adapters/stream-normalizer.js +23 -0
- package/data/build/dist/host/cli-adapters/stream-normalizer.js.map +1 -1
- package/data/build/dist/host/cli-adapters/subagent-tool.d.ts +5 -0
- package/data/build/dist/host/cli-adapters/subagent-tool.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/subagent-tool.js +112 -0
- package/data/build/dist/host/cli-adapters/subagent-tool.js.map +1 -0
- package/data/build/dist/host/cli-adapters/zcode-driver.d.ts +57 -0
- package/data/build/dist/host/cli-adapters/zcode-driver.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/zcode-driver.js +843 -0
- package/data/build/dist/host/cli-adapters/zcode-driver.js.map +1 -0
- package/data/build/dist/host/cli-adapters/zcode-subscription.d.ts +28 -0
- package/data/build/dist/host/cli-adapters/zcode-subscription.d.ts.map +1 -0
- package/data/build/dist/host/cli-adapters/zcode-subscription.js +212 -0
- package/data/build/dist/host/cli-adapters/zcode-subscription.js.map +1 -0
- package/data/build/dist/host/cli-bridge/bridge-holder.d.ts +27 -0
- package/data/build/dist/host/cli-bridge/bridge-holder.d.ts.map +1 -0
- package/data/build/dist/host/cli-bridge/bridge-holder.js +51 -0
- package/data/build/dist/host/cli-bridge/bridge-holder.js.map +1 -0
- package/data/build/dist/host/cli-bridge/bridge-server.d.ts +39 -0
- package/data/build/dist/host/cli-bridge/bridge-server.d.ts.map +1 -0
- package/data/build/dist/host/cli-bridge/bridge-server.js +140 -0
- package/data/build/dist/host/cli-bridge/bridge-server.js.map +1 -0
- package/data/build/dist/host/cli-bridge/command-code-mod.d.ts +29 -0
- package/data/build/dist/host/cli-bridge/command-code-mod.d.ts.map +1 -0
- package/data/build/dist/host/cli-bridge/command-code-mod.js +91 -0
- package/data/build/dist/host/cli-bridge/command-code-mod.js.map +1 -0
- package/data/build/dist/host/cli-bridge/dispatch.d.ts +19 -0
- package/data/build/dist/host/cli-bridge/dispatch.d.ts.map +1 -0
- package/data/build/dist/host/cli-bridge/dispatch.js +128 -0
- package/data/build/dist/host/cli-bridge/dispatch.js.map +1 -0
- package/data/build/dist/host/cli-bridge/injections.d.ts +28 -0
- package/data/build/dist/host/cli-bridge/injections.d.ts.map +1 -0
- package/data/build/dist/host/cli-bridge/injections.js +131 -0
- package/data/build/dist/host/cli-bridge/injections.js.map +1 -0
- package/data/build/dist/host/cli-bridge/mcp-stdio-entry.d.ts +8 -0
- package/data/build/dist/host/cli-bridge/mcp-stdio-entry.d.ts.map +1 -0
- package/data/build/dist/host/cli-bridge/mcp-stdio-entry.js +170 -0
- package/data/build/dist/host/cli-bridge/mcp-stdio-entry.js.map +1 -0
- package/data/build/dist/host/features/lan-access-dsh.d.ts.map +1 -1
- package/data/build/dist/host/features/lan-access-dsh.js +6 -2
- package/data/build/dist/host/features/lan-access-dsh.js.map +1 -1
- package/data/build/dist/host/features/peer-host.d.ts +21 -1
- package/data/build/dist/host/features/peer-host.d.ts.map +1 -1
- package/data/build/dist/host/features/peer-host.js +176 -31
- package/data/build/dist/host/features/peer-host.js.map +1 -1
- package/data/build/dist/host/features/types.d.ts +2 -0
- package/data/build/dist/host/features/types.d.ts.map +1 -1
- package/data/build/dist/host/index.d.ts +15 -1
- package/data/build/dist/host/index.d.ts.map +1 -1
- package/data/build/dist/host/index.js +48 -2
- package/data/build/dist/host/index.js.map +1 -1
- package/data/build/dist/host/lan-access-dsh.d.ts +7 -1
- package/data/build/dist/host/lan-access-dsh.d.ts.map +1 -1
- package/data/build/dist/host/lan-access-dsh.js +95 -19
- package/data/build/dist/host/lan-access-dsh.js.map +1 -1
- package/data/build/dist/host/login-attempt-guard.d.ts +55 -0
- package/data/build/dist/host/login-attempt-guard.d.ts.map +1 -0
- package/data/build/dist/host/login-attempt-guard.js +201 -0
- package/data/build/dist/host/login-attempt-guard.js.map +1 -0
- package/data/build/dist/host/modules/peer-host/host-api-proxy-service.d.ts +3 -0
- package/data/build/dist/host/modules/peer-host/host-api-proxy-service.d.ts.map +1 -1
- package/data/build/dist/host/modules/peer-host/host-api-proxy-service.js +2 -0
- package/data/build/dist/host/modules/peer-host/host-api-proxy-service.js.map +1 -1
- package/data/build/dist/host/modules/peer-host/peer-host-aggregate-service.d.ts +1 -0
- package/data/build/dist/host/modules/peer-host/peer-host-aggregate-service.d.ts.map +1 -1
- package/data/build/dist/host/modules/peer-host/peer-host-aggregate-service.js +1 -0
- package/data/build/dist/host/modules/peer-host/peer-host-aggregate-service.js.map +1 -1
- package/data/build/dist/host/modules/peer-host/peer-host-native-protocol.d.ts +1 -1
- package/data/build/dist/host/modules/peer-host/peer-host-native-protocol.d.ts.map +1 -1
- package/data/build/dist/host/modules/peer-host/peer-host-native-protocol.js +9 -1
- package/data/build/dist/host/modules/peer-host/peer-host-native-protocol.js.map +1 -1
- package/data/build/dist/host/modules/peer-host/peer-host-native-transport.d.ts +8 -0
- package/data/build/dist/host/modules/peer-host/peer-host-native-transport.d.ts.map +1 -1
- package/data/build/dist/host/modules/peer-host/peer-host-native-transport.js +9 -0
- package/data/build/dist/host/modules/peer-host/peer-host-native-transport.js.map +1 -1
- package/data/build/dist/host/modules/peer-host/peer-host-remote-summary-source.d.ts +7 -0
- package/data/build/dist/host/modules/peer-host/peer-host-remote-summary-source.d.ts.map +1 -1
- package/data/build/dist/host/modules/peer-host/peer-host-remote-summary-source.js +31 -3
- package/data/build/dist/host/modules/peer-host/peer-host-remote-summary-source.js.map +1 -1
- package/data/build/dist/host/modules/peer-host/peer-host-virtual-registry.d.ts +2 -0
- package/data/build/dist/host/modules/peer-host/peer-host-virtual-registry.d.ts.map +1 -1
- package/data/build/dist/host/modules/peer-host/peer-host-virtual-registry.js +26 -7
- package/data/build/dist/host/modules/peer-host/peer-host-virtual-registry.js.map +1 -1
- package/data/build/dist/host/modules/pwa/pwa-assets.d.ts +6 -4
- package/data/build/dist/host/modules/pwa/pwa-assets.d.ts.map +1 -1
- package/data/build/dist/host/modules/pwa/pwa-assets.js +11 -9
- package/data/build/dist/host/modules/pwa/pwa-assets.js.map +1 -1
- package/data/build/dist/host/modules/pwa/pwa-session-notifications.d.ts +3 -0
- package/data/build/dist/host/modules/pwa/pwa-session-notifications.d.ts.map +1 -1
- package/data/build/dist/host/modules/pwa/pwa-session-notifications.js +6 -4
- package/data/build/dist/host/modules/pwa/pwa-session-notifications.js.map +1 -1
- package/data/build/dist/host/native-session-bridge.d.ts.map +1 -1
- package/data/build/dist/host/native-session-bridge.js +106 -59
- package/data/build/dist/host/native-session-bridge.js.map +1 -1
- package/data/build/dist/host/rpc.js +8 -2
- package/data/build/dist/host/rpc.js.map +1 -1
- package/data/build/dist/host/settings.d.ts.map +1 -1
- package/data/build/dist/host/settings.js +14 -4
- package/data/build/dist/host/settings.js.map +1 -1
- package/data/build/dist/host/terminal/backends/local-pty-backend.d.ts.map +1 -1
- package/data/build/dist/host/terminal/backends/local-pty-backend.js +14 -0
- package/data/build/dist/host/terminal/backends/local-pty-backend.js.map +1 -1
- package/data/build/dist/host/terminal/backends/tmux-backend.d.ts +40 -1
- package/data/build/dist/host/terminal/backends/tmux-backend.d.ts.map +1 -1
- package/data/build/dist/host/terminal/backends/tmux-backend.js +291 -18
- package/data/build/dist/host/terminal/backends/tmux-backend.js.map +1 -1
- package/data/build/dist/host/terminal/runtime-adapter.d.ts +32 -0
- package/data/build/dist/host/terminal/runtime-adapter.d.ts.map +1 -1
- package/data/build/dist/host/terminal/runtime-adapter.js +8 -0
- package/data/build/dist/host/terminal/runtime-adapter.js.map +1 -1
- package/data/build/dist/host/terminal/runtime-manager.d.ts +3 -0
- package/data/build/dist/host/terminal/runtime-manager.d.ts.map +1 -1
- package/data/build/dist/host/terminal/runtime-manager.js +92 -4
- package/data/build/dist/host/terminal/runtime-manager.js.map +1 -1
- package/data/build/dist/host/terminal/terminal-controller.d.ts.map +1 -1
- package/data/build/dist/host/terminal/terminal-controller.js +58 -6
- package/data/build/dist/host/terminal/terminal-controller.js.map +1 -1
- package/data/build/dist/host/terminal/terminal-process-service.d.ts.map +1 -1
- package/data/build/dist/host/terminal/terminal-process-service.js +12 -2
- package/data/build/dist/host/terminal/terminal-process-service.js.map +1 -1
- package/data/build/dist/host/terminal/terminal-service.d.ts +41 -4
- package/data/build/dist/host/terminal/terminal-service.d.ts.map +1 -1
- package/data/build/dist/host/terminal/terminal-service.js +551 -61
- package/data/build/dist/host/terminal/terminal-service.js.map +1 -1
- package/data/build/dist/index.d.ts +2 -2
- package/data/build/dist/index.d.ts.map +1 -1
- package/data/build/dist/index.js +2 -2
- package/data/build/dist/index.js.map +1 -1
- package/data/build/dist/shared/contracts/cli-adapter.d.ts +69 -2
- package/data/build/dist/shared/contracts/cli-adapter.d.ts.map +1 -1
- package/data/build/dist/shared/contracts/config.d.ts +63 -10
- package/data/build/dist/shared/contracts/config.d.ts.map +1 -1
- package/data/build/dist/shared/contracts/config.js +57 -5
- package/data/build/dist/shared/contracts/config.js.map +1 -1
- package/data/build/dist/shared/contracts/peer-host.d.ts +2 -0
- package/data/build/dist/shared/contracts/peer-host.d.ts.map +1 -1
- package/data/build/dist/shared/contracts/peer-host.js.map +1 -1
- package/data/build/dist/shared/contracts/subscription.d.ts +20 -1
- 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 +8 -1
- 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.d.ts.map +1 -1
- package/data/build/dist/shared/contracts/version.js +1 -1
- package/data/build/dist/shared/contracts/version.js.map +1 -1
- package/data/build/dist/shared/debug.d.ts +8 -0
- package/data/build/dist/shared/debug.d.ts.map +1 -1
- package/data/build/dist/shared/debug.js +43 -7
- package/data/build/dist/shared/debug.js.map +1 -1
- package/data/build/dist/shared/delegation-carrier.d.ts +24 -0
- package/data/build/dist/shared/delegation-carrier.d.ts.map +1 -0
- package/data/build/dist/shared/delegation-carrier.js +111 -0
- package/data/build/dist/shared/delegation-carrier.js.map +1 -0
- package/data/build/dist/shared/index.d.ts +3 -3
- package/data/build/dist/shared/index.d.ts.map +1 -1
- package/data/build/dist/shared/index.js +2 -2
- package/data/build/dist/shared/index.js.map +1 -1
- package/data/build/dist/shared/terminal-input.d.ts +8 -0
- package/data/build/dist/shared/terminal-input.d.ts.map +1 -0
- package/data/build/dist/shared/terminal-input.js +10 -0
- package/data/build/dist/shared/terminal-input.js.map +1 -0
- package/data/build/dist/transport/debug.d.ts +7 -0
- package/data/build/dist/transport/debug.d.ts.map +1 -1
- package/data/build/dist/transport/debug.js +33 -5
- package/data/build/dist/transport/debug.js.map +1 -1
- package/data/build/dist/transport/index.d.ts +1 -1
- package/data/build/dist/transport/index.d.ts.map +1 -1
- package/data/build/dist/transport/index.js +1 -1
- package/data/build/dist/transport/index.js.map +1 -1
- package/data/build/dist/typert.host.js +1 -1
- package/data/build/dist/typert.host.js.map +1 -1
- package/package.json +3 -1
- package/profile/README.md +2 -2
- package/profile/package.json +2 -2
- package/profile/version.json +1 -1
- package/version.json +1 -1
|
@@ -2,16 +2,29 @@ import { createElement, useEffect, useRef, useState } from 'react';
|
|
|
2
2
|
import { isSubscriptionUsageFresh } from '../shared/contracts/subscription.js';
|
|
3
3
|
import { DEFAULT_SUBSCRIPTION_USAGE_SETTINGS } from '../shared/contracts/config.js';
|
|
4
4
|
import { callCliRpc } from './cli-catalog.js';
|
|
5
|
+
import { resolveCodingNsTranslator, useCodingNsTranslator } from './locale.js';
|
|
5
6
|
import { providerIconUrl } from './provider-icons.js';
|
|
6
7
|
import { subscribeSessionAdapters } from './session-adapter-cache.js';
|
|
7
|
-
import { dshPopupSurfaceStyle, dshThemeColor } from './theme.js';
|
|
8
|
+
import { dshPopupSurfaceStyle, dshSettingsButtonStyle, dshSettingsPrimaryButtonStyle, dshThemeColor } from './theme.js';
|
|
8
9
|
import { useDismissOnOutsidePointer } from './popup-dismiss.js';
|
|
9
10
|
const SUBSCRIPTION_STYLE_ID = 'codingns4dsh-subscription-responsive-style';
|
|
11
|
+
/**
|
|
12
|
+
* 没有 locale 服务时的静态兜底:命名空间绑定固定指向内置中文词典,
|
|
13
|
+
* 且不产生任何语言变更通知。生产路径由 registerSubscriptionSlot 注入 DSH locale。
|
|
14
|
+
*/
|
|
15
|
+
const FALLBACK_LOCALE = {
|
|
16
|
+
bind: () => resolveCodingNsTranslator(undefined),
|
|
17
|
+
getSnapshot: () => ({ revision: 0 }),
|
|
18
|
+
subscribe: () => () => { },
|
|
19
|
+
register: () => () => { },
|
|
20
|
+
};
|
|
10
21
|
/**
|
|
11
22
|
* 进程内用量结果缓存:同一适配器/提供商在刷新间隔内直接复用上次结果,
|
|
12
23
|
* 避免每次进入会话或切回同一 Agent 都请求上游;null 结果不缓存,便于刚登录后立刻重试。
|
|
13
24
|
*/
|
|
14
25
|
const subscriptionUsageCache = new Map();
|
|
26
|
+
/** 图标重置按钮的悬停/按下/聚焦/禁用只能由注入样式表表达,内联样式无法命中伪类。 */
|
|
27
|
+
const RESET_BUTTON_CSS = '.codingns4dsh-subscription-reset{display:inline-flex;align-items:center;justify-content:center;flex:none;width:26px;height:26px;padding:0;border:1px solid var(--dsw-alias-border-l2,#d9d9d9);border-radius:50%;background:transparent;color:var(--dsw-alias-label-secondary,GrayText);cursor:pointer;transition:background .15s ease,color .15s ease}.codingns4dsh-subscription-reset:hover:not(:disabled){background:var(--dsw-alias-interactive-bg-hover,rgba(127,127,127,.08));color:var(--dsw-alias-label-primary,CanvasText)}.codingns4dsh-subscription-reset:active:not(:disabled){background:var(--dsw-alias-interactive-bg-active,rgba(127,127,127,.14))}.codingns4dsh-subscription-reset:focus-visible{outline:none;box-shadow:0 0 0 var(--dsw-focus-ring-width,2px) var(--dsw-focus-ring-color,var(--dsw-alias-state-business-primary,#1677ff))}.codingns4dsh-subscription-reset:disabled{opacity:.4;cursor:not-allowed}@media (prefers-reduced-motion: reduce){.codingns4dsh-subscription-reset{transition:none}}';
|
|
15
28
|
/** 移动端订阅入口只保留图标,完整数据仍可在点击后的弹层中查看。 */
|
|
16
29
|
function installSubscriptionStyles() {
|
|
17
30
|
if (typeof document === 'undefined' || document.querySelector(`style[data-plugin-css="${SUBSCRIPTION_STYLE_ID}"]`) !== null)
|
|
@@ -19,21 +32,28 @@ function installSubscriptionStyles() {
|
|
|
19
32
|
const style = document.createElement('style');
|
|
20
33
|
style.dataset.plugin = 'codingns4dsh';
|
|
21
34
|
style.dataset.pluginCss = SUBSCRIPTION_STYLE_ID;
|
|
22
|
-
style.textContent = '@media (max-width: 768px){.codingns4dsh-subscription-trigger{gap:0!important;padding-left:4px!important;padding-right:4px!important}.codingns4dsh-subscription-label,.codingns4dsh-subscription-value{display:none!important}.codingns4dsh-subscription-popover{position:fixed!important;left:12px!important;right:12px!important;bottom:48px!important;width:auto!important;min-width:0!important;max-width:none!important;max-height:calc(100vh - 72px)!important;overflow:auto!important}}';
|
|
35
|
+
style.textContent = '@media (max-width: 768px){.codingns4dsh-subscription-trigger{gap:0!important;padding-left:4px!important;padding-right:4px!important}.codingns4dsh-subscription-label,.codingns4dsh-subscription-value{display:none!important}.codingns4dsh-subscription-popover{position:fixed!important;left:12px!important;right:12px!important;bottom:48px!important;width:auto!important;min-width:0!important;max-width:none!important;max-height:calc(100vh - 72px)!important;overflow:auto!important}}' + RESET_BUTTON_CSS;
|
|
23
36
|
document.head.appendChild(style);
|
|
24
37
|
}
|
|
25
38
|
/** 在 DSH 原生步骤统计左侧显示当前 Agent 的订阅余量。 */
|
|
26
|
-
export function registerSubscriptionSlot(slots, rpc, getRefreshIntervalMins) {
|
|
39
|
+
export function registerSubscriptionSlot(slots, rpc, getRefreshIntervalMins, locale) {
|
|
27
40
|
installSubscriptionStyles();
|
|
41
|
+
const t = resolveCodingNsTranslator(locale);
|
|
28
42
|
return slots.inject('conversation.composer.dock', () => slots.register({
|
|
29
43
|
name: 'conversation.composer.dock',
|
|
30
44
|
id: 'codingns4dsh-subscription',
|
|
31
45
|
order: -20,
|
|
32
|
-
label: '
|
|
33
|
-
inject: (sessionId) => ({
|
|
46
|
+
label: t('usage.slotLabel'),
|
|
47
|
+
inject: (sessionId) => ({
|
|
48
|
+
rpc,
|
|
49
|
+
sessionId,
|
|
50
|
+
locale: locale ?? FALLBACK_LOCALE,
|
|
51
|
+
...(getRefreshIntervalMins === undefined ? {} : { getRefreshIntervalMins }),
|
|
52
|
+
}),
|
|
34
53
|
}, CommandCodeSubscriptionSlot));
|
|
35
54
|
}
|
|
36
55
|
function CommandCodeSubscriptionSlot(props) {
|
|
56
|
+
const t = useCodingNsTranslator(props.locale ?? FALLBACK_LOCALE);
|
|
37
57
|
const [usage, setUsage] = useState(null);
|
|
38
58
|
const [adapterId, setAdapterId] = useState(null);
|
|
39
59
|
const [providerId, setProviderId] = useState(null);
|
|
@@ -42,6 +62,13 @@ function CommandCodeSubscriptionSlot(props) {
|
|
|
42
62
|
const [loading, setLoading] = useState(false);
|
|
43
63
|
const [clock, setClock] = useState(() => Date.now());
|
|
44
64
|
const rootRef = useRef(null);
|
|
65
|
+
const resetDialogRef = useRef(null);
|
|
66
|
+
// 重置成功后的刷新不能重跑加载 effect,否则 usage 会被清空导致底部入口闪断。
|
|
67
|
+
const refreshRef = useRef(null);
|
|
68
|
+
const [resetOpen, setResetOpen] = useState(false);
|
|
69
|
+
const [resetPending, setResetPending] = useState(false);
|
|
70
|
+
const [resetResult, setResetResult] = useState(null);
|
|
71
|
+
const [resetError, setResetError] = useState(null);
|
|
45
72
|
const modelSelectionRevision = props.useSession?.((value) => JSON.stringify(value.modelSelection));
|
|
46
73
|
// 切换 Agent 可能只改变 Host 侧会话配置,DSH 会话快照不一定会更新;订阅适配器
|
|
47
74
|
// 缓存的变更才能真正触发重新查询,否则底部会一直显示上一个 Agent 的订阅数据。
|
|
@@ -55,6 +82,10 @@ function CommandCodeSubscriptionSlot(props) {
|
|
|
55
82
|
setAdapterId(null);
|
|
56
83
|
setProviderId(null);
|
|
57
84
|
setOpen(false);
|
|
85
|
+
setResetOpen(false);
|
|
86
|
+
setResetPending(false);
|
|
87
|
+
setResetResult(null);
|
|
88
|
+
setResetError(null);
|
|
58
89
|
return;
|
|
59
90
|
}
|
|
60
91
|
let active = true;
|
|
@@ -63,6 +94,10 @@ function CommandCodeSubscriptionSlot(props) {
|
|
|
63
94
|
setAdapterId(null);
|
|
64
95
|
setProviderId(null);
|
|
65
96
|
setOpen(false);
|
|
97
|
+
setResetOpen(false);
|
|
98
|
+
setResetPending(false);
|
|
99
|
+
setResetResult(null);
|
|
100
|
+
setResetError(null);
|
|
66
101
|
const refresh = async () => {
|
|
67
102
|
setLoading(true);
|
|
68
103
|
try {
|
|
@@ -85,7 +120,10 @@ function CommandCodeSubscriptionSlot(props) {
|
|
|
85
120
|
const intervalMins = props.getRefreshIntervalMins?.() ?? DEFAULT_SUBSCRIPTION_USAGE_SETTINGS.refreshIntervalMins;
|
|
86
121
|
const cacheKey = `${adapterId}|${selection.providerId ?? ''}`;
|
|
87
122
|
const cached = subscriptionUsageCache.get(cacheKey);
|
|
88
|
-
|
|
123
|
+
// New-API 的余额和 Token 日志可能随 Key/钱包状态快速变化,且旧结果
|
|
124
|
+
// 容易把历史日志投影到当前站点;每次刷新都重新读取,Sub2API 仍复用原缓存。
|
|
125
|
+
const canReuseCachedUsage = cached !== undefined && cached.usage.provider?.capability !== 'new-api';
|
|
126
|
+
if (canReuseCachedUsage && isSubscriptionUsageFresh(cached.capturedAt, Date.now(), intervalMins)) {
|
|
89
127
|
if (active)
|
|
90
128
|
setUsage(cached.usage);
|
|
91
129
|
return;
|
|
@@ -110,11 +148,13 @@ function CommandCodeSubscriptionSlot(props) {
|
|
|
110
148
|
setLoading(false);
|
|
111
149
|
}
|
|
112
150
|
};
|
|
151
|
+
refreshRef.current = refresh;
|
|
113
152
|
void refresh();
|
|
114
153
|
const intervalMins = props.getRefreshIntervalMins?.() ?? DEFAULT_SUBSCRIPTION_USAGE_SETTINGS.refreshIntervalMins;
|
|
115
154
|
const timer = intervalMins > 0 ? globalThis.setInterval(() => { void refresh(); }, intervalMins * 60_000) : undefined;
|
|
116
155
|
return () => {
|
|
117
156
|
active = false;
|
|
157
|
+
refreshRef.current = null;
|
|
118
158
|
if (timer !== undefined)
|
|
119
159
|
globalThis.clearInterval(timer);
|
|
120
160
|
};
|
|
@@ -125,35 +165,96 @@ function CommandCodeSubscriptionSlot(props) {
|
|
|
125
165
|
const timer = globalThis.setInterval(() => setClock(Date.now()), 60_000);
|
|
126
166
|
return () => globalThis.clearInterval(timer);
|
|
127
167
|
}, [eligible, usage]);
|
|
168
|
+
const closeResetDialog = () => {
|
|
169
|
+
if (resetPending)
|
|
170
|
+
return;
|
|
171
|
+
setResetOpen(false);
|
|
172
|
+
setResetResult(null);
|
|
173
|
+
setResetError(null);
|
|
174
|
+
};
|
|
175
|
+
const confirmReset = () => {
|
|
176
|
+
if (resetPending || adapterId === null)
|
|
177
|
+
return;
|
|
178
|
+
const cacheKey = `${adapterId}|${providerId ?? ''}`;
|
|
179
|
+
setResetPending(true);
|
|
180
|
+
setResetError(null);
|
|
181
|
+
void (async () => {
|
|
182
|
+
try {
|
|
183
|
+
const result = await callCliRpc(props.rpc, 'subscription/reset', {
|
|
184
|
+
adapterId,
|
|
185
|
+
...(providerId === null ? {} : { providerId }),
|
|
186
|
+
});
|
|
187
|
+
setResetResult(result.outcome);
|
|
188
|
+
// 重置改变了窗口与次数,必须绕过进程内缓存重新读取。
|
|
189
|
+
subscriptionUsageCache.delete(cacheKey);
|
|
190
|
+
await refreshRef.current?.();
|
|
191
|
+
}
|
|
192
|
+
catch (error) {
|
|
193
|
+
setResetError(error instanceof Error ? error.message : '');
|
|
194
|
+
}
|
|
195
|
+
finally {
|
|
196
|
+
setResetPending(false);
|
|
197
|
+
}
|
|
198
|
+
})();
|
|
199
|
+
};
|
|
128
200
|
useDismissOnOutsidePointer(rootRef, open, () => setOpen(false));
|
|
201
|
+
useDismissOnOutsidePointer(resetDialogRef, resetOpen && !resetPending, closeResetDialog);
|
|
129
202
|
// 未拿到真实订阅数据时不占用底部栏空间;加载状态不能伪装成订阅存在。
|
|
130
203
|
if (!eligible || usage === null || (usage.sub2api === undefined && usage.deepseek === undefined && usage.providerBalance === undefined && resolveDisplayWindow(usage) === null))
|
|
131
204
|
return null;
|
|
132
205
|
const sub2api = usage.sub2api;
|
|
133
206
|
const deepseek = usage.deepseek;
|
|
134
207
|
const providerBalance = usage.providerBalance;
|
|
208
|
+
const isNewApiProvider = providerBalance !== undefined && usage.provider?.capability === 'new-api';
|
|
135
209
|
const displayWindow = sub2api === undefined && deepseek === undefined && providerBalance === undefined ? resolveDisplayWindow(usage) : null;
|
|
136
210
|
const remaining = displayWindow?.remainingPercent ?? null;
|
|
137
|
-
const resetLabel = displayWindow === null ? null : formatCountdown(displayWindow.resetsAt, clock);
|
|
138
|
-
const providerName = subscriptionProviderName(adapterId, providerId, usage);
|
|
211
|
+
const resetLabel = displayWindow === null ? null : formatCountdown(displayWindow.resetsAt, t, clock);
|
|
212
|
+
const providerName = subscriptionProviderName(adapterId, providerId, usage, t);
|
|
139
213
|
const deepseekBalance = deepseek === undefined ? null : selectDeepseekBalance(deepseek);
|
|
140
|
-
const
|
|
141
|
-
const
|
|
214
|
+
const providerBalanceRemaining = providerBalance === undefined ? null : balancePercent(providerBalance.remaining, providerBalance.total);
|
|
215
|
+
const providerBalancePlan = providerBalance?.planName?.trim() || null;
|
|
216
|
+
const newApiHeadline = isNewApiProvider && providerBalance !== undefined ? formatNewApiHeadline(providerBalance) : null;
|
|
217
|
+
// 官方余额读取器可能没有可直连的 Provider Logo;此时统一回退到当前
|
|
218
|
+
// 适配器注册的内置图标,ZCode 等 Agent 不再显示空 src 的破图。
|
|
219
|
+
const adapterIconSource = providerIconUrl(adapterId ?? 'dsh') ?? '';
|
|
220
|
+
const providerLogoSource = usage.provider?.logoDataUrl?.trim() || (!isRemoteWebContext() ? usage.provider?.logoUrl?.trim() : '') || adapterIconSource;
|
|
221
|
+
const deepseekIconSource = providerLogoSource;
|
|
142
222
|
const label = sub2api === undefined && deepseek === undefined && providerBalance === undefined
|
|
143
|
-
?
|
|
223
|
+
? t('usage.remainingLabel', { provider: providerName, percent: formatPercent(remaining ?? 0) })
|
|
144
224
|
: sub2api !== undefined
|
|
145
|
-
?
|
|
225
|
+
? t('usage.upstreamBalanceLabel', { provider: providerName, amount: formatSub2ApiMoney(sub2api.balance, sub2api.unit) })
|
|
146
226
|
: deepseek !== undefined
|
|
147
|
-
?
|
|
148
|
-
:
|
|
227
|
+
? t('usage.balanceLabel', { provider: providerName, amount: deepseekBalance === null ? t('usage.unavailable') : formatDeepseekMoney(deepseekBalance.totalBalance, deepseekBalance.currency) })
|
|
228
|
+
: isNewApiProvider
|
|
229
|
+
? newApiHeadline === null ? providerName : `${providerName} ${newApiHeadline}`
|
|
230
|
+
: providerBalancePlan === null
|
|
231
|
+
? t('usage.providerBalanceLabel', { provider: providerName, amount: formatProviderBalance(providerBalance, t('usage.upstreamNotProvided')) })
|
|
232
|
+
: t('usage.providerBalancePlanLabel', { provider: providerName, plan: providerBalancePlan, amount: formatProviderBalance(providerBalance, t('usage.upstreamNotProvided')) });
|
|
149
233
|
const logoSource = providerLogoSource || (sub2api === undefined ? '' : (sub2api.logoDataUrl ?? (isRemoteWebContext() ? '' : sub2api.logoUrl)));
|
|
234
|
+
const resetCredits = usage.resetCredits;
|
|
235
|
+
// 重置只对官方 Codex 订阅开放;第三方上游走 sub2api 面板,不会带出重置券。
|
|
236
|
+
const resetRequest = adapterId === 'codex' && resetCredits !== null
|
|
237
|
+
? {
|
|
238
|
+
enabled: resetCredits.availableCount > 0 && !resetPending,
|
|
239
|
+
onRequest: () => {
|
|
240
|
+
setOpen(false);
|
|
241
|
+
setResetResult(null);
|
|
242
|
+
setResetError(null);
|
|
243
|
+
setResetOpen(true);
|
|
244
|
+
},
|
|
245
|
+
}
|
|
246
|
+
: null;
|
|
150
247
|
const triggerContent = sub2api === undefined && deepseek === undefined && providerBalance === undefined
|
|
151
248
|
? createElement('span', { 'aria-hidden': true, style: progressRingStyle() }, createElement('span', { style: { ...progressRingVisualStyle, background: progressRingVisualBackground(remaining === null ? 0 : remaining / 100, false) } }, createElement('span', { style: progressRingValueStyle }, createElement('span', undefined, formatRingPercentage(remaining ?? 0)), createElement('span', { style: progressRingSuffixStyle }, '%'))))
|
|
152
249
|
: sub2api !== undefined
|
|
153
250
|
? createElement('span', { 'aria-hidden': true, style: sub2apiIdentityStyle }, createElement('img', { src: logoSource || providerIconUrl(adapterId ?? 'dsh') || '', alt: '', width: 20, height: 20, style: sub2apiLogoStyle }), createElement('span', { className: 'codingns4dsh-subscription-value' }, formatSub2ApiMoney(sub2api.balance, sub2api.unit)))
|
|
154
251
|
: deepseek !== undefined
|
|
155
|
-
? createElement('span', { 'aria-hidden': true, style: deepseekBalanceIdentityStyle }, deepseekIconSource !==
|
|
156
|
-
:
|
|
252
|
+
? createElement('span', { 'aria-hidden': true, style: deepseekBalanceIdentityStyle }, deepseekIconSource !== '' && createElement('img', { src: deepseekIconSource, alt: '', width: 18, height: 18, style: deepseekLogoStyle }), createElement('span', { className: 'codingns4dsh-subscription-value', style: deepseekBalanceStyle }, deepseekBalance === null ? '--' : formatDeepseekMoney(deepseekBalance.totalBalance, deepseekBalance.currency)))
|
|
253
|
+
: isNewApiProvider
|
|
254
|
+
? createElement('span', { 'aria-hidden': true, style: deepseekBalanceIdentityStyle }, deepseekIconSource !== '' && createElement('img', { src: deepseekIconSource, alt: '', width: 18, height: 18, style: deepseekLogoStyle }), newApiHeadline !== null && createElement('span', { className: 'codingns4dsh-subscription-value', style: deepseekBalanceStyle }, newApiHeadline))
|
|
255
|
+
: providerBalanceRemaining !== null
|
|
256
|
+
? createRemainingRing(providerBalanceRemaining)
|
|
257
|
+
: createElement('span', { 'aria-hidden': true, style: deepseekBalanceIdentityStyle }, deepseekIconSource !== '' && createElement('img', { src: deepseekIconSource, alt: '', width: 18, height: 18, style: deepseekLogoStyle }), createElement('span', { className: 'codingns4dsh-subscription-value', style: deepseekBalanceStyle }, formatProviderBalance(providerBalance, t('usage.upstreamNotProvided'))));
|
|
157
258
|
return createElement('div', { ref: rootRef, style: subscriptionRootStyle }, createElement('button', {
|
|
158
259
|
type: 'button',
|
|
159
260
|
className: 'codingns4dsh-subscription-trigger',
|
|
@@ -163,48 +264,312 @@ function CommandCodeSubscriptionSlot(props) {
|
|
|
163
264
|
'aria-expanded': open,
|
|
164
265
|
style: subscriptionTriggerStyle,
|
|
165
266
|
}, triggerContent, createElement('span', { className: 'codingns4dsh-subscription-label', style: subscriptionLabelStyle }, sub2api === undefined && deepseek === undefined && providerBalance === undefined
|
|
166
|
-
? (resetLabel ?? '
|
|
167
|
-
: sub2api !== undefined ?
|
|
267
|
+
? (resetLabel ?? t('usage.subscriptionRemaining'))
|
|
268
|
+
: sub2api !== undefined ? t('usage.todayCostShort', { amount: formatSub2ApiMoney(sub2api.today.cost, sub2api.unit) }) : deepseek !== undefined ? t('usage.accountBalance') : isNewApiProvider ? providerName : providerBalancePlan ?? t('usage.officialRemaining'))), open && createElement(SubscriptionPopover, { usage, providerName, t, nowMs: clock, reset: resetRequest }), resetOpen && createElement(ResetConfirmDialog, {
|
|
269
|
+
count: resetCredits?.availableCount ?? 0,
|
|
270
|
+
pending: resetPending,
|
|
271
|
+
result: resetResult,
|
|
272
|
+
error: resetError,
|
|
273
|
+
t,
|
|
274
|
+
onCancel: closeResetDialog,
|
|
275
|
+
onConfirm: confirmReset,
|
|
276
|
+
onClose: closeResetDialog,
|
|
277
|
+
dialogRef: resetDialogRef,
|
|
278
|
+
}));
|
|
168
279
|
}
|
|
169
|
-
function SubscriptionPopover({ usage, providerName }) {
|
|
280
|
+
function SubscriptionPopover({ usage, providerName, t, nowMs, reset }) {
|
|
170
281
|
if (usage.sub2api !== undefined)
|
|
171
|
-
return createElement(Sub2ApiPopover, { usage: usage.sub2api, providerName });
|
|
282
|
+
return createElement(Sub2ApiPopover, { usage: usage.sub2api, providerName, t });
|
|
172
283
|
if (usage.deepseek !== undefined)
|
|
173
|
-
return createElement(DeepseekPopover, { usage: usage.deepseek, providerName });
|
|
174
|
-
if (usage.providerBalance !== undefined)
|
|
175
|
-
|
|
284
|
+
return createElement(DeepseekPopover, { usage: usage.deepseek, providerName, t });
|
|
285
|
+
if (usage.providerBalance !== undefined) {
|
|
286
|
+
if (usage.provider?.capability === 'new-api')
|
|
287
|
+
return createElement(NewApiPopover, { usage: usage.providerBalance, providerName, t });
|
|
288
|
+
return createElement(ProviderBalancePopover, { usage: usage.providerBalance, providerName, t, nowMs });
|
|
289
|
+
}
|
|
176
290
|
const windows = [
|
|
177
|
-
{ id: 'primary', label: formatSubscriptionWindowLabel(usage.primary, '
|
|
178
|
-
{ id: 'secondary', label: formatSubscriptionWindowLabel(usage.secondary, '
|
|
179
|
-
{ id: 'monthly', label: formatSubscriptionWindowLabel(usage.monthly, '
|
|
291
|
+
{ id: 'primary', label: formatSubscriptionWindowLabel(usage.primary, t('usage.windowFiveHour'), t), window: usage.primary },
|
|
292
|
+
{ id: 'secondary', label: formatSubscriptionWindowLabel(usage.secondary, t('usage.windowWeekly'), t), window: usage.secondary },
|
|
293
|
+
{ id: 'monthly', label: formatSubscriptionWindowLabel(usage.monthly, t('usage.windowMonthly'), t), window: usage.monthly },
|
|
180
294
|
];
|
|
181
|
-
|
|
295
|
+
const credits = usage.credits ?? null;
|
|
296
|
+
const creditText = credits === null
|
|
297
|
+
? null
|
|
298
|
+
: credits.unlimited
|
|
299
|
+
? t('usage.creditUnlimited')
|
|
300
|
+
: credits.balance !== null
|
|
301
|
+
? formatCreditBalance(credits.balance)
|
|
302
|
+
: credits.hasCredits ? '0.00' : '--';
|
|
303
|
+
const expiries = usage.resetCredits === null
|
|
304
|
+
? []
|
|
305
|
+
: usage.resetCredits.credits
|
|
306
|
+
.map((credit) => credit.expiresAt)
|
|
307
|
+
.filter((expiry) => expiry !== null)
|
|
308
|
+
.sort((left, right) => left - right);
|
|
309
|
+
return createElement('div', { className: 'codingns4dsh-subscription-popover', role: 'dialog', 'aria-label': t('usage.popoverSubscriptionUsage', { provider: providerName }), style: subscriptionPopoverStyle }, createElement('div', { style: popoverHeadingStyle }, createElement('strong', undefined, t('usage.popoverSubscriptionTitle', { provider: providerName })), usage.planType && createElement('span', { style: { color: dshThemeColor.labelTertiary } }, formatPlanType(usage.planType))), ...windows.map(({ id, label, window }) => window === null ? null : createElement('section', { key: id, style: windowStyle }, createElement('div', { style: windowHeadingStyle }, createElement('span', undefined, label), createElement('span', undefined, `${formatPercent(window.remainingPercent)}%`)), createElement('div', { role: 'progressbar', 'aria-label': t('usage.windowRemaining', { label, percent: formatPercent(window.remainingPercent) }), 'aria-valuemin': 0, 'aria-valuemax': 100, 'aria-valuenow': window.remainingPercent, style: barStyle }, createElement('span', { style: { ...barFillStyle, width: `${window.remainingPercent}%` } })), window.resetsAt !== null && createElement('div', { style: resetStyle }, t('usage.resetsIn', { time: formatCountdown(window.resetsAt, t) })))), (creditText !== null || usage.resetCredits !== null) && createElement('section', { style: resetCreditsSectionStyle }, creditText !== null && createElement('div', { style: resetCreditsRowStyle }, createElement('span', undefined, t('usage.creditBalanceLabel')), createElement('span', { style: resetCreditsValueStyle }, creditText)), usage.resetCredits !== null && createElement('div', { style: resetCreditsRowStyle }, createElement('span', undefined, t('usage.resetCreditsLabel')), createElement('span', { style: resetCreditsValueGroupStyle }, createElement('span', { style: resetCreditsValueStyle }, t('usage.resetCreditsCount', { count: usage.resetCredits.availableCount })), reset !== null && createElement('button', {
|
|
310
|
+
type: 'button',
|
|
311
|
+
className: 'codingns4dsh-subscription-reset',
|
|
312
|
+
disabled: !reset.enabled,
|
|
313
|
+
onClick: reset.onRequest,
|
|
314
|
+
title: reset.enabled ? t('usage.resetTooltipReady') : t('usage.resetTooltipNone'),
|
|
315
|
+
'aria-label': t('usage.resetButton'),
|
|
316
|
+
}, createElement(ResetIcon, undefined)))), expiries.slice(0, 3).map((expiry, index) => createElement('div', { key: `${expiry}-${index}`, style: resetCreditsExpiryStyle }, t('usage.resetCreditsExpiresAt', { time: formatResetExpiry(expiry, t, nowMs) }))), expiries.length > 3 && createElement('div', { style: resetCreditsExpiryStyle }, t('usage.resetCreditsMore', { count: expiries.length - 3 }))));
|
|
317
|
+
}
|
|
318
|
+
/** 重置按钮复用会话变更视图的刷新字形,保持插件内图标语言一致。 */
|
|
319
|
+
function ResetIcon() {
|
|
320
|
+
return createElement('svg', { width: 14, height: 14, viewBox: '0 0 20 20', fill: 'none', 'aria-hidden': true }, createElement('path', { d: 'M16 8.5A6.2 6.2 0 1 0 16.1 12', stroke: 'currentColor', strokeWidth: 1.6, strokeLinecap: 'round' }), createElement('path', { d: 'M16 4.5v4h-4', stroke: 'currentColor', strokeWidth: 1.6, strokeLinecap: 'round', strokeLinejoin: 'round' }));
|
|
321
|
+
}
|
|
322
|
+
function ResetConfirmDialog({ count, pending, result, error, t, onCancel, onConfirm, onClose, dialogRef }) {
|
|
323
|
+
const finished = result !== null || error !== null;
|
|
324
|
+
const message = pending
|
|
325
|
+
? t('usage.resetDialogPending')
|
|
326
|
+
: result !== null
|
|
327
|
+
? resetOutcomeMessage(result, t)
|
|
328
|
+
: error !== null && error.trim() !== ''
|
|
329
|
+
? error
|
|
330
|
+
: t('usage.resetDialogBody', { count });
|
|
331
|
+
const messageColor = error !== null
|
|
332
|
+
? dshThemeColor.error
|
|
333
|
+
: result === 'reset' || result === 'alreadyRedeemed' ? dshThemeColor.success : dshThemeColor.labelTertiary;
|
|
334
|
+
return createElement('div', { className: 'codingns4dsh-subscription-reset-overlay', role: 'presentation', style: resetDialogOverlayStyle }, createElement('div', {
|
|
335
|
+
ref: dialogRef,
|
|
336
|
+
role: 'dialog',
|
|
337
|
+
'aria-modal': true,
|
|
338
|
+
'aria-label': t('usage.resetDialogTitle'),
|
|
339
|
+
style: resetDialogStyle,
|
|
340
|
+
}, createElement('div', { style: { display: 'grid', gap: 4 } }, createElement('strong', { style: { fontSize: 14, lineHeight: 1.4 } }, t('usage.resetDialogTitle')), createElement('span', { style: { color: messageColor, fontSize: 12, lineHeight: '18px' } }, message)), createElement('div', { style: { display: 'flex', justifyContent: 'flex-end', gap: 8, paddingTop: 4 } }, finished
|
|
341
|
+
? createElement('button', { type: 'button', onClick: onClose, style: dshSettingsPrimaryButtonStyle }, t('usage.resetDialogClose'))
|
|
342
|
+
: createElement('button', { type: 'button', disabled: pending, onClick: onCancel, style: dshSettingsButtonStyle, autoFocus: true }, t('usage.resetDialogCancel')), !finished && createElement('button', { type: 'button', disabled: pending, onClick: onConfirm, style: dshSettingsPrimaryButtonStyle }, t('usage.resetDialogConfirm')))));
|
|
343
|
+
}
|
|
344
|
+
function resetOutcomeMessage(outcome, t) {
|
|
345
|
+
switch (outcome) {
|
|
346
|
+
case 'reset': return t('usage.resetOutcomeReset');
|
|
347
|
+
case 'alreadyRedeemed': return t('usage.resetOutcomeAlreadyRedeemed');
|
|
348
|
+
case 'nothingToReset': return t('usage.resetOutcomeNothingToReset');
|
|
349
|
+
case 'noCredit': return t('usage.resetOutcomeNoCredit');
|
|
350
|
+
}
|
|
182
351
|
}
|
|
183
352
|
/** 根据服务端返回的窗口时长生成准确的额度标签,避免把七天窗口误显示成五小时。 */
|
|
184
|
-
function formatSubscriptionWindowLabel(window, fallback) {
|
|
353
|
+
function formatSubscriptionWindowLabel(window, fallback, t) {
|
|
185
354
|
const durationMins = window?.windowDurationMins;
|
|
186
355
|
if (durationMins === null || durationMins === undefined || !Number.isFinite(durationMins) || durationMins <= 0)
|
|
187
356
|
return fallback;
|
|
188
357
|
if (durationMins % (24 * 60) === 0)
|
|
189
|
-
return
|
|
358
|
+
return t('usage.windowDays', { count: durationMins / (24 * 60) });
|
|
190
359
|
if (durationMins % 60 === 0)
|
|
191
|
-
return
|
|
192
|
-
return
|
|
360
|
+
return t('usage.windowHours', { count: durationMins / 60 });
|
|
361
|
+
return t('usage.windowMinutes', { count: durationMins });
|
|
193
362
|
}
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
363
|
+
/**
|
|
364
|
+
* New-API 的普通 Key 没有 Sub2API 那种统一的完整统计对象。
|
|
365
|
+
* 这里只投影读取器明确拿到的真实数值,隐藏内部 quota、Key 状态和占位文本,
|
|
366
|
+
* 并把日志返回的模型/日期汇总拆成短表格,避免一整串文本撑坏弹层。
|
|
367
|
+
*/
|
|
368
|
+
function NewApiPopover({ usage, providerName, t }) {
|
|
369
|
+
const labels = NEW_API_DETAIL_LABELS;
|
|
370
|
+
const details = usage.details.filter((item) => isNewApiDisplayValue(item.value));
|
|
371
|
+
const find = (...labels) => {
|
|
372
|
+
for (const label of labels) {
|
|
373
|
+
const item = details.find((candidate) => candidate.label === label);
|
|
374
|
+
if (item !== undefined)
|
|
375
|
+
return item.value;
|
|
376
|
+
}
|
|
377
|
+
return null;
|
|
378
|
+
};
|
|
379
|
+
const stats = [];
|
|
380
|
+
const remaining = resolveNewApiRemaining(usage, details);
|
|
381
|
+
if (remaining !== null)
|
|
382
|
+
stats.push({ label: t('usage.newApiBalance'), value: formatNewApiBalanceAmount(remaining, usage.unit) });
|
|
383
|
+
// Token 接口的 total_used 是内部 quota,即使 unit 写成 TOKENS 也不把它
|
|
384
|
+
// 当作真实 Token;只有日志明确聚合出的 Token 才能展示。
|
|
385
|
+
const todayTokens = find(labels.todayTokensLogs);
|
|
386
|
+
if (todayTokens !== null)
|
|
387
|
+
stats.push({ label: t('usage.statTodayTokens'), value: formatNewApiMetric(todayTokens, usage.unit, true) });
|
|
388
|
+
const totalTokens = find(labels.totalTokensLogs);
|
|
389
|
+
if (totalTokens !== null)
|
|
390
|
+
stats.push({ label: t('usage.statTotalTokens'), value: formatNewApiMetric(totalTokens, usage.unit, true) });
|
|
391
|
+
const feeUnit = resolveNewApiFeeUnit(usage, details, labels);
|
|
392
|
+
const todayCost = find(labels.todayCost);
|
|
393
|
+
if (todayCost !== null && feeUnit !== null)
|
|
394
|
+
stats.push({ label: t('usage.statTodayCost'), value: formatNewApiMetric(todayCost, feeUnit, false) });
|
|
395
|
+
const totalCost = find(labels.totalCost);
|
|
396
|
+
if (totalCost !== null && feeUnit !== null)
|
|
397
|
+
stats.push({ label: t('usage.statTotalCost'), value: formatNewApiMetric(totalCost, feeUnit, false) });
|
|
398
|
+
const cacheHitRate = find(labels.cacheHitRateLogs);
|
|
399
|
+
if (cacheHitRate !== null)
|
|
400
|
+
stats.push({ label: t('usage.statTotalCacheHitRate'), value: String(cacheHitRate) });
|
|
401
|
+
const models = parseNewApiStats(find(labels.modelsLogs));
|
|
402
|
+
const daily = parseNewApiStats(find(labels.dailyLogs));
|
|
403
|
+
const headline = formatNewApiHeadline(usage, details);
|
|
404
|
+
return createElement('div', { className: 'codingns4dsh-subscription-popover', role: 'dialog', 'aria-label': t('usage.upstreamUsageTitle', { provider: providerName }), style: subscriptionPopoverStyle }, createElement('div', { style: popoverHeadingStyle }, createElement('strong', undefined, t('usage.upstreamUsageTitle', { provider: providerName })), headline !== null && createElement('span', { style: { color: dshThemeColor.labelTertiary } }, headline)), stats.length > 0 && createElement('div', { style: sub2apiStatsGridStyle }, ...stats.map((stat) => createSub2ApiStat(stat.label, stat.value))), models.length > 0 && createNewApiStatsTable(t('usage.byModel'), models, t('usage.colModel'), t('usage.colRequests'), t('usage.colToken')), daily.length > 0 && createNewApiStatsTable(t('usage.byDay'), daily, t('usage.colDate'), t('usage.colRequests'), t('usage.colToken')));
|
|
405
|
+
}
|
|
406
|
+
const NEW_API_DETAIL_LABELS = {
|
|
407
|
+
todayTokensLogs: `${String.fromCodePoint(0x4eca, 0x65e5)} Token${String.fromCodePoint(0xff08, 0x6700, 0x8fd1, 0x65e5, 0x5fd7, 0xff09)}`,
|
|
408
|
+
totalTokensLogs: `${String.fromCodePoint(0x7d2f, 0x8ba1)} Token${String.fromCodePoint(0xff08, 0x6700, 0x8fd1, 0x65e5, 0x5fd7, 0xff09)}`,
|
|
409
|
+
todayCost: String.fromCodePoint(0x4eca, 0x65e5, 0x8d39, 0x7528),
|
|
410
|
+
totalCost: String.fromCodePoint(0x7d2f, 0x8ba1, 0x8d39, 0x7528),
|
|
411
|
+
cacheHitRateLogs: `${String.fromCodePoint(0x7f13, 0x5b58, 0x547d, 0x4e2d, 0x7387)}${String.fromCodePoint(0xff08, 0x6700, 0x8fd1, 0x65e5, 0x5fd7, 0xff09)}`,
|
|
412
|
+
modelsLogs: `${String.fromCodePoint(0x6309, 0x6a21, 0x578b, 0x7edf, 0x8ba1)}${String.fromCodePoint(0xff08, 0x6700, 0x8fd1, 0x65e5, 0x5fd7, 0xff09)}`,
|
|
413
|
+
dailyLogs: `${String.fromCodePoint(0x6309, 0x65e5, 0x7edf, 0x8ba1)}${String.fromCodePoint(0xff08, 0x6700, 0x8fd1, 0x65e5, 0x5fd7, 0xff09)}`,
|
|
414
|
+
remainingBalance: String.fromCodePoint(0x4f59, 0x989d, 0x2f, 0x5269, 0x4f59, 0x989d, 0x5ea6),
|
|
415
|
+
unavailable: String.fromCodePoint(0x4e0a, 0x6e38, 0x672a, 0x63d0, 0x4f9b),
|
|
416
|
+
unknownUnit: String.fromCodePoint(0x4e0a, 0x6e38, 0x5355, 0x4f4d, 0x672a, 0x660e, 0x786e),
|
|
417
|
+
upstreamUnit: String.fromCodePoint(0x4e0a, 0x6e38, 0x5355, 0x4f4d),
|
|
418
|
+
delimiter: String.fromCodePoint(0xff1b),
|
|
419
|
+
};
|
|
420
|
+
function resolveNewApiFeeUnit(usage, details, labels) {
|
|
421
|
+
if (usage.currency?.trim().toUpperCase() === 'USD')
|
|
422
|
+
return 'USD';
|
|
423
|
+
const declared = details.find((item) => item.label === labels.upstreamUnit);
|
|
424
|
+
return typeof declared?.value === 'string' && declared.value.trim().toUpperCase() === 'USD' ? 'USD' : null;
|
|
425
|
+
}
|
|
426
|
+
function isNewApiDisplayValue(value) {
|
|
427
|
+
if (typeof value === 'number')
|
|
428
|
+
return Number.isFinite(value);
|
|
429
|
+
const normalized = value.trim();
|
|
430
|
+
return normalized !== '' && normalized !== '--' && normalized !== NEW_API_DETAIL_LABELS.unavailable && normalized !== NEW_API_DETAIL_LABELS.unknownUnit;
|
|
198
431
|
}
|
|
199
|
-
function
|
|
200
|
-
|
|
432
|
+
function formatNewApiMetric(value, unit, token) {
|
|
433
|
+
const numeric = typeof value === 'number' ? value : Number(value);
|
|
434
|
+
if (!Number.isFinite(numeric))
|
|
435
|
+
return String(value);
|
|
436
|
+
if (token)
|
|
437
|
+
return formatCompactTokenCount(numeric);
|
|
438
|
+
return formatProviderBalanceAmount(numeric, unit);
|
|
201
439
|
}
|
|
202
|
-
function
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
440
|
+
function formatNewApiHeadline(usage, details = usage.details) {
|
|
441
|
+
// New-API 可能同时返回 unlimited_quota=true 与明确的 remaining。这里只
|
|
442
|
+
// 显示明确余额;令牌额度标记不是账户余额,不能投影成“无限额度”。
|
|
443
|
+
const remaining = resolveNewApiRemaining(usage, details);
|
|
444
|
+
if (remaining !== null && Number.isFinite(remaining))
|
|
445
|
+
return formatNewApiBalanceValue(remaining, usage.unit);
|
|
446
|
+
return null;
|
|
447
|
+
}
|
|
448
|
+
function resolveNewApiRemaining(usage, details) {
|
|
449
|
+
if (usage.remaining !== null && Number.isFinite(usage.remaining))
|
|
450
|
+
return usage.remaining;
|
|
451
|
+
const detail = details.find((item) => item.label === NEW_API_DETAIL_LABELS.remainingBalance);
|
|
452
|
+
return typeof detail?.value === 'number' && Number.isFinite(detail.value) ? detail.value : null;
|
|
453
|
+
}
|
|
454
|
+
function formatNewApiBalanceValue(value, unit) {
|
|
455
|
+
const normalized = unit?.trim().toUpperCase() ?? '';
|
|
456
|
+
if (normalized === '')
|
|
457
|
+
return formatNewApiDecimal(value);
|
|
458
|
+
if (normalized !== 'USD')
|
|
459
|
+
return formatProviderBalanceValue(value, unit);
|
|
460
|
+
return `$${formatNewApiDecimal(value)}`;
|
|
461
|
+
}
|
|
462
|
+
function formatNewApiBalanceAmount(value, unit) {
|
|
463
|
+
const normalized = unit?.trim().toUpperCase() ?? '';
|
|
464
|
+
if (normalized === '')
|
|
465
|
+
return formatNewApiDecimal(value);
|
|
466
|
+
if (normalized !== 'USD')
|
|
467
|
+
return formatProviderBalanceAmount(value, unit);
|
|
468
|
+
return `$${formatNewApiDecimal(value)}`;
|
|
469
|
+
}
|
|
470
|
+
function formatNewApiDecimal(value) {
|
|
471
|
+
if (!Number.isFinite(value))
|
|
472
|
+
return '--';
|
|
473
|
+
if (value === 0)
|
|
474
|
+
return '0.00';
|
|
475
|
+
if (Math.abs(value) >= 0.01)
|
|
476
|
+
return value.toFixed(2);
|
|
477
|
+
const precision = 6;
|
|
478
|
+
return value.toFixed(precision).replace(/0+$/u, '').replace(/\.$/u, '');
|
|
479
|
+
}
|
|
480
|
+
function parseNewApiStats(value) {
|
|
481
|
+
if (typeof value !== 'string')
|
|
482
|
+
return [];
|
|
483
|
+
return value.split(NEW_API_DETAIL_LABELS.delimiter).flatMap((part) => {
|
|
484
|
+
const match = /^\s*(.+?):\s*([\d,.]+(?:[KMB])?)\s*Token\s*\/\s*([\d,]+)\s*次\s*$/u.exec(part);
|
|
485
|
+
if (match === null)
|
|
486
|
+
return [];
|
|
487
|
+
return [{ name: match[1].trim(), tokens: match[2], requests: match[3] }];
|
|
488
|
+
});
|
|
489
|
+
}
|
|
490
|
+
function createNewApiStatsTable(title, rows, nameLabel, requestsLabel, tokensLabel) {
|
|
491
|
+
return createElement('section', { style: sub2apiSectionStyle }, createElement('strong', { style: sub2apiSectionTitleStyle }, title), createElement('div', { style: sub2apiTableScrollStyle }, createElement('table', { style: sub2apiTableStyle }, createElement('thead', undefined, createElement('tr', undefined, createElement('th', { style: sub2apiThStyle }, nameLabel), createElement('th', { style: sub2apiThStyle }, requestsLabel), createElement('th', { style: sub2apiThStyle }, tokensLabel))), createElement('tbody', undefined, ...rows.map((row) => createElement('tr', { key: `${row.name}-${row.requests}` }, createElement('td', { style: sub2apiTdStyle }, row.name), createElement('td', { style: sub2apiTdStyle }, row.requests), createElement('td', { style: sub2apiTdStyle }, row.tokens)))))));
|
|
492
|
+
}
|
|
493
|
+
function ProviderBalancePopover({ usage, providerName, t, nowMs }) {
|
|
494
|
+
const models = summarizeProviderBalance(usage);
|
|
495
|
+
const overallPercent = balancePercent(usage.remaining, usage.total);
|
|
496
|
+
const details = usage.details.filter((item) => !isProviderModelDetail(item.label));
|
|
497
|
+
return createElement('div', { className: 'codingns4dsh-subscription-popover', role: 'dialog', 'aria-label': t('usage.officialRemainingPopover', { provider: providerName }), style: subscriptionPopoverStyle }, createElement('div', { style: popoverHeadingStyle }, createElement('span', { style: providerBalanceHeadingStyle }, createElement('strong', undefined, providerName), usage.planName?.trim() && createElement('span', { style: providerBalancePlanStyle }, usage.planName.trim())), createElement('span', { style: { color: dshThemeColor.labelTertiary } }, formatProviderBalance(usage, t('usage.upstreamNotProvided')))), overallPercent !== null && usage.remaining !== null && usage.total !== null && createElement(BalanceProgress, {
|
|
498
|
+
label: t('usage.officialRemainingPopover', { provider: providerName }),
|
|
499
|
+
percent: overallPercent,
|
|
500
|
+
value: `${formatProviderBalanceAmount(usage.remaining, usage.unit)} / ${formatProviderBalanceAmount(usage.total, usage.unit)}`,
|
|
501
|
+
style: overallBalanceStyle,
|
|
502
|
+
}), usage.used !== null && createElement('div', { style: balanceMetaStyle }, t('usage.usedShort', { amount: formatProviderBalanceAmount(usage.used, usage.unit) })), createElement('section', { style: providerDetailsSectionStyle }, createElement('strong', { style: providerBalanceSectionTitleStyle }, t('usage.providerDetails')), details.length === 0
|
|
503
|
+
? createElement('div', { style: resetStyle }, t('usage.upstreamNotProvided'))
|
|
504
|
+
: details.map((item, index) => createElement('div', { key: `${item.label}-${index}`, style: providerDetailRowStyle }, createElement('span', undefined, item.label), createElement('span', { style: providerDetailValueStyle }, formatProviderDetailValue(item.value, t))))), models.length === 0
|
|
505
|
+
? createElement('div', { style: resetStyle }, t('usage.noMoreStats'))
|
|
506
|
+
: models.map((model) => createElement('section', { key: model.name, style: providerBalanceModelStyle }, createElement('div', { style: windowHeadingStyle }, createElement('span', undefined, model.name), createElement('span', undefined, model.total === null ? formatProviderBalanceAmount(model.remaining ?? 0, usage.unit) : `${formatProviderBalanceAmount(model.remaining ?? 0, usage.unit)} / ${formatProviderBalanceAmount(model.total, usage.unit)}`)), model.total !== null && model.remaining !== null && createElement(BalanceProgress, {
|
|
507
|
+
label: model.name,
|
|
508
|
+
percent: balancePercent(model.remaining, model.total) ?? 0,
|
|
509
|
+
value: '',
|
|
510
|
+
}), createElement('div', { style: balanceMetaStyle }, model.used === null ? null : createElement('span', undefined, t('usage.usedShort', { amount: formatProviderBalanceAmount(model.used, usage.unit) })), model.periodEnd === null ? null : createElement('span', undefined, t('usage.expiresIn', { time: formatExpiryCountdown(model.periodEnd, t, nowMs) }))))));
|
|
511
|
+
}
|
|
512
|
+
function BalanceProgress({ label, percent, value, style }) {
|
|
513
|
+
const normalized = Math.max(0, Math.min(100, percent));
|
|
514
|
+
return createElement('div', { style: style ?? providerBalanceProgressStyle }, createElement('div', { style: balanceProgressHeaderStyle }, createElement('span', { style: visuallyHiddenStyle }, label), value !== '' && createElement('span', { style: balanceProgressValueStyle }, value), createElement('span', { style: balanceProgressPercentStyle }, `${Math.round(normalized)}%`)), createElement('div', { role: 'progressbar', 'aria-label': label, 'aria-valuemin': 0, 'aria-valuemax': 100, 'aria-valuenow': normalized, style: providerBalanceBarStyle }, createElement('span', { style: { ...providerBalanceBarFillStyle, width: `${normalized}%` } })));
|
|
515
|
+
}
|
|
516
|
+
function summarizeProviderBalance(usage) {
|
|
517
|
+
const models = new Map();
|
|
518
|
+
for (const item of usage.details) {
|
|
519
|
+
const label = item.label.trim();
|
|
520
|
+
const matched = PROVIDER_DETAIL_SUFFIXES.find(({ suffix }) => label.endsWith(` ${suffix}`));
|
|
521
|
+
if (matched === undefined)
|
|
522
|
+
continue;
|
|
523
|
+
const name = label.slice(0, -(matched.suffix.length + 1)).trim();
|
|
524
|
+
if (name === '')
|
|
525
|
+
continue;
|
|
526
|
+
const model = models.get(name) ?? { name, remaining: null, used: null, total: null, periodEnd: null };
|
|
527
|
+
if (matched.kind === 'remaining')
|
|
528
|
+
model.remaining = typeof item.value === 'number' ? item.value : null;
|
|
529
|
+
else if (matched.kind === 'used')
|
|
530
|
+
model.used = typeof item.value === 'number' ? item.value : null;
|
|
531
|
+
else if (matched.kind === 'total')
|
|
532
|
+
model.total = typeof item.value === 'number' ? item.value : null;
|
|
533
|
+
else
|
|
534
|
+
model.periodEnd = typeof item.value === 'string' ? item.value : null;
|
|
535
|
+
models.set(name, model);
|
|
536
|
+
}
|
|
537
|
+
return [...models.values()];
|
|
538
|
+
}
|
|
539
|
+
function isProviderModelDetail(label) {
|
|
540
|
+
const normalized = label.trim();
|
|
541
|
+
return PROVIDER_DETAIL_SUFFIXES.some(({ suffix }) => normalized.endsWith(` ${suffix}`));
|
|
542
|
+
}
|
|
543
|
+
function formatProviderDetailValue(value, t) {
|
|
544
|
+
if (typeof value === 'number')
|
|
545
|
+
return Number.isFinite(value) ? String(value) : t('usage.upstreamNotProvided');
|
|
546
|
+
const normalized = value.trim();
|
|
547
|
+
return normalized === '' || normalized === '--' ? t('usage.upstreamNotProvided') : normalized;
|
|
548
|
+
}
|
|
549
|
+
const PROVIDER_DETAIL_SUFFIXES = [
|
|
550
|
+
{ suffix: String.fromCodePoint(0x5269, 0x4f59), kind: 'remaining' },
|
|
551
|
+
{ suffix: String.fromCodePoint(0x5df2, 0x7528), kind: 'used' },
|
|
552
|
+
{ suffix: String.fromCodePoint(0x603b, 0x91cf), kind: 'total' },
|
|
553
|
+
{ suffix: String.fromCodePoint(0x5468, 0x671f, 0x7ed3, 0x675f), kind: 'periodEnd' },
|
|
554
|
+
{ suffix: 'remaining', kind: 'remaining' },
|
|
555
|
+
{ suffix: 'used', kind: 'used' },
|
|
556
|
+
{ suffix: 'total', kind: 'total' },
|
|
557
|
+
{ suffix: 'period end', kind: 'periodEnd' },
|
|
558
|
+
];
|
|
559
|
+
function balancePercent(remaining, total) {
|
|
560
|
+
if (remaining === null || total === null || !Number.isFinite(remaining) || !Number.isFinite(total) || total <= 0)
|
|
561
|
+
return null;
|
|
562
|
+
return Math.max(0, Math.min(100, remaining / total * 100));
|
|
563
|
+
}
|
|
564
|
+
function DeepseekPopover({ usage, providerName, t }) {
|
|
565
|
+
return createElement('div', { className: 'codingns4dsh-subscription-popover', role: 'dialog', 'aria-label': t('usage.providerAccountBalance', { provider: providerName }), style: subscriptionPopoverStyle }, createElement('div', { style: popoverHeadingStyle }, createElement('strong', undefined, t('usage.providerAccountBalance', { provider: providerName })), createElement('span', { style: { color: usage.isAvailable === false ? dshThemeColor.error : dshThemeColor.labelTertiary } }, usage.isAvailable === false ? t('usage.unavailable') : t('usage.available'))), usage.balances.map((balance) => createElement('section', { key: balance.currency, style: deepseekBalanceSectionStyle }, createElement('div', { style: windowHeadingStyle }, createElement('span', undefined, balance.currency), createElement('strong', undefined, formatDeepseekMoney(balance.totalBalance, balance.currency))), createElement('div', { style: deepseekBalanceDetailsStyle }, createElement('span', undefined, t('usage.granted', { amount: formatDeepseekMoney(balance.grantedBalance, balance.currency) })), createElement('span', undefined, t('usage.toppedUp', { amount: formatDeepseekMoney(balance.toppedUpBalance, balance.currency) }))))), createElement('div', { style: deepseekUnavailableStatsStyle }, t('usage.deepseekApiNote')));
|
|
566
|
+
}
|
|
567
|
+
function Sub2ApiPopover({ usage, providerName, t }) {
|
|
568
|
+
return createElement('div', { className: 'codingns4dsh-subscription-popover', role: 'dialog', 'aria-label': t('usage.upstreamUsageTitle', { provider: providerName }), style: subscriptionPopoverStyle }, createElement('div', { style: popoverHeadingStyle }, createElement('strong', undefined, t('usage.upstreamUsageTitle', { provider: providerName })), createElement('span', { style: { color: dshThemeColor.labelTertiary } }, formatSub2ApiMoney(usage.balance, usage.unit))), createElement('div', { style: upstreamMetaStyle }, createElement('span', { style: upstreamTypeStyle }, usage.upstreamType), usage.upstreamUrl === ''
|
|
569
|
+
? createElement('span', { style: upstreamMutedStyle }, t('usage.addressMissing'))
|
|
570
|
+
: createElement('a', { href: usage.upstreamUrl, target: '_blank', rel: 'noreferrer', title: usage.upstreamUrl, style: upstreamLinkStyle }, usage.upstreamUrl)), createElement('div', { style: sub2apiStatsGridStyle }, createSub2ApiStat(t('usage.statTodayRequests'), formatInteger(usage.today.requests)), createSub2ApiStat(t('usage.statTodayTokens'), formatSub2ApiTokens(usage.today.totalTokens)), createSub2ApiStat(t('usage.statTodayCost'), formatSub2ApiMoney(usage.today.cost, usage.unit)), createSub2ApiStat(t('usage.statTotalRequests'), formatInteger(usage.total.requests)), createSub2ApiStat(t('usage.statTotalTokens'), formatSub2ApiTokens(usage.total.totalTokens)), createSub2ApiStat(t('usage.statTotalCost'), formatSub2ApiMoney(usage.total.cost, usage.unit)), createSub2ApiStat(t('usage.statTodayCacheHitRate'), formatSub2ApiPercent(usage.today.cacheHitRate)), createSub2ApiStat(t('usage.statTotalCacheHitRate'), formatSub2ApiPercent(usage.total.cacheHitRate))), createElement('section', { style: sub2apiSectionStyle }, createElement('strong', { style: sub2apiSectionTitleStyle }, t('usage.byModel')), usage.models.length === 0
|
|
571
|
+
? createElement('div', { style: resetStyle }, t('usage.noModelStats'))
|
|
572
|
+
: createElement('div', { style: sub2apiTableScrollStyle }, createElement('table', { style: sub2apiTableStyle }, createElement('thead', undefined, createElement('tr', undefined, createElement('th', { style: sub2apiThStyle }, t('usage.colModel')), createElement('th', { style: sub2apiThStyle }, t('usage.colRequests')), createElement('th', { style: sub2apiThStyle }, t('usage.colToken')), createElement('th', { style: sub2apiThStyle }, t('usage.colCost')), createElement('th', { style: sub2apiThStyle }, t('usage.colCache')))), createElement('tbody', undefined, ...usage.models.map((model) => createModelRow(model, usage.unit)))))));
|
|
208
573
|
}
|
|
209
574
|
function createSub2ApiStat(label, value) {
|
|
210
575
|
return createElement('div', { style: sub2apiStatStyle }, createElement('span', { style: sub2apiStatLabelStyle }, label), createElement('strong', undefined, value));
|
|
@@ -218,22 +583,23 @@ function resolveDisplayWindow(usage) {
|
|
|
218
583
|
function selectDeepseekBalance(usage) {
|
|
219
584
|
return usage.balances.find((balance) => balance.currency.toUpperCase() === 'USD') ?? usage.balances[0] ?? null;
|
|
220
585
|
}
|
|
586
|
+
/** 已具备用量读取契约的适配器才挂载底部订阅入口。 */
|
|
221
587
|
function isSubscriptionAdapter(adapterId) {
|
|
222
|
-
return adapterId === 'command-code' || adapterId === 'codex' || adapterId === 'claude-code' || adapterId === 'dsh' || adapterId === 'grok' || adapterId === 'kimi' || adapterId === 'opencode';
|
|
588
|
+
return adapterId === 'command-code' || adapterId === 'codex' || adapterId === 'claude-code' || adapterId === 'codebuddy' || adapterId === 'codebuddy-cn' || adapterId === 'dsh' || adapterId === 'grok' || adapterId === 'kimi' || adapterId === 'opencode' || adapterId === 'workbuddy' || adapterId === 'zcode';
|
|
223
589
|
}
|
|
224
590
|
function isRemoteWebContext() {
|
|
225
591
|
return globalThis.__CODINGNS4DSH_REMOTE_WEB_CONTEXT__ === true;
|
|
226
592
|
}
|
|
227
|
-
function subscriptionProviderName(adapterId, providerId, usage) {
|
|
593
|
+
function subscriptionProviderName(adapterId, providerId, usage, t) {
|
|
228
594
|
if (usage.provider?.displayName)
|
|
229
595
|
return usage.provider.displayName;
|
|
230
596
|
if (adapterId === 'dsh' && providerId !== null) {
|
|
231
597
|
if (/^(?:deepseek(?:-official)?|official-deepseek)$/iu.test(providerId))
|
|
232
|
-
return '
|
|
598
|
+
return t('usage.providerDeepseekOfficial');
|
|
233
599
|
return formatProviderName(providerId);
|
|
234
600
|
}
|
|
235
601
|
if (adapterId === 'dsh' && usage.sub2api !== undefined)
|
|
236
|
-
return
|
|
602
|
+
return t('usage.providerUpstream', { name: usage.sub2api.upstreamType });
|
|
237
603
|
switch (adapterId) {
|
|
238
604
|
case 'command-code': return 'Command Code';
|
|
239
605
|
case 'codex': return 'Codex';
|
|
@@ -242,6 +608,10 @@ function subscriptionProviderName(adapterId, providerId, usage) {
|
|
|
242
608
|
case 'grok': return 'Grok';
|
|
243
609
|
case 'kimi': return 'Kimi Code';
|
|
244
610
|
case 'opencode': return 'OpenCode';
|
|
611
|
+
case 'zcode': return 'ZCode';
|
|
612
|
+
case 'codebuddy': return 'CodeBuddy';
|
|
613
|
+
case 'codebuddy-cn': return 'CodeBuddy';
|
|
614
|
+
case 'workbuddy': return 'WorkBuddy';
|
|
245
615
|
default: return 'Agent';
|
|
246
616
|
}
|
|
247
617
|
}
|
|
@@ -265,24 +635,51 @@ function formatDeepseekMoney(value, currency) {
|
|
|
265
635
|
return `¥${amount}`;
|
|
266
636
|
return `${amount} ${normalizedCurrency}`;
|
|
267
637
|
}
|
|
268
|
-
function formatProviderBalance(usage) {
|
|
638
|
+
function formatProviderBalance(usage, unavailable = '--') {
|
|
269
639
|
if (usage === undefined || usage.remaining === null)
|
|
270
|
-
return
|
|
640
|
+
return unavailable;
|
|
271
641
|
return formatProviderBalanceValue(usage.remaining, usage.unit);
|
|
272
642
|
}
|
|
273
643
|
function formatProviderBalanceValue(value, unit) {
|
|
644
|
+
const normalized = unit?.trim().toUpperCase() ?? '';
|
|
645
|
+
const amount = formatProviderBalanceAmount(value, unit);
|
|
646
|
+
if (normalized === '%' || normalized === 'USD')
|
|
647
|
+
return amount;
|
|
648
|
+
return `${amount}${normalized === '' ? '' : ` ${normalized}`}`;
|
|
649
|
+
}
|
|
650
|
+
function formatProviderBalanceAmount(value, unit) {
|
|
274
651
|
const normalized = unit?.trim().toUpperCase() ?? '';
|
|
275
652
|
if (normalized === '%')
|
|
276
653
|
return `${value.toFixed(0)}%`;
|
|
654
|
+
// 小于 0.01 的非零余额不能被固定两位小数舍成 $0.00;复用
|
|
655
|
+
// New-API 的金额格式化规则,正常金额保留两位,小额保留非零有效位。
|
|
277
656
|
if (normalized === 'USD')
|
|
278
|
-
return `$${value
|
|
279
|
-
return
|
|
657
|
+
return `$${formatNewApiDecimal(value)}`;
|
|
658
|
+
return isTokenUnit(normalized) ? formatCompactTokenCount(value) : value.toFixed(2);
|
|
280
659
|
}
|
|
281
|
-
function formatSub2ApiTokens(value) { return
|
|
660
|
+
function formatSub2ApiTokens(value) { return formatCompactTokenCount(value); }
|
|
661
|
+
function formatCompactTokenCount(value) {
|
|
662
|
+
if (!Number.isFinite(value))
|
|
663
|
+
return '--';
|
|
664
|
+
const absolute = Math.abs(value);
|
|
665
|
+
const format = (divisor, suffix) => {
|
|
666
|
+
const amount = value / divisor;
|
|
667
|
+
const rounded = Math.round(amount * 10) / 10;
|
|
668
|
+
return `${Number.isInteger(rounded) ? rounded.toFixed(0) : rounded.toFixed(1)}${suffix}`;
|
|
669
|
+
};
|
|
670
|
+
if (absolute >= 1_000_000_000)
|
|
671
|
+
return format(1_000_000_000, 'B');
|
|
672
|
+
if (absolute >= 1_000_000)
|
|
673
|
+
return format(1_000_000, 'M');
|
|
674
|
+
if (absolute >= 1_000)
|
|
675
|
+
return format(1_000, 'K');
|
|
676
|
+
return String(Math.round(value));
|
|
677
|
+
}
|
|
678
|
+
function isTokenUnit(unit) { return /^(?:TOKENS?|TOKEN_COUNT)$/u.test(unit); }
|
|
282
679
|
function formatSub2ApiPercent(value) { return `${Math.max(0, Math.min(100, value)).toFixed(1)}%`; }
|
|
283
680
|
function formatInteger(value) { return new Intl.NumberFormat('zh-CN').format(Math.max(0, Math.round(value))); }
|
|
284
681
|
function formatPlanType(value) { return value.replace(/^individual-/u, '').replace(/(^|-)([a-z])/gu, (_match, _separator, letter) => ` ${letter.toUpperCase()}`).trim(); }
|
|
285
|
-
function formatCountdown(timestampSeconds, nowMs = Date.now()) {
|
|
682
|
+
function formatCountdown(timestampSeconds, t, nowMs = Date.now()) {
|
|
286
683
|
if (timestampSeconds === null)
|
|
287
684
|
return null;
|
|
288
685
|
const minutes = Math.max(0, Math.ceil((timestampSeconds * 1000 - nowMs) / 60_000));
|
|
@@ -290,10 +687,28 @@ function formatCountdown(timestampSeconds, nowMs = Date.now()) {
|
|
|
290
687
|
const hours = Math.floor((minutes % 1440) / 60);
|
|
291
688
|
const remainder = minutes % 60;
|
|
292
689
|
if (days > 0)
|
|
293
|
-
return
|
|
690
|
+
return t('usage.countdownDaysHours', { days, hours });
|
|
294
691
|
if (hours > 0)
|
|
295
|
-
return
|
|
296
|
-
return
|
|
692
|
+
return remainder > 0 ? t('usage.countdownHoursMinutes', { hours, minutes: remainder }) : t('usage.countdownHours', { hours });
|
|
693
|
+
return t('usage.countdownMinutes', { minutes: remainder });
|
|
694
|
+
}
|
|
695
|
+
function formatExpiryCountdown(value, t, nowMs) {
|
|
696
|
+
const timestamp = Date.parse(value);
|
|
697
|
+
if (Number.isNaN(timestamp))
|
|
698
|
+
return value;
|
|
699
|
+
if (timestamp <= nowMs)
|
|
700
|
+
return t('usage.expired');
|
|
701
|
+
return formatCountdown(timestamp / 1000, t, nowMs) ?? t('usage.expired');
|
|
702
|
+
}
|
|
703
|
+
function formatResetExpiry(expiry, t, nowMs) {
|
|
704
|
+
if (expiry * 1000 <= nowMs)
|
|
705
|
+
return t('usage.resetCreditsExpired');
|
|
706
|
+
return formatCountdown(expiry, t, nowMs) ?? t('usage.resetCreditsExpired');
|
|
707
|
+
}
|
|
708
|
+
/** 点数余额保留两位小数展示;无法解析时原样保留上游字符串。 */
|
|
709
|
+
function formatCreditBalance(value) {
|
|
710
|
+
const numeric = Number(value);
|
|
711
|
+
return Number.isFinite(numeric) ? numeric.toFixed(2) : value;
|
|
297
712
|
}
|
|
298
713
|
const subscriptionRootStyle = { position: 'relative', minWidth: 0, display: 'inline-flex', alignItems: 'center' };
|
|
299
714
|
const subscriptionTriggerStyle = { display: 'inline-flex', alignItems: 'center', gap: 6, height: 28, border: 0, borderRadius: 14, padding: '0 8px 0 4px', color: dshThemeColor.labelSecondary, background: 'transparent', cursor: 'pointer', fontSize: 13, lineHeight: '20px' };
|
|
@@ -303,8 +718,24 @@ const sub2apiLogoStyle = { display: 'block', borderRadius: 4, objectFit: 'contai
|
|
|
303
718
|
const deepseekBalanceIdentityStyle = { display: 'inline-flex', alignItems: 'center', gap: 5, whiteSpace: 'nowrap', fontVariantNumeric: 'tabular-nums' };
|
|
304
719
|
const deepseekLogoStyle = { display: 'block', borderRadius: 5, objectFit: 'contain' };
|
|
305
720
|
const deepseekBalanceStyle = { display: 'inline-flex', alignItems: 'center', color: dshThemeColor.labelSecondary, fontSize: 13, fontWeight: 600, fontVariantNumeric: 'tabular-nums' };
|
|
721
|
+
const providerBalanceHeadingStyle = { display: 'grid', gap: 2, minWidth: 0 };
|
|
722
|
+
const providerBalancePlanStyle = { color: dshThemeColor.labelTertiary, fontSize: 11, fontWeight: 500, overflow: 'hidden', textOverflow: 'ellipsis', whiteSpace: 'nowrap' };
|
|
306
723
|
const deepseekBalanceSectionStyle = { display: 'grid', gap: 6, marginTop: 10, padding: '10px 0 2px', borderTop: `1px solid ${dshThemeColor.border}` };
|
|
307
724
|
const deepseekBalanceDetailsStyle = { display: 'flex', justifyContent: 'space-between', gap: 12, color: dshThemeColor.labelTertiary, fontSize: 12 };
|
|
725
|
+
const overallBalanceStyle = { display: 'grid', gap: 5, marginTop: 10 };
|
|
726
|
+
const providerDetailsSectionStyle = { display: 'grid', gap: 6, marginTop: 12, paddingTop: 10, borderTop: `1px solid ${dshThemeColor.border}` };
|
|
727
|
+
const providerBalanceSectionTitleStyle = { fontSize: 12, color: dshThemeColor.labelSecondary };
|
|
728
|
+
const providerDetailRowStyle = { display: 'flex', justifyContent: 'space-between', gap: 12, color: dshThemeColor.labelTertiary, fontSize: 12, lineHeight: '17px' };
|
|
729
|
+
const providerDetailValueStyle = { color: dshThemeColor.labelSecondary, textAlign: 'right', overflowWrap: 'anywhere' };
|
|
730
|
+
const providerBalanceModelStyle = { display: 'grid', gap: 6, marginTop: 12, paddingTop: 10, borderTop: `1px solid ${dshThemeColor.border}` };
|
|
731
|
+
const providerBalanceProgressStyle = { display: 'grid', gap: 5, marginTop: 10 };
|
|
732
|
+
const balanceProgressHeaderStyle = { display: 'flex', justifyContent: 'space-between', gap: 8, minWidth: 0, color: dshThemeColor.labelTertiary, fontSize: 11, fontVariantNumeric: 'tabular-nums' };
|
|
733
|
+
const balanceProgressValueStyle = { color: dshThemeColor.labelSecondary, fontWeight: 600 };
|
|
734
|
+
const balanceProgressPercentStyle = { color: dshThemeColor.labelTertiary, fontVariantNumeric: 'tabular-nums' };
|
|
735
|
+
const balanceMetaStyle = { display: 'flex', justifyContent: 'space-between', gap: 12, color: dshThemeColor.labelTertiary, fontSize: 11, lineHeight: '16px', fontVariantNumeric: 'tabular-nums' };
|
|
736
|
+
const visuallyHiddenStyle = { position: 'absolute', width: 1, height: 1, padding: 0, margin: -1, overflow: 'hidden', clip: 'rect(0, 0, 0, 0)', whiteSpace: 'nowrap', border: 0 };
|
|
737
|
+
const providerBalanceBarStyle = { height: 7, overflow: 'hidden', borderRadius: 4, background: dshThemeColor.border };
|
|
738
|
+
const providerBalanceBarFillStyle = { display: 'block', height: '100%', borderRadius: 4, background: dshThemeColor.accent, transition: 'width .2s ease' };
|
|
308
739
|
const deepseekUnavailableStatsStyle = { marginTop: 12, paddingTop: 10, borderTop: `1px solid ${dshThemeColor.border}`, color: dshThemeColor.labelTertiary, fontSize: 12, lineHeight: '17px' };
|
|
309
740
|
const progressRingVisualStyle = { boxSizing: 'border-box', width: '100%', height: '100%', display: 'inline-flex', alignItems: 'center', justifyContent: 'center', padding: 2, borderRadius: 'inherit' };
|
|
310
741
|
const progressRingValueStyle = { boxSizing: 'border-box', width: '100%', height: '100%', display: 'inline-flex', alignItems: 'center', justifyContent: 'center', gap: 0.5, borderRadius: 'inherit', background: dshThemeColor.menuBackground, fontSize: 7, lineHeight: 1, fontWeight: 700, color: dshThemeColor.labelPrimary, whiteSpace: 'nowrap' };
|
|
@@ -320,6 +751,13 @@ const barStyle = { height: 7, overflow: 'hidden', borderRadius: 4, background: d
|
|
|
320
751
|
const barFillStyle = { display: 'block', height: '100%', borderRadius: 4, background: dshThemeColor.accent, transition: 'width .2s ease' };
|
|
321
752
|
const resetStyle = { color: dshThemeColor.labelTertiary, fontSize: 12 };
|
|
322
753
|
const subscriptionPopoverStyle = { ...dshPopupSurfaceStyle, position: 'absolute', zIndex: 1200, bottom: 'calc(100% + 8px)', left: 0, width: 'max-content', minWidth: 280, maxWidth: 'min(400px, calc(100vw - 24px))', boxSizing: 'border-box', padding: 14, borderRadius: 12 };
|
|
754
|
+
const resetCreditsSectionStyle = { display: 'grid', gap: 6, marginTop: 10, padding: '10px 12px', border: `1px solid ${dshThemeColor.border}`, borderRadius: 10, background: dshThemeColor.surfaceSubtle };
|
|
755
|
+
const resetCreditsRowStyle = { display: 'flex', alignItems: 'center', justifyContent: 'space-between', gap: 12, color: dshThemeColor.labelSecondary, fontSize: 13 };
|
|
756
|
+
const resetCreditsValueGroupStyle = { display: 'inline-flex', alignItems: 'center', gap: 8 };
|
|
757
|
+
const resetCreditsValueStyle = { color: dshThemeColor.labelPrimary, fontWeight: 600, fontVariantNumeric: 'tabular-nums' };
|
|
758
|
+
const resetCreditsExpiryStyle = { color: dshThemeColor.labelTertiary, fontSize: 11, lineHeight: '16px', fontVariantNumeric: 'tabular-nums' };
|
|
759
|
+
const resetDialogOverlayStyle = { position: 'fixed', inset: 0, zIndex: 1400, display: 'flex', alignItems: 'center', justifyContent: 'center', padding: 20, boxSizing: 'border-box', background: dshThemeColor.overlay };
|
|
760
|
+
const resetDialogStyle = { ...dshPopupSurfaceStyle, width: 'min(100%, 420px)', boxSizing: 'border-box', padding: 16, borderRadius: 12, display: 'grid', gap: 12 };
|
|
323
761
|
const sub2apiStatsGridStyle = { display: 'grid', gridTemplateColumns: 'repeat(2, minmax(0, 1fr))', gap: 8, paddingTop: 12 };
|
|
324
762
|
const sub2apiStatStyle = { display: 'grid', gap: 2, minWidth: 0 };
|
|
325
763
|
const sub2apiStatLabelStyle = { color: dshThemeColor.labelTertiary, fontSize: 11 };
|
|
@@ -331,6 +769,9 @@ const sub2apiThStyle = { padding: '4px 5px', textAlign: 'left', color: dshThemeC
|
|
|
331
769
|
const sub2apiTdStyle = { padding: '5px', borderTop: `1px solid ${dshThemeColor.border}`, color: dshThemeColor.labelSecondary, overflowWrap: 'anywhere' };
|
|
332
770
|
function progressRingStyle() { return { position: 'relative', display: 'inline-flex', flex: '0 0 28px', width: 28, height: 28, alignItems: 'center', justifyContent: 'center', borderRadius: '50%', padding: 0, border: 0, boxShadow: `inset 0 0 0 1px ${dshThemeColor.border}`, background: 'transparent' }; }
|
|
333
771
|
function progressRingVisualBackground(progress, loading) { return loading ? dshThemeColor.border : `conic-gradient(${dshThemeColor.accent} ${Math.max(0, Math.min(1, progress)) * 360}deg, ${dshThemeColor.border} 0deg)`; }
|
|
772
|
+
function createRemainingRing(percent) {
|
|
773
|
+
return createElement('span', { 'aria-hidden': true, style: progressRingStyle() }, createElement('span', { style: { ...progressRingVisualStyle, background: progressRingVisualBackground(percent / 100, false) } }, createElement('span', { style: progressRingValueStyle }, createElement('span', undefined, formatRingPercentage(percent)), createElement('span', { style: progressRingSuffixStyle }, '%'))));
|
|
774
|
+
}
|
|
334
775
|
export { CommandCodeSubscriptionSlot };
|
|
335
776
|
export const registerCommandCodeSubscriptionSlot = registerSubscriptionSlot;
|
|
336
777
|
//# sourceMappingURL=subscription-slot.js.map
|