@slkiser/opencode-quota 1.0.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/LICENSE +21 -0
- package/README.md +103 -0
- package/dist/data/modelsdev-pricing.min.json +504 -0
- package/dist/index.d.ts +10 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +15 -0
- package/dist/index.js.map +1 -0
- package/dist/lib/cache.d.ts +49 -0
- package/dist/lib/cache.d.ts.map +1 -0
- package/dist/lib/cache.js +127 -0
- package/dist/lib/cache.js.map +1 -0
- package/dist/lib/config.d.ts +30 -0
- package/dist/lib/config.d.ts.map +1 -0
- package/dist/lib/config.js +154 -0
- package/dist/lib/config.js.map +1 -0
- package/dist/lib/copilot.d.ts +25 -0
- package/dist/lib/copilot.d.ts.map +1 -0
- package/dist/lib/copilot.js +306 -0
- package/dist/lib/copilot.js.map +1 -0
- package/dist/lib/entries.d.ts +60 -0
- package/dist/lib/entries.d.ts.map +1 -0
- package/dist/lib/entries.js +8 -0
- package/dist/lib/entries.js.map +1 -0
- package/dist/lib/firmware.d.ts +15 -0
- package/dist/lib/firmware.d.ts.map +1 -0
- package/dist/lib/firmware.js +79 -0
- package/dist/lib/firmware.js.map +1 -0
- package/dist/lib/format.d.ts +16 -0
- package/dist/lib/format.d.ts.map +1 -0
- package/dist/lib/format.js +99 -0
- package/dist/lib/format.js.map +1 -0
- package/dist/lib/google-token-cache.d.ts +30 -0
- package/dist/lib/google-token-cache.d.ts.map +1 -0
- package/dist/lib/google-token-cache.js +100 -0
- package/dist/lib/google-token-cache.js.map +1 -0
- package/dist/lib/google.d.ts +43 -0
- package/dist/lib/google.d.ts.map +1 -0
- package/dist/lib/google.js +399 -0
- package/dist/lib/google.js.map +1 -0
- package/dist/lib/markdown-table.d.ts +8 -0
- package/dist/lib/markdown-table.d.ts.map +1 -0
- package/dist/lib/markdown-table.js +56 -0
- package/dist/lib/markdown-table.js.map +1 -0
- package/dist/lib/modelsdev-pricing.d.ts +23 -0
- package/dist/lib/modelsdev-pricing.d.ts.map +1 -0
- package/dist/lib/modelsdev-pricing.js +32 -0
- package/dist/lib/modelsdev-pricing.js.map +1 -0
- package/dist/lib/openai.d.ts +33 -0
- package/dist/lib/openai.d.ts.map +1 -0
- package/dist/lib/openai.js +162 -0
- package/dist/lib/openai.js.map +1 -0
- package/dist/lib/opencode-auth.d.ts +11 -0
- package/dist/lib/opencode-auth.d.ts.map +1 -0
- package/dist/lib/opencode-auth.js +27 -0
- package/dist/lib/opencode-auth.js.map +1 -0
- package/dist/lib/opencode-storage.d.ts +45 -0
- package/dist/lib/opencode-storage.d.ts.map +1 -0
- package/dist/lib/opencode-storage.js +120 -0
- package/dist/lib/opencode-storage.js.map +1 -0
- package/dist/lib/quota-command-format.d.ts +14 -0
- package/dist/lib/quota-command-format.d.ts.map +1 -0
- package/dist/lib/quota-command-format.js +122 -0
- package/dist/lib/quota-command-format.js.map +1 -0
- package/dist/lib/quota-stats-format.d.ts +9 -0
- package/dist/lib/quota-stats-format.d.ts.map +1 -0
- package/dist/lib/quota-stats-format.js +244 -0
- package/dist/lib/quota-stats-format.js.map +1 -0
- package/dist/lib/quota-stats.d.ts +71 -0
- package/dist/lib/quota-stats.d.ts.map +1 -0
- package/dist/lib/quota-stats.js +270 -0
- package/dist/lib/quota-stats.js.map +1 -0
- package/dist/lib/quota-status.d.ts +23 -0
- package/dist/lib/quota-status.d.ts.map +1 -0
- package/dist/lib/quota-status.js +112 -0
- package/dist/lib/quota-status.js.map +1 -0
- package/dist/lib/toast-format-grouped.d.ts +25 -0
- package/dist/lib/toast-format-grouped.d.ts.map +1 -0
- package/dist/lib/toast-format-grouped.js +123 -0
- package/dist/lib/toast-format-grouped.js.map +1 -0
- package/dist/lib/types.d.ts +218 -0
- package/dist/lib/types.d.ts.map +1 -0
- package/dist/lib/types.js +39 -0
- package/dist/lib/types.js.map +1 -0
- package/dist/plugin.d.ts +13 -0
- package/dist/plugin.d.ts.map +1 -0
- package/dist/plugin.js +633 -0
- package/dist/plugin.js.map +1 -0
- package/dist/providers/copilot.d.ts +8 -0
- package/dist/providers/copilot.d.ts.map +1 -0
- package/dist/providers/copilot.js +50 -0
- package/dist/providers/copilot.js.map +1 -0
- package/dist/providers/firmware.d.ts +6 -0
- package/dist/providers/firmware.d.ts.map +1 -0
- package/dist/providers/firmware.js +52 -0
- package/dist/providers/firmware.js.map +1 -0
- package/dist/providers/google-antigravity.d.ts +6 -0
- package/dist/providers/google-antigravity.d.ts.map +1 -0
- package/dist/providers/google-antigravity.js +77 -0
- package/dist/providers/google-antigravity.js.map +1 -0
- package/dist/providers/openai.d.ts +6 -0
- package/dist/providers/openai.d.ts.map +1 -0
- package/dist/providers/openai.js +106 -0
- package/dist/providers/openai.js.map +1 -0
- package/dist/providers/registry.d.ts +8 -0
- package/dist/providers/registry.d.ts.map +1 -0
- package/dist/providers/registry.js +14 -0
- package/dist/providers/registry.js.map +1 -0
- package/package.json +71 -0
package/dist/plugin.js
ADDED
|
@@ -0,0 +1,633 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* OpenCode Quota Toast Plugin
|
|
3
|
+
*
|
|
4
|
+
* Shows a minimal quota status toast without LLM invocation.
|
|
5
|
+
* Triggers on session.idle, session.compacted, and question tool completion.
|
|
6
|
+
* Supports GitHub Copilot and Google (via opencode-antigravity-auth).
|
|
7
|
+
*/
|
|
8
|
+
import { DEFAULT_CONFIG } from "./lib/types.js";
|
|
9
|
+
import { loadConfig, createLoadConfigMeta } from "./lib/config.js";
|
|
10
|
+
import { getOrFetchWithCacheControl } from "./lib/cache.js";
|
|
11
|
+
import { formatQuotaRows } from "./lib/format.js";
|
|
12
|
+
import { formatQuotaCommand } from "./lib/quota-command-format.js";
|
|
13
|
+
import { getProviders } from "./providers/registry.js";
|
|
14
|
+
import { tool } from "@opencode-ai/plugin";
|
|
15
|
+
import { aggregateUsage } from "./lib/quota-stats.js";
|
|
16
|
+
import { formatQuotaStatsReport } from "./lib/quota-stats-format.js";
|
|
17
|
+
import { buildQuotaStatusReport } from "./lib/quota-status.js";
|
|
18
|
+
import { refreshGoogleTokensForAllAccounts } from "./lib/google.js";
|
|
19
|
+
// =============================================================================
|
|
20
|
+
// Plugin Implementation
|
|
21
|
+
// =============================================================================
|
|
22
|
+
/**
|
|
23
|
+
* Main plugin export
|
|
24
|
+
*/
|
|
25
|
+
export const QuotaToastPlugin = async ({ client }) => {
|
|
26
|
+
const typedClient = client;
|
|
27
|
+
/**
|
|
28
|
+
* Inject tool output directly into the session without triggering an LLM response.
|
|
29
|
+
* This prevents models from summarizing/rewriting our carefully formatted reports.
|
|
30
|
+
*/
|
|
31
|
+
async function injectRawOutput(sessionID, output) {
|
|
32
|
+
try {
|
|
33
|
+
await typedClient.session.prompt({
|
|
34
|
+
path: { id: sessionID },
|
|
35
|
+
body: {
|
|
36
|
+
noReply: true,
|
|
37
|
+
// ignored=true keeps this out of future model context while still
|
|
38
|
+
// showing it to the user in the transcript.
|
|
39
|
+
parts: [{ type: "text", text: output, ignored: true }],
|
|
40
|
+
},
|
|
41
|
+
});
|
|
42
|
+
}
|
|
43
|
+
catch (err) {
|
|
44
|
+
// Log but don't fail - the tool output will still be returned
|
|
45
|
+
await typedClient.app.log({
|
|
46
|
+
body: {
|
|
47
|
+
service: "quota-toast",
|
|
48
|
+
level: "warn",
|
|
49
|
+
message: "Failed to inject raw output",
|
|
50
|
+
extra: { error: err instanceof Error ? err.message : String(err) },
|
|
51
|
+
},
|
|
52
|
+
});
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
// Keep init fast/non-blocking so TUI never hangs. We still want the first
|
|
56
|
+
// toast trigger to work reliably, so we refresh config on-demand.
|
|
57
|
+
let config = DEFAULT_CONFIG;
|
|
58
|
+
let configLoaded = false;
|
|
59
|
+
let configInFlight = null;
|
|
60
|
+
let configMeta = createLoadConfigMeta();
|
|
61
|
+
async function refreshConfig() {
|
|
62
|
+
if (configInFlight)
|
|
63
|
+
return configInFlight;
|
|
64
|
+
configInFlight = (async () => {
|
|
65
|
+
try {
|
|
66
|
+
configMeta = createLoadConfigMeta();
|
|
67
|
+
config = await loadConfig(typedClient, configMeta);
|
|
68
|
+
configLoaded = true;
|
|
69
|
+
}
|
|
70
|
+
catch {
|
|
71
|
+
// Leave configLoaded=false so we can retry on next trigger.
|
|
72
|
+
config = DEFAULT_CONFIG;
|
|
73
|
+
}
|
|
74
|
+
finally {
|
|
75
|
+
configInFlight = null;
|
|
76
|
+
}
|
|
77
|
+
})();
|
|
78
|
+
return configInFlight;
|
|
79
|
+
}
|
|
80
|
+
function parseOptionalJsonArgs(input) {
|
|
81
|
+
const raw = input?.trim() || "";
|
|
82
|
+
if (!raw)
|
|
83
|
+
return { ok: true, value: {} };
|
|
84
|
+
try {
|
|
85
|
+
const parsed = JSON.parse(raw);
|
|
86
|
+
if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
|
|
87
|
+
return { ok: false, error: 'Arguments must be a JSON object (e.g. {"force":true}).' };
|
|
88
|
+
}
|
|
89
|
+
return { ok: true, value: parsed };
|
|
90
|
+
}
|
|
91
|
+
catch {
|
|
92
|
+
return { ok: false, error: "Failed to parse JSON arguments." };
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
// Best-effort async init (do not await)
|
|
96
|
+
void (async () => {
|
|
97
|
+
await refreshConfig();
|
|
98
|
+
try {
|
|
99
|
+
await typedClient.app.log({
|
|
100
|
+
body: {
|
|
101
|
+
service: "quota-toast",
|
|
102
|
+
level: "info",
|
|
103
|
+
message: "plugin initialized",
|
|
104
|
+
extra: {
|
|
105
|
+
configLoaded,
|
|
106
|
+
configSource: configMeta.source,
|
|
107
|
+
configPaths: configMeta.paths,
|
|
108
|
+
enabledProviders: config.enabledProviders,
|
|
109
|
+
minIntervalMs: config.minIntervalMs,
|
|
110
|
+
googleModels: config.googleModels,
|
|
111
|
+
showOnIdle: config.showOnIdle,
|
|
112
|
+
showOnQuestion: config.showOnQuestion,
|
|
113
|
+
showOnCompact: config.showOnCompact,
|
|
114
|
+
showOnBothFail: config.showOnBothFail,
|
|
115
|
+
},
|
|
116
|
+
},
|
|
117
|
+
});
|
|
118
|
+
}
|
|
119
|
+
catch {
|
|
120
|
+
// ignore
|
|
121
|
+
}
|
|
122
|
+
})();
|
|
123
|
+
// If disabled in config, it'll be picked up on first trigger; we can't
|
|
124
|
+
// reliably read config synchronously without risking TUI startup.
|
|
125
|
+
/**
|
|
126
|
+
* Log a message (debug level)
|
|
127
|
+
*/
|
|
128
|
+
async function log(message, extra) {
|
|
129
|
+
try {
|
|
130
|
+
await typedClient.app.log({
|
|
131
|
+
body: {
|
|
132
|
+
service: "quota-toast",
|
|
133
|
+
level: "debug",
|
|
134
|
+
message,
|
|
135
|
+
extra,
|
|
136
|
+
},
|
|
137
|
+
});
|
|
138
|
+
}
|
|
139
|
+
catch {
|
|
140
|
+
// Ignore logging errors
|
|
141
|
+
}
|
|
142
|
+
}
|
|
143
|
+
/**
|
|
144
|
+
* Check if session is a subagent session
|
|
145
|
+
*/
|
|
146
|
+
async function isSubagentSession(sessionID) {
|
|
147
|
+
try {
|
|
148
|
+
const response = await typedClient.session.get({ path: { id: sessionID } });
|
|
149
|
+
// Subagent sessions have a parentID
|
|
150
|
+
return !!response.data?.parentID;
|
|
151
|
+
}
|
|
152
|
+
catch {
|
|
153
|
+
// If we can't determine, assume it's a primary session
|
|
154
|
+
return false;
|
|
155
|
+
}
|
|
156
|
+
}
|
|
157
|
+
function formatDebugInfo(params) {
|
|
158
|
+
const availability = params.availability
|
|
159
|
+
? params.availability.map((x) => `${x.id}=${x.ok ? "ok" : "no"}`).join(" ")
|
|
160
|
+
: "unknown";
|
|
161
|
+
const providers = params.enabledProviders.length > 0 ? params.enabledProviders.join(",") : "(none)";
|
|
162
|
+
const modelPart = params.currentModel ? ` model=${params.currentModel}` : "";
|
|
163
|
+
const paths = configMeta.paths.length > 0 ? configMeta.paths.join(" | ") : "(none)";
|
|
164
|
+
return [
|
|
165
|
+
`Quota Toast Debug (opencode-quota)`,
|
|
166
|
+
`trigger=${params.trigger} reason=${params.reason}`,
|
|
167
|
+
`configSource=${configMeta.source} paths=${paths}`,
|
|
168
|
+
`enabled=${config.enabled} providers=${providers}${modelPart}`,
|
|
169
|
+
`available=${availability}`,
|
|
170
|
+
].join("\n");
|
|
171
|
+
}
|
|
172
|
+
async function fetchQuotaMessage(trigger) {
|
|
173
|
+
// Ensure we have loaded config at least once. If load fails, we keep trying
|
|
174
|
+
// on subsequent triggers.
|
|
175
|
+
if (!configLoaded) {
|
|
176
|
+
await refreshConfig();
|
|
177
|
+
}
|
|
178
|
+
if (!config.enabled) {
|
|
179
|
+
return config.debug
|
|
180
|
+
? formatDebugInfo({ trigger, reason: "disabled", enabledProviders: [] })
|
|
181
|
+
: null;
|
|
182
|
+
}
|
|
183
|
+
const providers = getProviders().filter((p) => config.enabledProviders.includes(p.id));
|
|
184
|
+
// Providers are opt-in; when none are enabled, do nothing.
|
|
185
|
+
if (providers.length === 0) {
|
|
186
|
+
return config.debug
|
|
187
|
+
? formatDebugInfo({ trigger, reason: "enabledProviders empty", enabledProviders: [] })
|
|
188
|
+
: null;
|
|
189
|
+
}
|
|
190
|
+
let currentModel;
|
|
191
|
+
if (config.onlyCurrentModel) {
|
|
192
|
+
try {
|
|
193
|
+
const configResponse = await typedClient.config.get();
|
|
194
|
+
currentModel = configResponse.data?.model;
|
|
195
|
+
}
|
|
196
|
+
catch {
|
|
197
|
+
currentModel = undefined;
|
|
198
|
+
}
|
|
199
|
+
}
|
|
200
|
+
const ctx = {
|
|
201
|
+
client: typedClient,
|
|
202
|
+
config: {
|
|
203
|
+
googleModels: config.googleModels,
|
|
204
|
+
toastStyle: config.toastStyle,
|
|
205
|
+
},
|
|
206
|
+
};
|
|
207
|
+
const filtered = config.onlyCurrentModel && currentModel
|
|
208
|
+
? providers.filter((p) => p.matchesCurrentModel ? p.matchesCurrentModel(currentModel) : true)
|
|
209
|
+
: providers;
|
|
210
|
+
// availability checks are cheap, do them in parallel
|
|
211
|
+
const avail = await Promise.all(filtered.map(async (p) => ({ p, ok: await p.isAvailable(ctx) })));
|
|
212
|
+
const active = avail.filter((x) => x.ok).map((x) => x.p);
|
|
213
|
+
if (active.length === 0) {
|
|
214
|
+
return config.debug
|
|
215
|
+
? formatDebugInfo({
|
|
216
|
+
trigger,
|
|
217
|
+
reason: "no enabled providers available",
|
|
218
|
+
currentModel,
|
|
219
|
+
enabledProviders: config.enabledProviders,
|
|
220
|
+
availability: avail.map((x) => ({ id: x.p.id, ok: x.ok })),
|
|
221
|
+
})
|
|
222
|
+
: null;
|
|
223
|
+
}
|
|
224
|
+
const results = await Promise.all(active.map((p) => p.fetch(ctx)));
|
|
225
|
+
const entries = results.flatMap((r) => r.entries);
|
|
226
|
+
const errors = results.flatMap((r) => r.errors);
|
|
227
|
+
const attemptedAny = results.some((r) => r.attempted);
|
|
228
|
+
if (entries.length > 0) {
|
|
229
|
+
const formatted = formatQuotaRows({
|
|
230
|
+
version: "1.0.0",
|
|
231
|
+
layout: config.layout,
|
|
232
|
+
entries,
|
|
233
|
+
errors,
|
|
234
|
+
style: config.toastStyle,
|
|
235
|
+
});
|
|
236
|
+
if (!config.debug)
|
|
237
|
+
return formatted;
|
|
238
|
+
const debugFooter = `\n\n[debug] src=${configMeta.source} providers=${config.enabledProviders.join(",") || "(none)"} avail=${avail
|
|
239
|
+
.map((x) => `${x.p.id}:${x.ok ? "ok" : "no"}`)
|
|
240
|
+
.join(" ")}`;
|
|
241
|
+
return formatted + debugFooter;
|
|
242
|
+
}
|
|
243
|
+
if (config.showOnBothFail && attemptedAny && errors.length > 0) {
|
|
244
|
+
if (!config.debug)
|
|
245
|
+
return "Quota unavailable";
|
|
246
|
+
return ("Quota unavailable" +
|
|
247
|
+
"\n\n" +
|
|
248
|
+
formatDebugInfo({
|
|
249
|
+
trigger,
|
|
250
|
+
reason: "all providers failed",
|
|
251
|
+
currentModel,
|
|
252
|
+
enabledProviders: config.enabledProviders,
|
|
253
|
+
availability: avail.map((x) => ({ id: x.p.id, ok: x.ok })),
|
|
254
|
+
}));
|
|
255
|
+
}
|
|
256
|
+
return config.debug
|
|
257
|
+
? formatDebugInfo({
|
|
258
|
+
trigger,
|
|
259
|
+
reason: "no entries",
|
|
260
|
+
currentModel,
|
|
261
|
+
enabledProviders: config.enabledProviders,
|
|
262
|
+
availability: avail.map((x) => ({ id: x.p.id, ok: x.ok })),
|
|
263
|
+
})
|
|
264
|
+
: null;
|
|
265
|
+
}
|
|
266
|
+
/**
|
|
267
|
+
* Show quota toast for a session
|
|
268
|
+
*/
|
|
269
|
+
async function showQuotaToast(sessionID, trigger) {
|
|
270
|
+
// Check if subagent session
|
|
271
|
+
if (await isSubagentSession(sessionID)) {
|
|
272
|
+
await log("Skipping toast for subagent session", { sessionID, trigger });
|
|
273
|
+
return;
|
|
274
|
+
}
|
|
275
|
+
// Get or fetch quota (with caching/throttling)
|
|
276
|
+
// If debug is enabled, bypass caching so the toast reflects current state.
|
|
277
|
+
function shouldCacheToastMessage(msg) {
|
|
278
|
+
// Cache when we have any quota row (which always includes a "NN%" token).
|
|
279
|
+
// Do not cache when output is only error rows (rendered as "label: message").
|
|
280
|
+
const lines = msg.split("\n");
|
|
281
|
+
return lines.some((l) => /\b\d{1,3}%\b/.test(l) && !/:\s/.test(l));
|
|
282
|
+
}
|
|
283
|
+
const message = config.debug
|
|
284
|
+
? await fetchQuotaMessage(trigger)
|
|
285
|
+
: await getOrFetchWithCacheControl(async () => {
|
|
286
|
+
const msg = await fetchQuotaMessage(trigger);
|
|
287
|
+
const cache = msg ? shouldCacheToastMessage(msg) : true;
|
|
288
|
+
return { message: msg, cache };
|
|
289
|
+
}, config.minIntervalMs);
|
|
290
|
+
if (!message) {
|
|
291
|
+
await log("No quota message to display", { trigger });
|
|
292
|
+
return;
|
|
293
|
+
}
|
|
294
|
+
if (!config.enableToast) {
|
|
295
|
+
await log("Toast disabled (enableToast=false)", { trigger });
|
|
296
|
+
return;
|
|
297
|
+
}
|
|
298
|
+
// Show toast
|
|
299
|
+
try {
|
|
300
|
+
await typedClient.tui.showToast({
|
|
301
|
+
body: {
|
|
302
|
+
message,
|
|
303
|
+
variant: "info",
|
|
304
|
+
duration: config.toastDurationMs,
|
|
305
|
+
},
|
|
306
|
+
});
|
|
307
|
+
await log("Displayed quota toast", { message, trigger });
|
|
308
|
+
}
|
|
309
|
+
catch (err) {
|
|
310
|
+
await log("Failed to show toast", {
|
|
311
|
+
error: err instanceof Error ? err.message : String(err),
|
|
312
|
+
});
|
|
313
|
+
}
|
|
314
|
+
}
|
|
315
|
+
async function fetchQuotaCommandMessage(trigger) {
|
|
316
|
+
if (!configLoaded)
|
|
317
|
+
await refreshConfig();
|
|
318
|
+
if (!config.enabled)
|
|
319
|
+
return null;
|
|
320
|
+
const providers = getProviders().filter((p) => config.enabledProviders.includes(p.id));
|
|
321
|
+
if (providers.length === 0)
|
|
322
|
+
return null;
|
|
323
|
+
const ctx = {
|
|
324
|
+
client: typedClient,
|
|
325
|
+
config: {
|
|
326
|
+
googleModels: config.googleModels,
|
|
327
|
+
// Always format /quota in grouped mode for a more dashboard-like look.
|
|
328
|
+
toastStyle: "grouped",
|
|
329
|
+
},
|
|
330
|
+
};
|
|
331
|
+
const avail = await Promise.all(providers.map(async (p) => ({ p, ok: await p.isAvailable(ctx) })));
|
|
332
|
+
const active = avail.filter((x) => x.ok).map((x) => x.p);
|
|
333
|
+
if (active.length === 0)
|
|
334
|
+
return null;
|
|
335
|
+
const results = await Promise.all(active.map((p) => p.fetch(ctx)));
|
|
336
|
+
const entries = results.flatMap((r) => r.entries);
|
|
337
|
+
const errors = results.flatMap((r) => r.errors);
|
|
338
|
+
if (entries.length === 0)
|
|
339
|
+
return null;
|
|
340
|
+
return formatQuotaCommand({ entries, errors });
|
|
341
|
+
}
|
|
342
|
+
async function buildQuotaReport(params) {
|
|
343
|
+
const result = await aggregateUsage({ sinceMs: params.sinceMs, untilMs: params.untilMs });
|
|
344
|
+
return formatQuotaStatsReport({
|
|
345
|
+
title: params.title,
|
|
346
|
+
result,
|
|
347
|
+
topModels: params.topModels,
|
|
348
|
+
topSessions: params.topSessions,
|
|
349
|
+
focusSessionID: params.sessionID,
|
|
350
|
+
});
|
|
351
|
+
}
|
|
352
|
+
async function buildStatusReport(params) {
|
|
353
|
+
await refreshConfig();
|
|
354
|
+
let currentModel;
|
|
355
|
+
try {
|
|
356
|
+
const configResponse = await typedClient.config.get();
|
|
357
|
+
currentModel = configResponse.data?.model;
|
|
358
|
+
}
|
|
359
|
+
catch {
|
|
360
|
+
currentModel = undefined;
|
|
361
|
+
}
|
|
362
|
+
const providers = getProviders();
|
|
363
|
+
const availability = await Promise.all(providers.map(async (p) => {
|
|
364
|
+
let ok = false;
|
|
365
|
+
try {
|
|
366
|
+
ok = await p.isAvailable({
|
|
367
|
+
client: typedClient,
|
|
368
|
+
config: { googleModels: config.googleModels },
|
|
369
|
+
});
|
|
370
|
+
}
|
|
371
|
+
catch {
|
|
372
|
+
ok = false;
|
|
373
|
+
}
|
|
374
|
+
return {
|
|
375
|
+
id: p.id,
|
|
376
|
+
enabled: config.enabledProviders.includes(p.id),
|
|
377
|
+
available: ok,
|
|
378
|
+
matchesCurrentModel: typeof p.matchesCurrentModel === "function" && currentModel
|
|
379
|
+
? p.matchesCurrentModel(currentModel)
|
|
380
|
+
: undefined,
|
|
381
|
+
};
|
|
382
|
+
}));
|
|
383
|
+
const refresh = params.refreshGoogleTokens
|
|
384
|
+
? await refreshGoogleTokensForAllAccounts({ skewMs: params.skewMs, force: params.force })
|
|
385
|
+
: null;
|
|
386
|
+
return await buildQuotaStatusReport({
|
|
387
|
+
configSource: configMeta.source,
|
|
388
|
+
configPaths: configMeta.paths,
|
|
389
|
+
enabledProviders: config.enabledProviders,
|
|
390
|
+
onlyCurrentModel: config.onlyCurrentModel,
|
|
391
|
+
currentModel,
|
|
392
|
+
providerAvailability: availability,
|
|
393
|
+
googleRefresh: refresh
|
|
394
|
+
? {
|
|
395
|
+
attempted: true,
|
|
396
|
+
total: refresh.total,
|
|
397
|
+
successCount: refresh.successCount,
|
|
398
|
+
failures: refresh.failures,
|
|
399
|
+
}
|
|
400
|
+
: { attempted: false },
|
|
401
|
+
});
|
|
402
|
+
}
|
|
403
|
+
// Return hook implementations
|
|
404
|
+
return {
|
|
405
|
+
// Register built-in slash commands (in addition to /tool quota_*)
|
|
406
|
+
config: async (input) => {
|
|
407
|
+
const cfg = input;
|
|
408
|
+
cfg.command ??= {};
|
|
409
|
+
cfg.command["quota"] = {
|
|
410
|
+
template: "/quota",
|
|
411
|
+
description: "Show quota toast output in chat.",
|
|
412
|
+
};
|
|
413
|
+
cfg.command["quota_daily"] = {
|
|
414
|
+
template: "/quota_daily",
|
|
415
|
+
description: "Token + official API cost summary for the last 24 hours (rolling).",
|
|
416
|
+
};
|
|
417
|
+
cfg.command["quota_weekly"] = {
|
|
418
|
+
template: "/quota_weekly",
|
|
419
|
+
description: "Token + official API cost summary for the last 7 days (rolling).",
|
|
420
|
+
};
|
|
421
|
+
cfg.command["quota_monthly"] = {
|
|
422
|
+
template: "/quota_monthly",
|
|
423
|
+
description: "Token + official API cost summary for the last 30 days (rolling).",
|
|
424
|
+
};
|
|
425
|
+
cfg.command["quota_all"] = {
|
|
426
|
+
template: "/quota_all",
|
|
427
|
+
description: "Token + official API cost summary for all locally saved OpenCode history.",
|
|
428
|
+
};
|
|
429
|
+
cfg.command["quota_status"] = {
|
|
430
|
+
template: "/quota_status",
|
|
431
|
+
description: "Diagnostics for toast + pricing + local storage (includes unknown pricing report).",
|
|
432
|
+
};
|
|
433
|
+
},
|
|
434
|
+
"command.execute.before": async (input) => {
|
|
435
|
+
const cmd = input.command;
|
|
436
|
+
const sessionID = input.sessionID;
|
|
437
|
+
if (cmd === "quota") {
|
|
438
|
+
// Separate cache for /quota so it doesn't pollute the toast cache.
|
|
439
|
+
let quotaCache = globalThis.__opencodeQuotaCommandCache;
|
|
440
|
+
if (!quotaCache) {
|
|
441
|
+
quotaCache = { message: "", timestamp: 0 };
|
|
442
|
+
globalThis.__opencodeQuotaCommandCache = quotaCache;
|
|
443
|
+
}
|
|
444
|
+
const now = Date.now();
|
|
445
|
+
const cached = quotaCache.timestamp && now - quotaCache.timestamp < config.minIntervalMs
|
|
446
|
+
? quotaCache.message
|
|
447
|
+
: null;
|
|
448
|
+
const msg = cached
|
|
449
|
+
? cached
|
|
450
|
+
: await (quotaCache.inFlight ??
|
|
451
|
+
(quotaCache.inFlight = (async () => {
|
|
452
|
+
try {
|
|
453
|
+
return await fetchQuotaCommandMessage("command:/quota");
|
|
454
|
+
}
|
|
455
|
+
finally {
|
|
456
|
+
quotaCache.inFlight = undefined;
|
|
457
|
+
}
|
|
458
|
+
})()));
|
|
459
|
+
if (msg) {
|
|
460
|
+
quotaCache.message = msg;
|
|
461
|
+
quotaCache.timestamp = Date.now();
|
|
462
|
+
}
|
|
463
|
+
if (!msg) {
|
|
464
|
+
await injectRawOutput(sessionID, "Quota unavailable");
|
|
465
|
+
throw new Error("__QUOTA_COMMAND_HANDLED__");
|
|
466
|
+
}
|
|
467
|
+
await injectRawOutput(sessionID, msg);
|
|
468
|
+
throw new Error("__QUOTA_COMMAND_HANDLED__");
|
|
469
|
+
}
|
|
470
|
+
const untilMs = Date.now();
|
|
471
|
+
if (cmd === "quota_daily") {
|
|
472
|
+
const sinceMs = untilMs - 24 * 60 * 60 * 1000;
|
|
473
|
+
const out = await buildQuotaReport({ title: "Quota Daily", sinceMs, untilMs, sessionID });
|
|
474
|
+
await injectRawOutput(sessionID, out);
|
|
475
|
+
throw new Error("__QUOTA_COMMAND_HANDLED__");
|
|
476
|
+
}
|
|
477
|
+
if (cmd === "quota_weekly") {
|
|
478
|
+
const sinceMs = untilMs - 7 * 24 * 60 * 60 * 1000;
|
|
479
|
+
const out = await buildQuotaReport({ title: "Quota Weekly", sinceMs, untilMs, sessionID });
|
|
480
|
+
await injectRawOutput(sessionID, out);
|
|
481
|
+
throw new Error("__QUOTA_COMMAND_HANDLED__");
|
|
482
|
+
}
|
|
483
|
+
if (cmd === "quota_monthly") {
|
|
484
|
+
const sinceMs = untilMs - 30 * 24 * 60 * 60 * 1000;
|
|
485
|
+
const out = await buildQuotaReport({ title: "Quota Monthly", sinceMs, untilMs, sessionID });
|
|
486
|
+
await injectRawOutput(sessionID, out);
|
|
487
|
+
throw new Error("__QUOTA_COMMAND_HANDLED__");
|
|
488
|
+
}
|
|
489
|
+
if (cmd === "quota_all") {
|
|
490
|
+
const out = await buildQuotaReport({
|
|
491
|
+
title: "Quota All",
|
|
492
|
+
sessionID,
|
|
493
|
+
topModels: 12,
|
|
494
|
+
topSessions: 12,
|
|
495
|
+
});
|
|
496
|
+
await injectRawOutput(sessionID, out);
|
|
497
|
+
throw new Error("__QUOTA_COMMAND_HANDLED__");
|
|
498
|
+
}
|
|
499
|
+
if (cmd === "quota_status") {
|
|
500
|
+
const parsed = parseOptionalJsonArgs(input.arguments);
|
|
501
|
+
if (!parsed.ok) {
|
|
502
|
+
await injectRawOutput(sessionID, `Invalid arguments for /quota_status\n\n${parsed.error}\n\nExample:\n/quota_status {\"refreshGoogleTokens\": true}`);
|
|
503
|
+
throw new Error("__QUOTA_COMMAND_HANDLED__");
|
|
504
|
+
}
|
|
505
|
+
const out = await buildStatusReport({
|
|
506
|
+
refreshGoogleTokens: parsed.value["refreshGoogleTokens"] === true,
|
|
507
|
+
skewMs: typeof parsed.value["skewMs"] === "number"
|
|
508
|
+
? parsed.value["skewMs"]
|
|
509
|
+
: undefined,
|
|
510
|
+
force: parsed.value["force"] === true,
|
|
511
|
+
});
|
|
512
|
+
await injectRawOutput(sessionID, out);
|
|
513
|
+
throw new Error("__QUOTA_COMMAND_HANDLED__");
|
|
514
|
+
}
|
|
515
|
+
},
|
|
516
|
+
tool: {
|
|
517
|
+
quota_daily: tool({
|
|
518
|
+
description: "Token + official API cost summary for the last 24 hours (rolling).",
|
|
519
|
+
args: {},
|
|
520
|
+
async execute(_args, context) {
|
|
521
|
+
const untilMs = Date.now();
|
|
522
|
+
const sinceMs = untilMs - 24 * 60 * 60 * 1000;
|
|
523
|
+
const out = await buildQuotaReport({
|
|
524
|
+
title: "Quota Daily",
|
|
525
|
+
sinceMs,
|
|
526
|
+
untilMs,
|
|
527
|
+
sessionID: context.sessionID,
|
|
528
|
+
});
|
|
529
|
+
context.metadata({ title: "Quota Daily" });
|
|
530
|
+
await injectRawOutput(context.sessionID, out);
|
|
531
|
+
return ""; // Empty return - output already injected with noReply
|
|
532
|
+
},
|
|
533
|
+
}),
|
|
534
|
+
quota_weekly: tool({
|
|
535
|
+
description: "Token + official API cost summary for the last 7 days (rolling).",
|
|
536
|
+
args: {},
|
|
537
|
+
async execute(_args, context) {
|
|
538
|
+
const untilMs = Date.now();
|
|
539
|
+
const sinceMs = untilMs - 7 * 24 * 60 * 60 * 1000;
|
|
540
|
+
const out = await buildQuotaReport({
|
|
541
|
+
title: "Quota Weekly",
|
|
542
|
+
sinceMs,
|
|
543
|
+
untilMs,
|
|
544
|
+
sessionID: context.sessionID,
|
|
545
|
+
});
|
|
546
|
+
context.metadata({ title: "Quota Weekly" });
|
|
547
|
+
await injectRawOutput(context.sessionID, out);
|
|
548
|
+
return ""; // Empty return - output already injected with noReply
|
|
549
|
+
},
|
|
550
|
+
}),
|
|
551
|
+
quota_monthly: tool({
|
|
552
|
+
description: "Token + official API cost summary for the last 30 days (rolling).",
|
|
553
|
+
args: {},
|
|
554
|
+
async execute(_args, context) {
|
|
555
|
+
const untilMs = Date.now();
|
|
556
|
+
const sinceMs = untilMs - 30 * 24 * 60 * 60 * 1000;
|
|
557
|
+
const out = await buildQuotaReport({
|
|
558
|
+
title: "Quota Monthly",
|
|
559
|
+
sinceMs,
|
|
560
|
+
untilMs,
|
|
561
|
+
sessionID: context.sessionID,
|
|
562
|
+
});
|
|
563
|
+
context.metadata({ title: "Quota Monthly" });
|
|
564
|
+
await injectRawOutput(context.sessionID, out);
|
|
565
|
+
return ""; // Empty return - output already injected with noReply
|
|
566
|
+
},
|
|
567
|
+
}),
|
|
568
|
+
quota_all: tool({
|
|
569
|
+
description: "Token + official API cost summary for all locally saved OpenCode history.",
|
|
570
|
+
args: {},
|
|
571
|
+
async execute(_args, context) {
|
|
572
|
+
const out = await buildQuotaReport({
|
|
573
|
+
title: "Quota All",
|
|
574
|
+
sessionID: context.sessionID,
|
|
575
|
+
topModels: 12,
|
|
576
|
+
topSessions: 12,
|
|
577
|
+
});
|
|
578
|
+
context.metadata({ title: "Quota All" });
|
|
579
|
+
await injectRawOutput(context.sessionID, out);
|
|
580
|
+
return ""; // Empty return - output already injected with noReply
|
|
581
|
+
},
|
|
582
|
+
}),
|
|
583
|
+
quota_status: tool({
|
|
584
|
+
description: "Diagnostics for toast + pricing + local storage (includes unknown pricing report).",
|
|
585
|
+
args: {
|
|
586
|
+
refreshGoogleTokens: tool.schema
|
|
587
|
+
.boolean()
|
|
588
|
+
.optional()
|
|
589
|
+
.describe("If true, refresh Google Antigravity access tokens before reporting"),
|
|
590
|
+
skewMs: tool.schema
|
|
591
|
+
.number()
|
|
592
|
+
.int()
|
|
593
|
+
.min(0)
|
|
594
|
+
.optional()
|
|
595
|
+
.describe("Refresh tokens expiring within this window (ms). Default: 120000"),
|
|
596
|
+
force: tool.schema
|
|
597
|
+
.boolean()
|
|
598
|
+
.optional()
|
|
599
|
+
.describe("If true, refresh even if cached token looks valid"),
|
|
600
|
+
},
|
|
601
|
+
async execute(args, context) {
|
|
602
|
+
const out = await buildStatusReport({
|
|
603
|
+
refreshGoogleTokens: args.refreshGoogleTokens,
|
|
604
|
+
skewMs: args.skewMs,
|
|
605
|
+
force: args.force,
|
|
606
|
+
});
|
|
607
|
+
context.metadata({ title: "Quota Status" });
|
|
608
|
+
await injectRawOutput(context.sessionID, out);
|
|
609
|
+
return ""; // Empty return - output already injected with noReply
|
|
610
|
+
},
|
|
611
|
+
}),
|
|
612
|
+
},
|
|
613
|
+
// Event hook for session.idle and session.compacted
|
|
614
|
+
event: async ({ event }) => {
|
|
615
|
+
const sessionID = event.properties.sessionID;
|
|
616
|
+
if (!sessionID)
|
|
617
|
+
return;
|
|
618
|
+
if (event.type === "session.idle" && config.showOnIdle) {
|
|
619
|
+
await showQuotaToast(sessionID, "session.idle");
|
|
620
|
+
}
|
|
621
|
+
else if (event.type === "session.compacted" && config.showOnCompact) {
|
|
622
|
+
await showQuotaToast(sessionID, "session.compacted");
|
|
623
|
+
}
|
|
624
|
+
},
|
|
625
|
+
// Tool execute hook for question tool
|
|
626
|
+
"tool.execute.after": async (input) => {
|
|
627
|
+
if (input.tool === "question" && config.showOnQuestion) {
|
|
628
|
+
await showQuotaToast(input.sessionID, "question");
|
|
629
|
+
}
|
|
630
|
+
},
|
|
631
|
+
};
|
|
632
|
+
};
|
|
633
|
+
//# sourceMappingURL=plugin.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"plugin.js","sourceRoot":"","sources":["../src/plugin.ts"],"names":[],"mappings":"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"}
|