@broberg/ai-sdk 0.59.0 → 0.59.1
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/index.d.ts +9 -4
- package/dist/index.js +20 -10
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.d.ts
CHANGED
|
@@ -52,10 +52,15 @@ interface SearchCache {
|
|
|
52
52
|
get(key: string): SearchResult | undefined;
|
|
53
53
|
set(key: string, value: SearchResult, ttlMs: number): void;
|
|
54
54
|
}
|
|
55
|
-
/** Running spend per key (tenant + day). Async allowed, so it can live in a database.
|
|
55
|
+
/** Running spend per key (tenant + day). Async allowed, so it can live in a database.
|
|
56
|
+
* `reserve` must CHECK AND ADD in one atomic step (e.g. `UPDATE … SET spent = spent + ?
|
|
57
|
+
* WHERE spent + ? <= cap`) and say whether it fitted — a separate read-then-write lets
|
|
58
|
+
* parallel calls all pass a cap only one of them fits under. `release` gives a
|
|
59
|
+
* reservation back when the call fails. */
|
|
56
60
|
interface SearchCapStore {
|
|
61
|
+
reserve(key: string, usd: number, capUsd: number): boolean | Promise<boolean>;
|
|
62
|
+
release(key: string, usd: number): void | Promise<void>;
|
|
57
63
|
getSpent(key: string): number | Promise<number>;
|
|
58
|
-
addSpent(key: string, usd: number): void | Promise<void>;
|
|
59
64
|
}
|
|
60
65
|
interface SearchOptions {
|
|
61
66
|
/** false = no cache. Default: one in-process memory cache shared by all calls. */
|
|
@@ -2325,8 +2330,8 @@ declare const falStubAdapter: ProviderAdapter;
|
|
|
2325
2330
|
* wires the live adapters. */
|
|
2326
2331
|
declare const stubProviders: Record<string, ProviderAdapter>;
|
|
2327
2332
|
|
|
2328
|
-
declare const VERSION: "0.59.
|
|
2329
|
-
declare const SDK_TAG: "@broberg/ai-sdk@0.59.
|
|
2333
|
+
declare const VERSION: "0.59.1";
|
|
2334
|
+
declare const SDK_TAG: "@broberg/ai-sdk@0.59.1";
|
|
2330
2335
|
|
|
2331
2336
|
/** Built-in defaults. Every entry is overridable via AiConfig.defaults or a
|
|
2332
2337
|
* per-call override.
|
package/dist/index.js
CHANGED
|
@@ -192,9 +192,19 @@ var SearchBudgetExceededError = class extends Error {
|
|
|
192
192
|
var sharedCache = memorySearchCache();
|
|
193
193
|
var sharedCapStore = /* @__PURE__ */ (() => {
|
|
194
194
|
const m = /* @__PURE__ */ new Map();
|
|
195
|
-
return {
|
|
196
|
-
|
|
197
|
-
|
|
195
|
+
return {
|
|
196
|
+
// Synchronous, so check-and-add cannot interleave with another call.
|
|
197
|
+
reserve: (k, usd, cap) => {
|
|
198
|
+
const s = m.get(k) ?? 0;
|
|
199
|
+
if (s + usd > cap) return false;
|
|
200
|
+
m.set(k, s + usd);
|
|
201
|
+
return true;
|
|
202
|
+
},
|
|
203
|
+
release: (k, usd) => {
|
|
204
|
+
m.set(k, (m.get(k) ?? 0) - usd);
|
|
205
|
+
},
|
|
206
|
+
getSpent: (k) => m.get(k) ?? 0
|
|
207
|
+
};
|
|
198
208
|
})();
|
|
199
209
|
var copenhagenDay = (d) => new Intl.DateTimeFormat("en-CA", { timeZone: "Europe/Copenhagen" }).format(d);
|
|
200
210
|
async function callProvider(provider, req, opts) {
|
|
@@ -250,10 +260,10 @@ async function search(req, opts = {}) {
|
|
|
250
260
|
const key = searchCacheKey(provider, req);
|
|
251
261
|
const hit = cache?.get(key);
|
|
252
262
|
if (hit) return { items: hit.items, meta: { ...hit.meta, cached: true, costUsd: 0, latencyMs: 0 } };
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
263
|
+
const price = SEARCH_PRICE_USD[provider];
|
|
264
|
+
const cap = opts.dailyCapUsd ?? Infinity;
|
|
265
|
+
if (!await capStore.reserve(capKey, price, cap)) {
|
|
266
|
+
throw new SearchBudgetExceededError(tenant, day, cap, await capStore.getSpent(capKey), price);
|
|
257
267
|
}
|
|
258
268
|
const t0 = performance.now();
|
|
259
269
|
try {
|
|
@@ -264,7 +274,6 @@ async function search(req, opts = {}) {
|
|
|
264
274
|
meta: { provider, latencyMs, cached: false, costUsd: SEARCH_PRICE_USD[provider], ...out.requestId ? { requestId: out.requestId } : {} }
|
|
265
275
|
};
|
|
266
276
|
cache?.set(key, result, ttl);
|
|
267
|
-
await capStore.addSpent(capKey, result.meta.costUsd);
|
|
268
277
|
try {
|
|
269
278
|
await sink?.record(usageRow(provider, req, result.meta.costUsd, latencyMs));
|
|
270
279
|
} catch {
|
|
@@ -272,6 +281,7 @@ async function search(req, opts = {}) {
|
|
|
272
281
|
return result;
|
|
273
282
|
} catch (e) {
|
|
274
283
|
lastErr = e;
|
|
284
|
+
await capStore.release(capKey, price);
|
|
275
285
|
if (sink?.recordFailure) {
|
|
276
286
|
try {
|
|
277
287
|
await sink.recordFailure({
|
|
@@ -3819,8 +3829,8 @@ var aiConfigSchema = z.object({
|
|
|
3819
3829
|
import { randomUUID } from "crypto";
|
|
3820
3830
|
|
|
3821
3831
|
// src/version.ts
|
|
3822
|
-
var VERSION = "0.59.
|
|
3823
|
-
var SDK_TAG = "@broberg/ai-sdk@0.59.
|
|
3832
|
+
var VERSION = "0.59.1";
|
|
3833
|
+
var SDK_TAG = "@broberg/ai-sdk@0.59.1";
|
|
3824
3834
|
|
|
3825
3835
|
// src/cost/sinks/upmetrics.ts
|
|
3826
3836
|
function isRetryableStatus(status) {
|