@prestyj/core 5.7.0 → 5.9.0
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/dist/{chunk-RQADK6HE.js → chunk-JXPW4JKV.js} +482 -288
- package/dist/chunk-JXPW4JKV.js.map +1 -0
- package/dist/index.cjs +672 -365
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +48 -8
- package/dist/index.d.ts +48 -8
- package/dist/index.js +122 -8
- package/dist/index.js.map +1 -1
- package/dist/model-registry.cjs +91 -24
- package/dist/model-registry.cjs.map +1 -1
- package/dist/model-registry.d.cts +24 -2
- package/dist/model-registry.d.ts +24 -2
- package/dist/model-registry.js +5 -1
- package/package.json +2 -2
- package/dist/chunk-RQADK6HE.js.map +0 -1
package/dist/index.d.cts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
export { ContextWindowOptions, DEFAULT_MAX_VIDEO_BYTES, MODELS, ModelInfo, getAuthStorageKey, getAuthStorageKeys, getContextWindow, getDefaultModel, getFastModel, getMaxThinkingLevel, getModel, getModelsForProvider, getSummaryModel, getVideoByteLimit, usesOpenAICodexTransport } from './model-registry.cjs';
|
|
1
|
+
export { ContextWindowOptions, DEFAULT_MAX_VIDEO_BYTES, MODELS, ModelInfo, getAuthStorageKey, getAuthStorageKeys, getContextWindow, getDefaultModel, getDefaultThinkingLevel, getFastModel, getMaxThinkingLevel, getModel, getModelsForProvider, getSummaryModel, getToolResultCharLimit, getVideoByteLimit, usesOpenAICodexTransport } from './model-registry.cjs';
|
|
2
2
|
import { Provider, ThinkingLevel } from '@prestyj/ai';
|
|
3
3
|
export { AppPaths, getAppPaths } from './paths.cjs';
|
|
4
4
|
|
|
@@ -58,6 +58,11 @@ interface OAuthCredentials {
|
|
|
58
58
|
accountId?: string;
|
|
59
59
|
projectId?: string;
|
|
60
60
|
baseUrl?: string;
|
|
61
|
+
/** ms timestamp until which this credential's usage window is exhausted.
|
|
62
|
+
* Set by AuthStorage.markUsageExhausted() when the provider rejects with a
|
|
63
|
+
* usage/quota stop; while in the future, resolution may skip this credential
|
|
64
|
+
* in favor of a configured fallback (e.g. Kimi OAuth → Moonshot API key). */
|
|
65
|
+
usageExhaustedUntil?: number;
|
|
61
66
|
}
|
|
62
67
|
interface OAuthLoginCallbacks {
|
|
63
68
|
onOpenUrl: (url: string) => void;
|
|
@@ -80,6 +85,14 @@ declare const MOONSHOT_OAUTH_KEY = "moonshot-oauth";
|
|
|
80
85
|
* order, is decided per-model via `getAuthStorageKeys()` in model-registry.ts.
|
|
81
86
|
*/
|
|
82
87
|
declare const XIAOMI_CREDITS_KEY = "xiaomi-credits";
|
|
88
|
+
/**
|
|
89
|
+
* Synchronous baseUrl read straight from the auth file, for boot paths that
|
|
90
|
+
* need the active endpoint before an AuthStorage instance exists (e.g. the
|
|
91
|
+
* CLI's sync main()). Missing/corrupt files yield undefined — callers treat
|
|
92
|
+
* that as the provider's public endpoint. Read-only: safe without the file
|
|
93
|
+
* lock (a torn mid-write read just falls back to undefined).
|
|
94
|
+
*/
|
|
95
|
+
declare function readStoredBaseUrlSync(authFile: string, provider: string): string | undefined;
|
|
83
96
|
declare class AuthStorage {
|
|
84
97
|
private data;
|
|
85
98
|
private filePath;
|
|
@@ -113,19 +126,46 @@ declare class AuthStorage {
|
|
|
113
126
|
* credential is absent (a present OAuth credential is refreshable).
|
|
114
127
|
*/
|
|
115
128
|
isStaticApiKey(provider: string): Promise<boolean>;
|
|
129
|
+
/**
|
|
130
|
+
* The base URL on the credential that is active right now, if any.
|
|
131
|
+
* Synchronous — call only after load()/resolveCredentials() populated the
|
|
132
|
+
* snapshot. For `moonshot` this is the Kimi For Coding URL whenever the
|
|
133
|
+
* OAuth entry is the one resolveCredentials would serve (i.e. not currently
|
|
134
|
+
* usage-exhausted with an API key configured).
|
|
135
|
+
*/
|
|
136
|
+
getStoredBaseUrl(provider: string): string | undefined;
|
|
116
137
|
load(): Promise<void>;
|
|
117
138
|
private ensureLoaded;
|
|
118
139
|
/**
|
|
119
140
|
* Force a re-read from disk, discarding the in-memory cache. Needed when
|
|
120
141
|
* another process mutates the auth file out-of-band — e.g. the desktop app
|
|
121
|
-
* writes API keys natively
|
|
122
|
-
* this instance, so a long-lived daemon's cache would otherwise stay stale and
|
|
123
|
-
* never see a newly added provider key.
|
|
142
|
+
* writes API keys natively without going through this instance.
|
|
124
143
|
*/
|
|
125
144
|
reload(): Promise<void>;
|
|
145
|
+
/**
|
|
146
|
+
* Apply one provider-scoped mutation to the latest on-disk snapshot.
|
|
147
|
+
* AuthStorage instances live in every app session/process, so writing this
|
|
148
|
+
* instance's cached snapshot can erase credentials another instance just
|
|
149
|
+
* added. The file lock only serializes writers; the re-read prevents stale
|
|
150
|
+
* full-file overwrites.
|
|
151
|
+
*/
|
|
152
|
+
private mutateLatest;
|
|
153
|
+
private reloadLatest;
|
|
126
154
|
getCredentials(provider: string): Promise<OAuthCredentials | undefined>;
|
|
127
155
|
setCredentials(provider: string, creds: OAuthCredentials): Promise<void>;
|
|
128
156
|
clearCredentials(provider: string): Promise<void>;
|
|
157
|
+
/**
|
|
158
|
+
* Mark the credential stored under `storageKey` as usage-exhausted until
|
|
159
|
+
* `resetsAt` (unix SECONDS, from the provider's rate-limit response) or a
|
|
160
|
+
* 15-minute default when no reset time is known. While the mark is in the
|
|
161
|
+
* future, `resolveCredentials("moonshot")` serves the Moonshot API key
|
|
162
|
+
* instead of the Kimi OAuth credential (when both are configured) — OAuth
|
|
163
|
+
* stays the preferred credential and is retried automatically once the mark
|
|
164
|
+
* lapses. Persisted to auth.json so a restart (or another ezcoder-app window)
|
|
165
|
+
* doesn't burn a request rediscovering the same exhausted window. No-op if
|
|
166
|
+
* nothing is stored under `storageKey`.
|
|
167
|
+
*/
|
|
168
|
+
markUsageExhausted(storageKey: string, resetsAt?: number): Promise<void>;
|
|
129
169
|
clearAll(): Promise<void>;
|
|
130
170
|
/**
|
|
131
171
|
* Returns valid credentials, auto-refreshing if expired.
|
|
@@ -142,14 +182,13 @@ declare class AuthStorage {
|
|
|
142
182
|
* Throws if not logged in.
|
|
143
183
|
*/
|
|
144
184
|
resolveToken(provider: string): Promise<string>;
|
|
145
|
-
private save;
|
|
146
185
|
}
|
|
147
186
|
declare class NotLoggedInError extends Error {
|
|
148
187
|
provider: string;
|
|
149
188
|
constructor(provider: string);
|
|
150
189
|
}
|
|
151
190
|
|
|
152
|
-
type SubscriptionUsageProvider = "anthropic" | "openai";
|
|
191
|
+
type SubscriptionUsageProvider = "anthropic" | "openai" | "moonshot";
|
|
153
192
|
interface SubscriptionUsageWindow {
|
|
154
193
|
kind: "current" | "weekly";
|
|
155
194
|
label: string;
|
|
@@ -165,7 +204,8 @@ interface SubscriptionUsageSnapshot {
|
|
|
165
204
|
}
|
|
166
205
|
declare class SubscriptionUsageError extends Error {
|
|
167
206
|
readonly status?: number | undefined;
|
|
168
|
-
|
|
207
|
+
readonly retryAfterMs?: number | undefined;
|
|
208
|
+
constructor(message: string, status?: number | undefined, retryAfterMs?: number | undefined);
|
|
169
209
|
}
|
|
170
210
|
type FetchFn = (input: string | URL | Request, init?: RequestInit) => Promise<Response>;
|
|
171
211
|
interface FetchSubscriptionUsageOptions {
|
|
@@ -413,4 +453,4 @@ interface AutoUpdater {
|
|
|
413
453
|
}
|
|
414
454
|
declare function createAutoUpdater(config: AutoUpdateConfig): AutoUpdater;
|
|
415
455
|
|
|
416
|
-
export { AuthStorage, type AutoUpdateConfig, type AutoUpdater, type InlineButton, type LogLevel, MOONSHOT_OAUTH_KEY, NotLoggedInError, type OAuthCredentials, type OAuthLoginCallbacks, type ProgressCallback, SubscriptionUsageError, type SubscriptionUsageProvider, type SubscriptionUsageSnapshot, type SubscriptionUsageWindow, TelegramBot, type TelegramConfig, type TelegramMessage, type TelegramUpdate, type TelegramVoiceMessage, XIAOMI_CREDITS_KEY, closeLogger, createAutoUpdater, decodeOggOpus, downmixToMono, fetchSubscriptionUsage, generatePKCE, getClaudeCliUserAgent, getClaudeCodeVersion, getNextThinkingLevel, getSessionId, getSupportedThinkingLevels, isKimiCodingEndpoint, isLoggerOpen, isModelLoaded, isThinkingLevelSupported, kimiCodeBaseUrl, kimiCodingHeaders, log, loginAnthropic, loginGemini, loginKimi, loginOpenAI, openLog, refreshAnthropicToken, refreshGeminiToken, refreshKimiToken, refreshOpenAIToken, registerLogCleanup, resample, setProgressCallback, transcribeVoice, withFileLock };
|
|
456
|
+
export { AuthStorage, type AutoUpdateConfig, type AutoUpdater, type InlineButton, type LogLevel, MOONSHOT_OAUTH_KEY, NotLoggedInError, type OAuthCredentials, type OAuthLoginCallbacks, type ProgressCallback, SubscriptionUsageError, type SubscriptionUsageProvider, type SubscriptionUsageSnapshot, type SubscriptionUsageWindow, TelegramBot, type TelegramConfig, type TelegramMessage, type TelegramUpdate, type TelegramVoiceMessage, XIAOMI_CREDITS_KEY, closeLogger, createAutoUpdater, decodeOggOpus, downmixToMono, fetchSubscriptionUsage, generatePKCE, getClaudeCliUserAgent, getClaudeCodeVersion, getNextThinkingLevel, getSessionId, getSupportedThinkingLevels, isKimiCodingEndpoint, isLoggerOpen, isModelLoaded, isThinkingLevelSupported, kimiCodeBaseUrl, kimiCodingHeaders, log, loginAnthropic, loginGemini, loginKimi, loginOpenAI, openLog, readStoredBaseUrlSync, refreshAnthropicToken, refreshGeminiToken, refreshKimiToken, refreshOpenAIToken, registerLogCleanup, resample, setProgressCallback, transcribeVoice, withFileLock };
|
package/dist/index.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
export { ContextWindowOptions, DEFAULT_MAX_VIDEO_BYTES, MODELS, ModelInfo, getAuthStorageKey, getAuthStorageKeys, getContextWindow, getDefaultModel, getFastModel, getMaxThinkingLevel, getModel, getModelsForProvider, getSummaryModel, getVideoByteLimit, usesOpenAICodexTransport } from './model-registry.js';
|
|
1
|
+
export { ContextWindowOptions, DEFAULT_MAX_VIDEO_BYTES, MODELS, ModelInfo, getAuthStorageKey, getAuthStorageKeys, getContextWindow, getDefaultModel, getDefaultThinkingLevel, getFastModel, getMaxThinkingLevel, getModel, getModelsForProvider, getSummaryModel, getToolResultCharLimit, getVideoByteLimit, usesOpenAICodexTransport } from './model-registry.js';
|
|
2
2
|
import { Provider, ThinkingLevel } from '@prestyj/ai';
|
|
3
3
|
export { AppPaths, getAppPaths } from './paths.js';
|
|
4
4
|
|
|
@@ -58,6 +58,11 @@ interface OAuthCredentials {
|
|
|
58
58
|
accountId?: string;
|
|
59
59
|
projectId?: string;
|
|
60
60
|
baseUrl?: string;
|
|
61
|
+
/** ms timestamp until which this credential's usage window is exhausted.
|
|
62
|
+
* Set by AuthStorage.markUsageExhausted() when the provider rejects with a
|
|
63
|
+
* usage/quota stop; while in the future, resolution may skip this credential
|
|
64
|
+
* in favor of a configured fallback (e.g. Kimi OAuth → Moonshot API key). */
|
|
65
|
+
usageExhaustedUntil?: number;
|
|
61
66
|
}
|
|
62
67
|
interface OAuthLoginCallbacks {
|
|
63
68
|
onOpenUrl: (url: string) => void;
|
|
@@ -80,6 +85,14 @@ declare const MOONSHOT_OAUTH_KEY = "moonshot-oauth";
|
|
|
80
85
|
* order, is decided per-model via `getAuthStorageKeys()` in model-registry.ts.
|
|
81
86
|
*/
|
|
82
87
|
declare const XIAOMI_CREDITS_KEY = "xiaomi-credits";
|
|
88
|
+
/**
|
|
89
|
+
* Synchronous baseUrl read straight from the auth file, for boot paths that
|
|
90
|
+
* need the active endpoint before an AuthStorage instance exists (e.g. the
|
|
91
|
+
* CLI's sync main()). Missing/corrupt files yield undefined — callers treat
|
|
92
|
+
* that as the provider's public endpoint. Read-only: safe without the file
|
|
93
|
+
* lock (a torn mid-write read just falls back to undefined).
|
|
94
|
+
*/
|
|
95
|
+
declare function readStoredBaseUrlSync(authFile: string, provider: string): string | undefined;
|
|
83
96
|
declare class AuthStorage {
|
|
84
97
|
private data;
|
|
85
98
|
private filePath;
|
|
@@ -113,19 +126,46 @@ declare class AuthStorage {
|
|
|
113
126
|
* credential is absent (a present OAuth credential is refreshable).
|
|
114
127
|
*/
|
|
115
128
|
isStaticApiKey(provider: string): Promise<boolean>;
|
|
129
|
+
/**
|
|
130
|
+
* The base URL on the credential that is active right now, if any.
|
|
131
|
+
* Synchronous — call only after load()/resolveCredentials() populated the
|
|
132
|
+
* snapshot. For `moonshot` this is the Kimi For Coding URL whenever the
|
|
133
|
+
* OAuth entry is the one resolveCredentials would serve (i.e. not currently
|
|
134
|
+
* usage-exhausted with an API key configured).
|
|
135
|
+
*/
|
|
136
|
+
getStoredBaseUrl(provider: string): string | undefined;
|
|
116
137
|
load(): Promise<void>;
|
|
117
138
|
private ensureLoaded;
|
|
118
139
|
/**
|
|
119
140
|
* Force a re-read from disk, discarding the in-memory cache. Needed when
|
|
120
141
|
* another process mutates the auth file out-of-band — e.g. the desktop app
|
|
121
|
-
* writes API keys natively
|
|
122
|
-
* this instance, so a long-lived daemon's cache would otherwise stay stale and
|
|
123
|
-
* never see a newly added provider key.
|
|
142
|
+
* writes API keys natively without going through this instance.
|
|
124
143
|
*/
|
|
125
144
|
reload(): Promise<void>;
|
|
145
|
+
/**
|
|
146
|
+
* Apply one provider-scoped mutation to the latest on-disk snapshot.
|
|
147
|
+
* AuthStorage instances live in every app session/process, so writing this
|
|
148
|
+
* instance's cached snapshot can erase credentials another instance just
|
|
149
|
+
* added. The file lock only serializes writers; the re-read prevents stale
|
|
150
|
+
* full-file overwrites.
|
|
151
|
+
*/
|
|
152
|
+
private mutateLatest;
|
|
153
|
+
private reloadLatest;
|
|
126
154
|
getCredentials(provider: string): Promise<OAuthCredentials | undefined>;
|
|
127
155
|
setCredentials(provider: string, creds: OAuthCredentials): Promise<void>;
|
|
128
156
|
clearCredentials(provider: string): Promise<void>;
|
|
157
|
+
/**
|
|
158
|
+
* Mark the credential stored under `storageKey` as usage-exhausted until
|
|
159
|
+
* `resetsAt` (unix SECONDS, from the provider's rate-limit response) or a
|
|
160
|
+
* 15-minute default when no reset time is known. While the mark is in the
|
|
161
|
+
* future, `resolveCredentials("moonshot")` serves the Moonshot API key
|
|
162
|
+
* instead of the Kimi OAuth credential (when both are configured) — OAuth
|
|
163
|
+
* stays the preferred credential and is retried automatically once the mark
|
|
164
|
+
* lapses. Persisted to auth.json so a restart (or another ezcoder-app window)
|
|
165
|
+
* doesn't burn a request rediscovering the same exhausted window. No-op if
|
|
166
|
+
* nothing is stored under `storageKey`.
|
|
167
|
+
*/
|
|
168
|
+
markUsageExhausted(storageKey: string, resetsAt?: number): Promise<void>;
|
|
129
169
|
clearAll(): Promise<void>;
|
|
130
170
|
/**
|
|
131
171
|
* Returns valid credentials, auto-refreshing if expired.
|
|
@@ -142,14 +182,13 @@ declare class AuthStorage {
|
|
|
142
182
|
* Throws if not logged in.
|
|
143
183
|
*/
|
|
144
184
|
resolveToken(provider: string): Promise<string>;
|
|
145
|
-
private save;
|
|
146
185
|
}
|
|
147
186
|
declare class NotLoggedInError extends Error {
|
|
148
187
|
provider: string;
|
|
149
188
|
constructor(provider: string);
|
|
150
189
|
}
|
|
151
190
|
|
|
152
|
-
type SubscriptionUsageProvider = "anthropic" | "openai";
|
|
191
|
+
type SubscriptionUsageProvider = "anthropic" | "openai" | "moonshot";
|
|
153
192
|
interface SubscriptionUsageWindow {
|
|
154
193
|
kind: "current" | "weekly";
|
|
155
194
|
label: string;
|
|
@@ -165,7 +204,8 @@ interface SubscriptionUsageSnapshot {
|
|
|
165
204
|
}
|
|
166
205
|
declare class SubscriptionUsageError extends Error {
|
|
167
206
|
readonly status?: number | undefined;
|
|
168
|
-
|
|
207
|
+
readonly retryAfterMs?: number | undefined;
|
|
208
|
+
constructor(message: string, status?: number | undefined, retryAfterMs?: number | undefined);
|
|
169
209
|
}
|
|
170
210
|
type FetchFn = (input: string | URL | Request, init?: RequestInit) => Promise<Response>;
|
|
171
211
|
interface FetchSubscriptionUsageOptions {
|
|
@@ -413,4 +453,4 @@ interface AutoUpdater {
|
|
|
413
453
|
}
|
|
414
454
|
declare function createAutoUpdater(config: AutoUpdateConfig): AutoUpdater;
|
|
415
455
|
|
|
416
|
-
export { AuthStorage, type AutoUpdateConfig, type AutoUpdater, type InlineButton, type LogLevel, MOONSHOT_OAUTH_KEY, NotLoggedInError, type OAuthCredentials, type OAuthLoginCallbacks, type ProgressCallback, SubscriptionUsageError, type SubscriptionUsageProvider, type SubscriptionUsageSnapshot, type SubscriptionUsageWindow, TelegramBot, type TelegramConfig, type TelegramMessage, type TelegramUpdate, type TelegramVoiceMessage, XIAOMI_CREDITS_KEY, closeLogger, createAutoUpdater, decodeOggOpus, downmixToMono, fetchSubscriptionUsage, generatePKCE, getClaudeCliUserAgent, getClaudeCodeVersion, getNextThinkingLevel, getSessionId, getSupportedThinkingLevels, isKimiCodingEndpoint, isLoggerOpen, isModelLoaded, isThinkingLevelSupported, kimiCodeBaseUrl, kimiCodingHeaders, log, loginAnthropic, loginGemini, loginKimi, loginOpenAI, openLog, refreshAnthropicToken, refreshGeminiToken, refreshKimiToken, refreshOpenAIToken, registerLogCleanup, resample, setProgressCallback, transcribeVoice, withFileLock };
|
|
456
|
+
export { AuthStorage, type AutoUpdateConfig, type AutoUpdater, type InlineButton, type LogLevel, MOONSHOT_OAUTH_KEY, NotLoggedInError, type OAuthCredentials, type OAuthLoginCallbacks, type ProgressCallback, SubscriptionUsageError, type SubscriptionUsageProvider, type SubscriptionUsageSnapshot, type SubscriptionUsageWindow, TelegramBot, type TelegramConfig, type TelegramMessage, type TelegramUpdate, type TelegramVoiceMessage, XIAOMI_CREDITS_KEY, closeLogger, createAutoUpdater, decodeOggOpus, downmixToMono, fetchSubscriptionUsage, generatePKCE, getClaudeCliUserAgent, getClaudeCodeVersion, getNextThinkingLevel, getSessionId, getSupportedThinkingLevels, isKimiCodingEndpoint, isLoggerOpen, isModelLoaded, isThinkingLevelSupported, kimiCodeBaseUrl, kimiCodingHeaders, log, loginAnthropic, loginGemini, loginKimi, loginOpenAI, openLog, readStoredBaseUrlSync, refreshAnthropicToken, refreshGeminiToken, refreshKimiToken, refreshOpenAIToken, registerLogCleanup, resample, setProgressCallback, transcribeVoice, withFileLock };
|
package/dist/index.js
CHANGED
|
@@ -13,12 +13,14 @@ import {
|
|
|
13
13
|
getClaudeCodeVersion,
|
|
14
14
|
getContextWindow,
|
|
15
15
|
getDefaultModel,
|
|
16
|
+
getDefaultThinkingLevel,
|
|
16
17
|
getFastModel,
|
|
17
18
|
getMaxThinkingLevel,
|
|
18
19
|
getModel,
|
|
19
20
|
getModelsForProvider,
|
|
20
21
|
getSessionId,
|
|
21
22
|
getSummaryModel,
|
|
23
|
+
getToolResultCharLimit,
|
|
22
24
|
getVideoByteLimit,
|
|
23
25
|
isKimiCodingEndpoint,
|
|
24
26
|
isLoggerOpen,
|
|
@@ -30,6 +32,7 @@ import {
|
|
|
30
32
|
loginKimi,
|
|
31
33
|
loginOpenAI,
|
|
32
34
|
openLog,
|
|
35
|
+
readStoredBaseUrlSync,
|
|
33
36
|
refreshAnthropicToken,
|
|
34
37
|
refreshGeminiToken,
|
|
35
38
|
refreshKimiToken,
|
|
@@ -37,7 +40,7 @@ import {
|
|
|
37
40
|
registerLogCleanup,
|
|
38
41
|
usesOpenAICodexTransport,
|
|
39
42
|
withFileLock
|
|
40
|
-
} from "./chunk-
|
|
43
|
+
} from "./chunk-JXPW4JKV.js";
|
|
41
44
|
import {
|
|
42
45
|
getAppPaths
|
|
43
46
|
} from "./chunk-WCIV25KV.js";
|
|
@@ -53,6 +56,7 @@ var OPENAI_GPT_56_THINKING_LEVELS = [
|
|
|
53
56
|
"ultra"
|
|
54
57
|
];
|
|
55
58
|
var SAKANA_THINKING_LEVELS = ["high", "xhigh"];
|
|
59
|
+
var XAI_THINKING_LEVELS = ["low", "medium", "high"];
|
|
56
60
|
var ANTHROPIC_OPUS_48_47_THINKING_LEVELS = [
|
|
57
61
|
"low",
|
|
58
62
|
"medium",
|
|
@@ -66,12 +70,19 @@ var ANTHROPIC_ADAPTIVE_THINKING_LEVELS = [
|
|
|
66
70
|
"high",
|
|
67
71
|
"max"
|
|
68
72
|
];
|
|
73
|
+
var MOONSHOT_K3_THINKING_LEVELS = ["low", "high", "max"];
|
|
69
74
|
function isOpenAIGptModel(provider, model) {
|
|
70
75
|
return provider === "openai" && model.startsWith("gpt-");
|
|
71
76
|
}
|
|
72
77
|
function isSakanaModel(provider) {
|
|
73
78
|
return provider === "sakana";
|
|
74
79
|
}
|
|
80
|
+
function isXaiModel(provider) {
|
|
81
|
+
return provider === "xai";
|
|
82
|
+
}
|
|
83
|
+
function isMoonshotK3Model(provider, model) {
|
|
84
|
+
return provider === "moonshot" && model === "kimi-k3";
|
|
85
|
+
}
|
|
75
86
|
function isAnthropicOpus48Or47Model(provider, model) {
|
|
76
87
|
return provider === "anthropic" && /opus-4-8|opus-4-7/.test(model);
|
|
77
88
|
}
|
|
@@ -91,6 +102,12 @@ function getSupportedThinkingLevels(provider, model) {
|
|
|
91
102
|
if (maxIndex2 === -1) return SAKANA_THINKING_LEVELS;
|
|
92
103
|
return SAKANA_THINKING_LEVELS.slice(0, maxIndex2 + 1);
|
|
93
104
|
}
|
|
105
|
+
if (isXaiModel(provider)) {
|
|
106
|
+
const maxIndex2 = XAI_THINKING_LEVELS.indexOf(maxLevel);
|
|
107
|
+
if (maxIndex2 === -1) return XAI_THINKING_LEVELS;
|
|
108
|
+
return XAI_THINKING_LEVELS.slice(0, maxIndex2 + 1);
|
|
109
|
+
}
|
|
110
|
+
if (isMoonshotK3Model(provider, model)) return MOONSHOT_K3_THINKING_LEVELS;
|
|
94
111
|
if (!isOpenAIGptModel(provider, model)) return [maxLevel];
|
|
95
112
|
const levels = model.startsWith("gpt-5.6-") ? OPENAI_GPT_56_THINKING_LEVELS : OPENAI_GPT_THINKING_LEVELS;
|
|
96
113
|
const maxIndex = levels.indexOf(maxLevel);
|
|
@@ -102,7 +119,7 @@ function isThinkingLevelSupported(provider, model, level) {
|
|
|
102
119
|
}
|
|
103
120
|
function getNextThinkingLevel(provider, model, current) {
|
|
104
121
|
const supportedLevels = getSupportedThinkingLevels(provider, model);
|
|
105
|
-
const shouldCycleLevels = isOpenAIGptModel(provider, model) || isAnthropicAdaptiveModel(provider, model) || isSakanaModel(provider);
|
|
122
|
+
const shouldCycleLevels = isOpenAIGptModel(provider, model) || isAnthropicAdaptiveModel(provider, model) || isSakanaModel(provider) || isXaiModel(provider) || isMoonshotK3Model(provider, model);
|
|
106
123
|
if (!shouldCycleLevels) {
|
|
107
124
|
return current ? void 0 : supportedLevels[0];
|
|
108
125
|
}
|
|
@@ -114,9 +131,10 @@ function getNextThinkingLevel(provider, model, current) {
|
|
|
114
131
|
|
|
115
132
|
// src/provider-usage.ts
|
|
116
133
|
var SubscriptionUsageError = class extends Error {
|
|
117
|
-
constructor(message, status) {
|
|
134
|
+
constructor(message, status, retryAfterMs2) {
|
|
118
135
|
super(message);
|
|
119
136
|
this.status = status;
|
|
137
|
+
this.retryAfterMs = retryAfterMs2;
|
|
120
138
|
this.name = "SubscriptionUsageError";
|
|
121
139
|
}
|
|
122
140
|
};
|
|
@@ -166,12 +184,20 @@ function normalizedCodexWindow(window, fallbackKind, now) {
|
|
|
166
184
|
resetsAt: codexResetAt(window, now)
|
|
167
185
|
};
|
|
168
186
|
}
|
|
169
|
-
|
|
187
|
+
function retryAfterMs(response, now) {
|
|
188
|
+
const value = response.headers.get("retry-after")?.trim();
|
|
189
|
+
if (!value) return void 0;
|
|
190
|
+
if (/^\d+(?:\.\d+)?$/.test(value)) return Math.ceil(Number(value) * 1e3);
|
|
191
|
+
const retryAt = Date.parse(value);
|
|
192
|
+
return Number.isFinite(retryAt) ? Math.max(0, retryAt - now) : void 0;
|
|
193
|
+
}
|
|
194
|
+
async function readUsageResponse(response, now) {
|
|
170
195
|
const text = await response.text();
|
|
171
196
|
if (!response.ok) {
|
|
172
197
|
throw new SubscriptionUsageError(
|
|
173
198
|
`Subscription usage request failed with HTTP ${response.status}`,
|
|
174
|
-
response.status
|
|
199
|
+
response.status,
|
|
200
|
+
retryAfterMs(response, now)
|
|
175
201
|
);
|
|
176
202
|
}
|
|
177
203
|
try {
|
|
@@ -192,7 +218,7 @@ async function fetchAnthropicUsage(credentials, fetchFn, signal, now) {
|
|
|
192
218
|
"User-Agent": "ezcoder"
|
|
193
219
|
}
|
|
194
220
|
});
|
|
195
|
-
const data = await readUsageResponse(response);
|
|
221
|
+
const data = await readUsageResponse(response, now());
|
|
196
222
|
const windows = [];
|
|
197
223
|
const currentPercent = clampPercent(data.five_hour?.utilization);
|
|
198
224
|
if (currentPercent !== void 0) {
|
|
@@ -228,7 +254,7 @@ async function fetchCodexUsage(credentials, fetchFn, signal, now) {
|
|
|
228
254
|
};
|
|
229
255
|
if (credentials.accountId) headers["ChatGPT-Account-Id"] = credentials.accountId;
|
|
230
256
|
const response = await fetchFn(CODEX_USAGE_URL, { method: "GET", signal, headers });
|
|
231
|
-
const data = await readUsageResponse(response);
|
|
257
|
+
const data = await readUsageResponse(response, now());
|
|
232
258
|
const windows = [
|
|
233
259
|
normalizedCodexWindow(data.rate_limit?.primary_window, "current", now()),
|
|
234
260
|
normalizedCodexWindow(data.rate_limit?.secondary_window, "weekly", now())
|
|
@@ -244,12 +270,97 @@ async function fetchCodexUsage(credentials, fetchFn, signal, now) {
|
|
|
244
270
|
fetchedAt: now()
|
|
245
271
|
};
|
|
246
272
|
}
|
|
273
|
+
function kimiNumber(value) {
|
|
274
|
+
if (typeof value === "string" && value.trim()) {
|
|
275
|
+
const parsed = Number(value);
|
|
276
|
+
return Number.isFinite(parsed) ? parsed : void 0;
|
|
277
|
+
}
|
|
278
|
+
return finiteNumber(value);
|
|
279
|
+
}
|
|
280
|
+
function kimiUsagePercent(detail) {
|
|
281
|
+
const used = kimiNumber(detail?.used);
|
|
282
|
+
const limit = kimiNumber(detail?.limit);
|
|
283
|
+
if (used === void 0 || limit === void 0 || limit <= 0) return void 0;
|
|
284
|
+
return Math.min(100, Math.max(0, used / limit * 100));
|
|
285
|
+
}
|
|
286
|
+
function kimiWindowMinutes(window) {
|
|
287
|
+
const duration = kimiNumber(window?.duration);
|
|
288
|
+
if (duration === void 0 || duration <= 0) return void 0;
|
|
289
|
+
switch (window?.timeUnit) {
|
|
290
|
+
case "TIME_UNIT_SECOND":
|
|
291
|
+
return duration / 60;
|
|
292
|
+
case "TIME_UNIT_MINUTE":
|
|
293
|
+
return duration;
|
|
294
|
+
case "TIME_UNIT_HOUR":
|
|
295
|
+
return duration * 60;
|
|
296
|
+
case "TIME_UNIT_DAY":
|
|
297
|
+
return duration * 24 * 60;
|
|
298
|
+
default:
|
|
299
|
+
return void 0;
|
|
300
|
+
}
|
|
301
|
+
}
|
|
302
|
+
async function fetchKimiUsage(credentials, fetchFn, signal, now) {
|
|
303
|
+
const response = await fetchFn(`${kimiCodeBaseUrl()}/usages`, {
|
|
304
|
+
method: "GET",
|
|
305
|
+
signal,
|
|
306
|
+
headers: {
|
|
307
|
+
Authorization: "Bearer " + credentials.accessToken,
|
|
308
|
+
Accept: "application/json",
|
|
309
|
+
// The managed coding endpoint gates on the kimi-code-cli client identity,
|
|
310
|
+
// same as model requests.
|
|
311
|
+
...kimiCodingHeaders()
|
|
312
|
+
}
|
|
313
|
+
});
|
|
314
|
+
const data = await readUsageResponse(response, now());
|
|
315
|
+
const windows = [];
|
|
316
|
+
const weeklyPercent = kimiUsagePercent(data.usage);
|
|
317
|
+
if (weeklyPercent !== void 0) {
|
|
318
|
+
windows.push({
|
|
319
|
+
kind: "weekly",
|
|
320
|
+
label: "Weekly",
|
|
321
|
+
usedPercent: weeklyPercent,
|
|
322
|
+
resetsAt: isoTimestamp(data.usage?.resetTime)
|
|
323
|
+
});
|
|
324
|
+
}
|
|
325
|
+
for (const limit of data.limits ?? []) {
|
|
326
|
+
const minutes = kimiWindowMinutes(limit?.window);
|
|
327
|
+
const percent = kimiUsagePercent(limit?.detail);
|
|
328
|
+
if (minutes === void 0 || percent === void 0) continue;
|
|
329
|
+
if (minutes >= 6 * 24 * 60) {
|
|
330
|
+
if (!windows.some((window) => window.kind === "weekly")) {
|
|
331
|
+
windows.push({
|
|
332
|
+
kind: "weekly",
|
|
333
|
+
label: "Weekly",
|
|
334
|
+
usedPercent: percent,
|
|
335
|
+
resetsAt: isoTimestamp(limit?.detail?.resetTime)
|
|
336
|
+
});
|
|
337
|
+
}
|
|
338
|
+
continue;
|
|
339
|
+
}
|
|
340
|
+
windows.push({
|
|
341
|
+
kind: "current",
|
|
342
|
+
label: `${Math.max(1, Math.round(minutes / 60))}-hour`,
|
|
343
|
+
usedPercent: percent,
|
|
344
|
+
resetsAt: isoTimestamp(limit?.detail?.resetTime)
|
|
345
|
+
});
|
|
346
|
+
}
|
|
347
|
+
windows.sort((left, right) => {
|
|
348
|
+
if (left.kind === right.kind) return 0;
|
|
349
|
+
return left.kind === "current" ? -1 : 1;
|
|
350
|
+
});
|
|
351
|
+
return {
|
|
352
|
+
provider: "moonshot",
|
|
353
|
+
displayName: "Kimi",
|
|
354
|
+
windows,
|
|
355
|
+
fetchedAt: now()
|
|
356
|
+
};
|
|
357
|
+
}
|
|
247
358
|
async function fetchSubscriptionUsage(provider, credentials, options = {}) {
|
|
248
359
|
const fetchFn = options.fetchFn ?? fetch;
|
|
249
360
|
const now = options.now ?? Date.now;
|
|
250
361
|
const signal = AbortSignal.timeout(options.timeoutMs ?? 8e3);
|
|
251
362
|
try {
|
|
252
|
-
return provider === "anthropic" ? await fetchAnthropicUsage(credentials, fetchFn, signal, now) : await fetchCodexUsage(credentials, fetchFn, signal, now);
|
|
363
|
+
return provider === "anthropic" ? await fetchAnthropicUsage(credentials, fetchFn, signal, now) : provider === "openai" ? await fetchCodexUsage(credentials, fetchFn, signal, now) : await fetchKimiUsage(credentials, fetchFn, signal, now);
|
|
253
364
|
} catch (error) {
|
|
254
365
|
if (error instanceof SubscriptionUsageError) throw error;
|
|
255
366
|
const message = error instanceof Error ? error.message : String(error);
|
|
@@ -754,6 +865,7 @@ export {
|
|
|
754
865
|
getClaudeCodeVersion,
|
|
755
866
|
getContextWindow,
|
|
756
867
|
getDefaultModel,
|
|
868
|
+
getDefaultThinkingLevel,
|
|
757
869
|
getFastModel,
|
|
758
870
|
getMaxThinkingLevel,
|
|
759
871
|
getModel,
|
|
@@ -762,6 +874,7 @@ export {
|
|
|
762
874
|
getSessionId,
|
|
763
875
|
getSummaryModel,
|
|
764
876
|
getSupportedThinkingLevels,
|
|
877
|
+
getToolResultCharLimit,
|
|
765
878
|
getVideoByteLimit,
|
|
766
879
|
isKimiCodingEndpoint,
|
|
767
880
|
isLoggerOpen,
|
|
@@ -775,6 +888,7 @@ export {
|
|
|
775
888
|
loginKimi,
|
|
776
889
|
loginOpenAI,
|
|
777
890
|
openLog,
|
|
891
|
+
readStoredBaseUrlSync,
|
|
778
892
|
refreshAnthropicToken,
|
|
779
893
|
refreshGeminiToken,
|
|
780
894
|
refreshKimiToken,
|