@hashimkarim/usagestat-linux-x64-gnu 2.0.0-alpha.1 → 2.0.0-alpha.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.
Files changed (273) hide show
  1. package/LICENSE +0 -0
  2. package/native-manifest.json +365 -77
  3. package/package.json +49 -1
  4. package/plugins/UPSTREAM-LICENSES.md +109 -0
  5. package/plugins/abacus-ai/icon.svg +0 -0
  6. package/plugins/abacus-ai/plugin.js +0 -0
  7. package/plugins/abacus-ai/plugin.json +0 -0
  8. package/plugins/aiand/icon.svg +6 -0
  9. package/plugins/aiand/plugin.js +108 -0
  10. package/plugins/aiand/plugin.json +22 -0
  11. package/plugins/alibaba/icon-color.svg +0 -0
  12. package/plugins/alibaba/icon.svg +0 -0
  13. package/plugins/alibaba/plugin.js +0 -0
  14. package/plugins/alibaba/plugin.json +0 -0
  15. package/plugins/alibaba-token-plan/icon-color.svg +0 -0
  16. package/plugins/alibaba-token-plan/icon.svg +0 -0
  17. package/plugins/alibaba-token-plan/plugin.js +0 -0
  18. package/plugins/alibaba-token-plan/plugin.json +0 -0
  19. package/plugins/amp/icon-color.svg +0 -0
  20. package/plugins/amp/icon-conflict.svg +0 -0
  21. package/plugins/amp/icon.svg +0 -0
  22. package/plugins/amp/plugin.js +0 -0
  23. package/plugins/amp/plugin.json +0 -0
  24. package/plugins/antigravity/icon-color.svg +0 -0
  25. package/plugins/antigravity/icon-conflict.svg +0 -0
  26. package/plugins/antigravity/icon.svg +0 -0
  27. package/plugins/antigravity/plugin.js +0 -0
  28. package/plugins/antigravity/plugin.json +0 -0
  29. package/plugins/antigravity-cli/icon.svg +0 -0
  30. package/plugins/antigravity-cli/plugin.js +0 -0
  31. package/plugins/antigravity-cli/plugin.json +0 -0
  32. package/plugins/antigravity-ide/icon.svg +0 -0
  33. package/plugins/antigravity-ide/plugin.js +0 -0
  34. package/plugins/antigravity-ide/plugin.json +0 -0
  35. package/plugins/augment/icon.svg +0 -0
  36. package/plugins/augment/plugin.js +0 -0
  37. package/plugins/augment/plugin.json +0 -0
  38. package/plugins/aws-bedrock/icon-color.svg +0 -0
  39. package/plugins/aws-bedrock/icon.svg +0 -0
  40. package/plugins/aws-bedrock/plugin.js +0 -0
  41. package/plugins/aws-bedrock/plugin.json +0 -0
  42. package/plugins/azure-openai/icon-color.svg +0 -0
  43. package/plugins/azure-openai/icon.svg +0 -0
  44. package/plugins/azure-openai/plugin.js +0 -0
  45. package/plugins/azure-openai/plugin.json +0 -0
  46. package/plugins/chutes/icon.svg +0 -0
  47. package/plugins/chutes/plugin.js +0 -0
  48. package/plugins/chutes/plugin.json +0 -0
  49. package/plugins/claude/icon-color.svg +0 -0
  50. package/plugins/claude/icon.svg +0 -0
  51. package/plugins/claude/plugin.js +70 -23
  52. package/plugins/claude/plugin.json +0 -0
  53. package/plugins/clawrouter/icon.svg +7 -0
  54. package/plugins/clawrouter/plugin.js +45 -0
  55. package/plugins/clawrouter/plugin.json +22 -0
  56. package/plugins/clinepass/icon.svg +4 -0
  57. package/plugins/clinepass/plugin.js +71 -0
  58. package/plugins/clinepass/plugin.json +23 -0
  59. package/plugins/codebuddy/plugin.js +331 -0
  60. package/plugins/codebuddy/plugin.json +30 -0
  61. package/plugins/codebuff/icon.svg +0 -0
  62. package/plugins/codebuff/plugin.js +0 -0
  63. package/plugins/codebuff/plugin.json +0 -0
  64. package/plugins/codex/icon-color.svg +0 -0
  65. package/plugins/codex/icon.svg +0 -0
  66. package/plugins/codex/plugin.js +7 -2
  67. package/plugins/codex/plugin.json +0 -0
  68. package/plugins/command-code/icon.svg +0 -0
  69. package/plugins/command-code/plugin.js +7 -0
  70. package/plugins/command-code/plugin.json +0 -0
  71. package/plugins/copilot/icon-color.svg +0 -0
  72. package/plugins/copilot/icon.svg +0 -0
  73. package/plugins/copilot/plugin.js +61 -9
  74. package/plugins/copilot/plugin.json +4 -1
  75. package/plugins/crof/icon.svg +0 -0
  76. package/plugins/crof/plugin.js +0 -0
  77. package/plugins/crof/plugin.json +0 -0
  78. package/plugins/crofai/icon.svg +0 -0
  79. package/plugins/crofai/plugin.js +0 -0
  80. package/plugins/crofai/plugin.json +0 -0
  81. package/plugins/cursor/icon-conflict.svg +0 -0
  82. package/plugins/cursor/icon.svg +0 -0
  83. package/plugins/cursor/plugin.js +46 -9
  84. package/plugins/cursor/plugin.json +3 -2
  85. package/plugins/cursor-nightly/icon.png +0 -0
  86. package/plugins/cursor-nightly/plugin.js +45 -8
  87. package/plugins/cursor-nightly/plugin.json +3 -2
  88. package/plugins/deepgram/icon.svg +0 -0
  89. package/plugins/deepgram/plugin.js +0 -0
  90. package/plugins/deepgram/plugin.json +0 -0
  91. package/plugins/deepinfra/icon.svg +4 -0
  92. package/plugins/deepinfra/plugin.js +97 -0
  93. package/plugins/deepinfra/plugin.json +28 -0
  94. package/plugins/deepseek/icon-color.svg +0 -0
  95. package/plugins/deepseek/icon.svg +0 -0
  96. package/plugins/deepseek/plugin.js +0 -0
  97. package/plugins/deepseek/plugin.json +0 -0
  98. package/plugins/devin/icon.svg +0 -0
  99. package/plugins/devin/plugin.js +111 -0
  100. package/plugins/devin/plugin.json +2 -1
  101. package/plugins/doubao/icon-color.svg +0 -0
  102. package/plugins/doubao/icon.svg +0 -0
  103. package/plugins/doubao/plugin.js +0 -0
  104. package/plugins/doubao/plugin.json +0 -0
  105. package/plugins/droid/icon.svg +0 -0
  106. package/plugins/droid/plugin.json +2 -1
  107. package/plugins/elevenlabs/icon.svg +0 -0
  108. package/plugins/elevenlabs/plugin.js +17 -2
  109. package/plugins/elevenlabs/plugin.json +0 -0
  110. package/plugins/factory/icon-conflict.svg +0 -0
  111. package/plugins/factory/icon.svg +0 -0
  112. package/plugins/factory/plugin.js +38 -14
  113. package/plugins/factory/plugin.json +2 -1
  114. package/plugins/fireworks-ai/icon.svg +0 -0
  115. package/plugins/fireworks-ai/plugin.js +0 -0
  116. package/plugins/fireworks-ai/plugin.json +0 -0
  117. package/plugins/gemini/icon-color.svg +0 -0
  118. package/plugins/gemini/icon.svg +0 -0
  119. package/plugins/gemini/plugin.js +0 -0
  120. package/plugins/gemini/plugin.json +0 -0
  121. package/plugins/grok/icon.svg +0 -0
  122. package/plugins/grok/plugin.js +30 -5
  123. package/plugins/grok/plugin.json +3 -1
  124. package/plugins/groqcloud/icon.svg +0 -0
  125. package/plugins/groqcloud/plugin.js +0 -0
  126. package/plugins/groqcloud/plugin.json +0 -0
  127. package/plugins/ibmbob/icon.svg +23 -0
  128. package/plugins/ibmbob/plugin.js +61 -0
  129. package/plugins/ibmbob/plugin.json +22 -0
  130. package/plugins/jetbrains-ai-assistant/icon-color.svg +0 -0
  131. package/plugins/jetbrains-ai-assistant/icon-conflict.svg +0 -0
  132. package/plugins/jetbrains-ai-assistant/icon.svg +0 -0
  133. package/plugins/jetbrains-ai-assistant/plugin.js +0 -0
  134. package/plugins/jetbrains-ai-assistant/plugin.json +0 -0
  135. package/plugins/kilo/icon.svg +0 -0
  136. package/plugins/kilo/plugin.js +0 -0
  137. package/plugins/kilo/plugin.json +0 -0
  138. package/plugins/kimi/icon-color.svg +0 -0
  139. package/plugins/kimi/icon-conflict.svg +0 -0
  140. package/plugins/kimi/icon.svg +0 -0
  141. package/plugins/kimi/plugin.js +122 -141
  142. package/plugins/kimi/plugin.json +5 -2
  143. package/plugins/kimi-k2/icon-color.svg +0 -0
  144. package/plugins/kimi-k2/icon.svg +0 -0
  145. package/plugins/kimi-k2/plugin.js +0 -0
  146. package/plugins/kimi-k2/plugin.json +0 -0
  147. package/plugins/kiro/icon-color.svg +0 -0
  148. package/plugins/kiro/icon-conflict.svg +0 -0
  149. package/plugins/kiro/icon.svg +0 -0
  150. package/plugins/kiro/plugin.js +49 -10
  151. package/plugins/kiro/plugin.json +3 -1
  152. package/plugins/litellm/icon.svg +0 -0
  153. package/plugins/litellm/plugin.js +0 -0
  154. package/plugins/litellm/plugin.json +0 -0
  155. package/plugins/llm-proxy/icon.svg +0 -0
  156. package/plugins/llm-proxy/plugin.js +0 -0
  157. package/plugins/llm-proxy/plugin.json +0 -0
  158. package/plugins/longcat/icon.svg +4 -0
  159. package/plugins/longcat/plugin.js +182 -0
  160. package/plugins/longcat/plugin.json +23 -0
  161. package/plugins/manus/icon.svg +0 -0
  162. package/plugins/manus/plugin.js +0 -0
  163. package/plugins/manus/plugin.json +0 -0
  164. package/plugins/mimo/icon.svg +0 -0
  165. package/plugins/mimo/plugin.js +0 -0
  166. package/plugins/mimo/plugin.json +0 -0
  167. package/plugins/minimax/icon-color.svg +0 -0
  168. package/plugins/minimax/icon-conflict.svg +0 -0
  169. package/plugins/minimax/icon.svg +0 -0
  170. package/plugins/minimax/plugin.js +25 -31
  171. package/plugins/minimax/plugin.json +0 -0
  172. package/plugins/mistral/icon-color.svg +0 -0
  173. package/plugins/mistral/icon.svg +0 -0
  174. package/plugins/mistral/plugin.js +0 -0
  175. package/plugins/mistral/plugin.json +0 -0
  176. package/plugins/moonshot/icon.svg +0 -0
  177. package/plugins/moonshot/plugin.js +8 -6
  178. package/plugins/moonshot/plugin.json +0 -0
  179. package/plugins/nanogpt/icon-color.svg +0 -0
  180. package/plugins/nanogpt/icon.svg +0 -0
  181. package/plugins/nanogpt/plugin.js +0 -0
  182. package/plugins/nanogpt/plugin.json +0 -0
  183. package/plugins/neuralwatt/icon.svg +0 -0
  184. package/plugins/neuralwatt/plugin.js +0 -0
  185. package/plugins/neuralwatt/plugin.json +0 -0
  186. package/plugins/notion/icon.svg +1 -0
  187. package/plugins/notion/plugin.js +282 -0
  188. package/plugins/notion/plugin.json +29 -0
  189. package/plugins/ollama/icon.svg +0 -0
  190. package/plugins/ollama/plugin.js +257 -56
  191. package/plugins/ollama/plugin.json +6 -3
  192. package/plugins/openai-api/icon.svg +0 -0
  193. package/plugins/openai-api/plugin.js +0 -0
  194. package/plugins/openai-api/plugin.json +0 -0
  195. package/plugins/opencode/icon.svg +0 -0
  196. package/plugins/opencode/plugin.js +0 -0
  197. package/plugins/opencode/plugin.json +0 -0
  198. package/plugins/opencode-go/icon-conflict.svg +0 -0
  199. package/plugins/opencode-go/icon.svg +0 -0
  200. package/plugins/opencode-go/plugin.js +78 -10
  201. package/plugins/opencode-go/plugin.json +5 -2
  202. package/plugins/openrouter/icon.svg +0 -0
  203. package/plugins/openrouter/plugin.js +371 -114
  204. package/plugins/openrouter/plugin.json +6 -0
  205. package/plugins/perplexity/icon-color.svg +0 -0
  206. package/plugins/perplexity/icon-conflict.svg +0 -0
  207. package/plugins/perplexity/icon.svg +0 -0
  208. package/plugins/perplexity/plugin.js +0 -0
  209. package/plugins/perplexity/plugin.json +0 -0
  210. package/plugins/poe/icon.svg +0 -0
  211. package/plugins/poe/plugin.js +24 -18
  212. package/plugins/poe/plugin.json +2 -0
  213. package/plugins/qoder/icon.svg +3 -0
  214. package/plugins/qoder/plugin.js +227 -0
  215. package/plugins/qoder/plugin.json +23 -0
  216. package/plugins/qwencloud/icon.svg +4 -0
  217. package/plugins/qwencloud/plugin.js +677 -0
  218. package/plugins/qwencloud/plugin.json +29 -0
  219. package/plugins/sakana/icon.svg +5 -0
  220. package/plugins/sakana/plugin.js +156 -0
  221. package/plugins/sakana/plugin.json +23 -0
  222. package/plugins/stepfun/icon-color.svg +0 -0
  223. package/plugins/stepfun/icon.svg +0 -0
  224. package/plugins/stepfun/plugin.js +0 -0
  225. package/plugins/stepfun/plugin.json +0 -0
  226. package/plugins/sub2api/icon.svg +4 -0
  227. package/plugins/sub2api/plugin.js +191 -0
  228. package/plugins/sub2api/plugin.json +16 -0
  229. package/plugins/synthetic/icon-conflict.svg +0 -0
  230. package/plugins/synthetic/icon.svg +0 -0
  231. package/plugins/synthetic/plugin.js +0 -0
  232. package/plugins/synthetic/plugin.json +0 -0
  233. package/plugins/t3chat/icon-color.svg +0 -0
  234. package/plugins/t3chat/icon.svg +0 -0
  235. package/plugins/t3chat/plugin.js +0 -0
  236. package/plugins/t3chat/plugin.json +0 -0
  237. package/plugins/venice/icon-color.svg +0 -0
  238. package/plugins/venice/icon.svg +0 -0
  239. package/plugins/venice/plugin.js +0 -0
  240. package/plugins/venice/plugin.json +0 -0
  241. package/plugins/vertex-ai/icon-color.svg +0 -0
  242. package/plugins/vertex-ai/icon.svg +0 -0
  243. package/plugins/vertex-ai/plugin.js +0 -0
  244. package/plugins/vertex-ai/plugin.json +0 -0
  245. package/plugins/warp/icon-color.svg +0 -0
  246. package/plugins/warp/icon.svg +0 -0
  247. package/plugins/warp/plugin.js +0 -0
  248. package/plugins/warp/plugin.json +0 -0
  249. package/plugins/wayfinder/icon.svg +5 -0
  250. package/plugins/wayfinder/plugin.js +47 -0
  251. package/plugins/wayfinder/plugin.json +16 -0
  252. package/plugins/windsurf/icon-conflict.svg +0 -0
  253. package/plugins/windsurf/icon.svg +0 -0
  254. package/plugins/windsurf/plugin.js +0 -0
  255. package/plugins/windsurf/plugin.json +0 -0
  256. package/plugins/xai/icon.svg +7 -0
  257. package/plugins/xai/plugin.js +162 -0
  258. package/plugins/xai/plugin.json +28 -0
  259. package/plugins/zai/icon-conflict.svg +0 -0
  260. package/plugins/zai/icon.svg +0 -0
  261. package/plugins/zai/plugin.js +111 -161
  262. package/plugins/zai/plugin.json +4 -1
  263. package/plugins/zed/icon.svg +0 -0
  264. package/plugins/zed/plugin.js +0 -0
  265. package/plugins/zed/plugin.json +0 -0
  266. package/plugins/zenmux/icon.svg +3 -0
  267. package/plugins/zenmux/plugin.js +102 -0
  268. package/plugins/zenmux/plugin.json +23 -0
  269. package/plugins/zoommate/icon.svg +1 -0
  270. package/plugins/zoommate/plugin.js +244 -0
  271. package/plugins/zoommate/plugin.json +29 -0
  272. package/usagestat +0 -0
  273. package/usagestatd +0 -0
@@ -0,0 +1,227 @@
1
+ (function () {
2
+ var GLOBAL_API = "https://qoder.com/api/v2/me/usages/big_model_credits";
3
+ var CHINA_API = "https://qoder.com.cn/api/v2/me/usages/big_model_credits";
4
+ var USER_AGENT = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/124.0.0.0 Safari/537.36";
5
+
6
+ function trim(value) {
7
+ return typeof value === "string" && value.trim() ? value.trim() : null;
8
+ }
9
+
10
+ function env(ctx, name) {
11
+ try {
12
+ return trim(ctx.host.env.get(name));
13
+ } catch (_) {
14
+ return null;
15
+ }
16
+ }
17
+
18
+ function setting(ctx, names) {
19
+ var settings = ctx.provider && ctx.provider.settings ? ctx.provider.settings : {};
20
+ for (var i = 0; i < names.length; i++) {
21
+ var value = trim(settings[names[i]]);
22
+ if (value) return value;
23
+ }
24
+ return null;
25
+ }
26
+
27
+ function normalizeCookie(raw) {
28
+ var header = trim(raw);
29
+ if (!header) return null;
30
+ if (header.slice(0, 7).toLowerCase() === "cookie:") header = header.slice(7).trim();
31
+ var pairs = [];
32
+ var chunks = header.split(";");
33
+ for (var i = 0; i < chunks.length; i++) {
34
+ var idx = chunks[i].indexOf("=");
35
+ if (idx < 0) continue;
36
+ var name = chunks[i].slice(0, idx).trim();
37
+ var value = chunks[i].slice(idx + 1).trim();
38
+ if (name && value) pairs.push(name + "=" + value);
39
+ }
40
+ return pairs.length ? pairs.join("; ") : null;
41
+ }
42
+
43
+ function cookieHeader(ctx) {
44
+ return normalizeCookie(ctx.provider && ctx.provider.cookieHeader) ||
45
+ normalizeCookie(setting(ctx, ["cookieHeader", "cookie"])) ||
46
+ normalizeCookie(env(ctx, "QODER_COOKIE"));
47
+ }
48
+
49
+ function requestRegion(ctx, url, referer, cookie) {
50
+ var result = ctx.util.requestJson({
51
+ method: "GET",
52
+ url: url,
53
+ headers: {
54
+ Cookie: cookie,
55
+ Accept: "application/json, text/plain, */*",
56
+ Referer: referer,
57
+ "User-Agent": USER_AGENT,
58
+ },
59
+ timeoutMs: 15000,
60
+ });
61
+ if (ctx.util.isAuthStatus(result.resp.status)) throw { auth: true, message: "Qoder session expired." };
62
+ if (result.resp.status < 200 || result.resp.status >= 300) throw "Qoder usage returned HTTP " + result.resp.status + ".";
63
+ if (!result.json || typeof result.json !== "object") throw "Failed to parse Qoder usage.";
64
+ return result.json;
65
+ }
66
+
67
+ function number(value) {
68
+ if (typeof value === "number" && Number.isFinite(value)) return value;
69
+ if (typeof value === "string" && value.trim()) {
70
+ var parsed = Number(value.replace(/,/g, ""));
71
+ if (Number.isFinite(parsed)) return parsed;
72
+ }
73
+ return null;
74
+ }
75
+
76
+ function first(obj, keys) {
77
+ if (!obj || typeof obj !== "object" || Array.isArray(obj)) return undefined;
78
+ for (var i = 0; i < keys.length; i++) {
79
+ if (obj[keys[i]] !== undefined && obj[keys[i]] !== null) return obj[keys[i]];
80
+ }
81
+ return undefined;
82
+ }
83
+
84
+ function stringFromKeys(obj, keys) {
85
+ var v = first(obj, keys);
86
+ return typeof v === "string" && v.trim() ? v.trim() : null;
87
+ }
88
+
89
+ function numberFromKeys(obj, keys) {
90
+ return number(first(obj, keys));
91
+ }
92
+
93
+ function parseDate(ctx, value) {
94
+ if (value === null || value === undefined || value === "") return null;
95
+ return ctx.util.toIso(value);
96
+ }
97
+
98
+ function normalizedPercent(value) {
99
+ var n = number(value);
100
+ if (n === null) return null;
101
+ if (n <= 1 && n >= 0) n *= 100;
102
+ return Math.max(0, Math.min(100, n));
103
+ }
104
+
105
+ function usagePercentage(used, total, remaining, provided) {
106
+ if (used < 0 || total < 0 || remaining < 0) throw "Qoder quota values must be nonnegative.";
107
+ if (total === 0) {
108
+ if (used !== 0 || remaining !== 0) throw "Qoder zero total quota has nonzero usage.";
109
+ return provided === null ? 100 : normalizedPercent(provided);
110
+ }
111
+ return provided === null ? used / total * 100 : normalizedPercent(provided);
112
+ }
113
+
114
+ function quotaSummary(root, containerKeys) {
115
+ var container = first(root, containerKeys);
116
+ if (!container || typeof container !== "object" || Array.isArray(container)) return null;
117
+ var summary = container.quotaSummary || container.quota_summary;
118
+ if (!summary || typeof summary !== "object" || Array.isArray(summary)) return null;
119
+ var used = numberFromKeys(summary, ["usedValue", "used_value"]);
120
+ var total = numberFromKeys(summary, ["limitValue", "limit_value"]);
121
+ if (used === null || total === null) throw "Missing Qoder quota summary values.";
122
+ var remaining = numberFromKeys(summary, ["remainingValue", "remaining_value"]);
123
+ if (remaining === null) remaining = Math.max(0, total - used);
124
+ var provided = numberFromKeys(summary, ["usagePercentage", "usage_percentage"]);
125
+ var unitRaw = stringFromKeys(summary, ["unit"]);
126
+ return {
127
+ used: used,
128
+ total: total,
129
+ remaining: remaining,
130
+ percentage: usagePercentage(used, total, remaining, provided),
131
+ unit: unitRaw && /^credits?$/i.test(unitRaw) ? "credits" : "units",
132
+ };
133
+ }
134
+
135
+ function mergeSummaries(a, b) {
136
+ var used = a.used + b.used;
137
+ var total = a.total + b.total;
138
+ var remaining = a.remaining + b.remaining;
139
+ return {
140
+ used: used,
141
+ total: total,
142
+ remaining: remaining,
143
+ percentage: usagePercentage(used, total, remaining, null),
144
+ unit: a.unit || b.unit || "credits",
145
+ };
146
+ }
147
+
148
+ function quotaSummarySnapshot(ctx, root, loginMethod) {
149
+ var base = quotaSummary(root, ["totalQuota", "total_quota"]);
150
+ if (!base) return null;
151
+ var shared = quotaSummary(root, ["sharedQuota", "shared_quota"]);
152
+ var merged = shared ? mergeSummaries(base, shared) : base;
153
+ var reset = parseDate(ctx, first(root, ["nextResetAt", "next_reset_at"]));
154
+ var detail = Math.round(merged.used) + "/" + Math.round(merged.total) + " " + (merged.unit || "credits") +
155
+ " used, " + Math.round(merged.remaining) + " remaining";
156
+ var opts = {
157
+ label: "Credits",
158
+ used: Math.max(0, Math.min(100, merged.percentage)),
159
+ limit: 100,
160
+ format: { kind: "percent" },
161
+ detail: detail,
162
+ };
163
+ if (reset) opts.resetsAt = reset;
164
+ return { displayName: "Qoder", source: "web", plan: loginMethod, lines: [ctx.line.progress(opts)] };
165
+ }
166
+
167
+ function collectCreditWindows(ctx, value, out) {
168
+ if (!value || typeof value !== "object") return;
169
+ if (Array.isArray(value)) {
170
+ for (var i = 0; i < value.length; i++) collectCreditWindows(ctx, value[i], out);
171
+ return;
172
+ }
173
+ var used = numberFromKeys(value, ["used", "usedCredits", "used_credits", "usage", "usedQuota", "used_quota"]);
174
+ var total = numberFromKeys(value, ["total", "totalCredits", "total_credits", "limit", "quota", "quotaLimit", "quota_limit"]);
175
+ var percent = normalizedPercent(first(value, ["usedPercent", "used_percent", "usagePercent", "usage_percent", "percent"]));
176
+ if (percent === null && used !== null && total !== null && total > 0) percent = used / total * 100;
177
+ if (percent !== null) {
178
+ var reset = parseDate(ctx, first(value, ["nextResetAt", "next_reset_at", "resetAt", "reset_at"]));
179
+ var detail = used !== null && total !== null ? Math.round(used) + "/" + Math.round(total) + " credits" : null;
180
+ var line = {
181
+ label: stringFromKeys(value, ["label", "name", "type"]) || "Credits",
182
+ used: Math.max(0, Math.min(100, percent)),
183
+ limit: 100,
184
+ format: { kind: "percent" },
185
+ };
186
+ if (reset) line.resetsAt = reset;
187
+ if (detail) line.detail = detail;
188
+ out.push(ctx.line.progress(line));
189
+ }
190
+ var keys = Object.keys(value);
191
+ for (var j = 0; j < keys.length; j++) collectCreditWindows(ctx, value[keys[j]], out);
192
+ }
193
+
194
+ function snapshotFromPayload(ctx, value, loginMethod) {
195
+ var root = value && value.data && typeof value.data === "object" ? value.data : value;
196
+ var summary = quotaSummarySnapshot(ctx, root, loginMethod);
197
+ if (summary) return summary;
198
+ var lines = [];
199
+ collectCreditWindows(ctx, root, lines);
200
+ lines.sort(function (a, b) { return b.used - a.used; });
201
+ if (!lines.length) throw "Missing Qoder credit usage.";
202
+ return { displayName: "Qoder", source: "web", plan: loginMethod, lines: lines };
203
+ }
204
+
205
+ function probe(ctx) {
206
+ var cookie = cookieHeader(ctx);
207
+ if (!cookie) throw "Qoder session not configured. Set QODER_COOKIE or provider cookieHeader.";
208
+ var authFailed = false;
209
+ var lastError = null;
210
+ var regions = [
211
+ [GLOBAL_API, "https://qoder.com/account/usage", "Qoder"],
212
+ [CHINA_API, "https://qoder.com.cn/account/usage", "Qoder China"],
213
+ ];
214
+ for (var i = 0; i < regions.length; i++) {
215
+ try {
216
+ return snapshotFromPayload(ctx, requestRegion(ctx, regions[i][0], regions[i][1], cookie), regions[i][2]);
217
+ } catch (error) {
218
+ if (error && error.auth) authFailed = true;
219
+ else lastError = error;
220
+ }
221
+ }
222
+ if (authFailed) throw "Qoder session expired.";
223
+ throw lastError || "No Qoder usage payload.";
224
+ }
225
+
226
+ globalThis.__openusage_plugin = { id: "qoder", probe: probe };
227
+ })();
@@ -0,0 +1,23 @@
1
+ {
2
+ "schemaVersion": 1,
3
+ "id": "qoder",
4
+ "name": "Qoder",
5
+ "version": "0.1.0",
6
+ "entry": "plugin.js",
7
+ "enabledByDefault": false,
8
+ "supportedModes": [
9
+ "web"
10
+ ],
11
+ "autoMode": "web",
12
+ "webUrl": "https://qoder.com",
13
+ "usageDashboardUrl": "https://qoder.com/account/usage",
14
+ "links": [
15
+ {
16
+ "label": "Dashboard",
17
+ "url": "https://qoder.com/account/usage"
18
+ }
19
+ ],
20
+ "envVars": [
21
+ "QODER_COOKIE"
22
+ ]
23
+ }
@@ -0,0 +1,4 @@
1
+ <svg width="200" height="200" viewBox="0 0 200 200" fill="none" xmlns="http://www.w3.org/2000/svg">
2
+ <path fill-rule="evenodd" clip-rule="evenodd" d="M100 12L120.5 47.5H161.5L141 83L161.5 118.5H120.5L100 154L79.5 118.5H38.5L59 83L38.5 47.5H79.5L100 12ZM100 58L113 83L100 108L87 83L100 58Z" fill="#111111"/>
3
+ <path d="M100 158C100 158 138 162 138 176C138 184 128 188 100 188C72 188 62 184 62 176C62 162 100 158 100 158Z" fill="#111111"/>
4
+ </svg>