@ultimat3/ai 5.0.1 → 7.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/package.json +10 -10
- package/src/budget.ts +8 -7
- package/src/llm-stream.ts +5 -3
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@ultimat3/ai",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "7.0.0",
|
|
4
4
|
"description": "LLM gateway, versioned prompts, evals as tests, embeddings, hybrid vector search, RAG",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"type": "module",
|
|
@@ -32,14 +32,14 @@
|
|
|
32
32
|
"test": "bun test"
|
|
33
33
|
},
|
|
34
34
|
"dependencies": {
|
|
35
|
-
"@ultimat3/action": "
|
|
36
|
-
"@ultimat3/cache": "
|
|
37
|
-
"@ultimat3/core": "
|
|
38
|
-
"@ultimat3/db": "
|
|
39
|
-
"@ultimat3/jobs": "
|
|
40
|
-
"@ultimat3/money": "
|
|
41
|
-
"@ultimat3/policy": "
|
|
42
|
-
"@ultimat3/schema": "
|
|
43
|
-
"@ultimat3/time": "
|
|
35
|
+
"@ultimat3/action": "7.0.0",
|
|
36
|
+
"@ultimat3/cache": "7.0.0",
|
|
37
|
+
"@ultimat3/core": "7.0.0",
|
|
38
|
+
"@ultimat3/db": "7.0.0",
|
|
39
|
+
"@ultimat3/jobs": "7.0.0",
|
|
40
|
+
"@ultimat3/money": "7.0.0",
|
|
41
|
+
"@ultimat3/policy": "7.0.0",
|
|
42
|
+
"@ultimat3/schema": "7.0.0",
|
|
43
|
+
"@ultimat3/time": "7.0.0"
|
|
44
44
|
}
|
|
45
45
|
}
|
package/src/budget.ts
CHANGED
|
@@ -4,12 +4,13 @@
|
|
|
4
4
|
// wrong answer that looks like a real one, and the caller has no signal anything happened.
|
|
5
5
|
// A thrown X_AI_BUDGET_EXCEEDED with the remaining count is strictly more useful.
|
|
6
6
|
//
|
|
7
|
-
// The carrier is an
|
|
8
|
-
//
|
|
9
|
-
//
|
|
10
|
-
//
|
|
7
|
+
// The carrier is an async context so nested calls (a RAG retrieval, a tool call that generates,
|
|
8
|
+
// an eval judge) all debit the same ledger without threading it through every signature. It opens
|
|
9
|
+
// through `@ultimat3/core`'s one lazy seam rather than constructing an `AsyncLocalStorage` here: a
|
|
10
|
+
// module-scope `new` threw at EVALUATION in a browser bundle, where the bundler stubs
|
|
11
|
+
// `node:async_hooks` to `{}`, and took every importer of `@ultimat3/ai` with it.
|
|
11
12
|
|
|
12
|
-
import {
|
|
13
|
+
import { asyncContext } from '@ultimat3/core';
|
|
13
14
|
import type { Money } from '@ultimat3/money';
|
|
14
15
|
import { assertSameCurrency } from '@ultimat3/money';
|
|
15
16
|
import { AiBudgetExceededError } from './errors';
|
|
@@ -307,7 +308,7 @@ function tighterMoney(a: Money | undefined, b: Money | undefined): Money | undef
|
|
|
307
308
|
return a.minor <= b.minor ? a : b;
|
|
308
309
|
}
|
|
309
310
|
|
|
310
|
-
const storage =
|
|
311
|
+
const storage = asyncContext<BudgetLedger>('an AI budget');
|
|
311
312
|
|
|
312
313
|
/** Run `fn` with `ledger` as the ambient budget for everything it awaits. */
|
|
313
314
|
export function withBudget<T>(ledger: BudgetLedger, fn: () => Promise<T>): Promise<T> {
|
|
@@ -316,5 +317,5 @@ export function withBudget<T>(ledger: BudgetLedger, fn: () => Promise<T>): Promi
|
|
|
316
317
|
|
|
317
318
|
/** The ambient ledger, or `undefined` outside a budget scope (spend is then unmetered). */
|
|
318
319
|
export function currentBudget(): BudgetLedger | undefined {
|
|
319
|
-
return storage.
|
|
320
|
+
return storage.get();
|
|
320
321
|
}
|
package/src/llm-stream.ts
CHANGED
|
@@ -21,7 +21,7 @@
|
|
|
21
21
|
* async chain — abandoning the iterator stops delivery, never the accounting.
|
|
22
22
|
*/
|
|
23
23
|
|
|
24
|
-
import {
|
|
24
|
+
import { asyncContext } from '@ultimat3/core';
|
|
25
25
|
import { AiTransportError } from './errors';
|
|
26
26
|
import type { Gateway } from './gateway';
|
|
27
27
|
import type { GenerateRequest, GenerateResult } from './provider';
|
|
@@ -102,7 +102,9 @@ export class LlmSink {
|
|
|
102
102
|
}
|
|
103
103
|
}
|
|
104
104
|
|
|
105
|
-
|
|
105
|
+
// Core's one lazy seam, never a construction here: a module-scope `new` threw at EVALUATION in a
|
|
106
|
+
// browser bundle, where the bundler stubs `node:async_hooks` to `{}`.
|
|
107
|
+
const sinks = asyncContext<LlmSink>('an LLM stream sink');
|
|
106
108
|
|
|
107
109
|
/** Mark everything `fn` awaits as a streamed invocation. */
|
|
108
110
|
export function withLlmSink<T>(sink: LlmSink, fn: () => Promise<T>): Promise<T> {
|
|
@@ -111,7 +113,7 @@ export function withLlmSink<T>(sink: LlmSink, fn: () => Promise<T>): Promise<T>
|
|
|
111
113
|
|
|
112
114
|
/** The sink of the streamed invocation this call belongs to, or `undefined` for a plain one. */
|
|
113
115
|
export function currentLlmSink(): LlmSink | undefined {
|
|
114
|
-
return sinks.
|
|
116
|
+
return sinks.get();
|
|
115
117
|
}
|
|
116
118
|
|
|
117
119
|
/**
|