hebbrix 2.1.0 → 2.2.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/CHANGELOG.md +27 -0
- package/README.md +16 -0
- package/dist/index.d.mts +246 -9
- package/dist/index.d.ts +246 -9
- package/dist/index.js +316 -42
- package/dist/index.mjs +312 -41
- package/package.json +4 -3
package/dist/index.mjs
CHANGED
|
@@ -1,3 +1,57 @@
|
|
|
1
|
+
// src/safety.ts
|
|
2
|
+
var REQUIRED_FIELDS = [
|
|
3
|
+
"no_match",
|
|
4
|
+
"abstain_recommended",
|
|
5
|
+
"query_confidence",
|
|
6
|
+
"grounding",
|
|
7
|
+
"evidence_ids",
|
|
8
|
+
"safety_contract_version"
|
|
9
|
+
];
|
|
10
|
+
function enforceSearchSafety(response, rowsKey = "results") {
|
|
11
|
+
const data = { ...response };
|
|
12
|
+
const rawRows = data[rowsKey];
|
|
13
|
+
const rows = Array.isArray(rawRows) ? rawRows.filter((row) => typeof row === "object" && row !== null) : [];
|
|
14
|
+
const missing = REQUIRED_FIELDS.filter(
|
|
15
|
+
(field) => !Object.prototype.hasOwnProperty.call(data, field)
|
|
16
|
+
);
|
|
17
|
+
let reason;
|
|
18
|
+
if (missing.length > 0) {
|
|
19
|
+
reason = `missing_safety_fields:${missing.join(",")}`;
|
|
20
|
+
} else if (typeof data.no_match !== "boolean" || typeof data.abstain_recommended !== "boolean") {
|
|
21
|
+
reason = "invalid_abstention_fields";
|
|
22
|
+
} else if (typeof data.query_confidence !== "number" || !Number.isFinite(data.query_confidence) || data.query_confidence < 0 || data.query_confidence > 1) {
|
|
23
|
+
reason = "invalid_query_confidence";
|
|
24
|
+
} else if (typeof data.grounding !== "object" || data.grounding === null || Array.isArray(data.grounding)) {
|
|
25
|
+
reason = "invalid_grounding_receipt";
|
|
26
|
+
} else if (!Array.isArray(data.evidence_ids)) {
|
|
27
|
+
reason = "invalid_evidence_ids";
|
|
28
|
+
} else {
|
|
29
|
+
const evidenceIds = new Set(data.evidence_ids.map(String));
|
|
30
|
+
const rowIds = rows.map((row) => row.memory_id ?? row.id).filter((value) => typeof value === "string" && value.length > 0);
|
|
31
|
+
if (rowIds.some((value) => !evidenceIds.has(value))) {
|
|
32
|
+
reason = "rows_not_bound_to_evidence_ids";
|
|
33
|
+
} else if (data.no_match && (rowIds.length > 0 || evidenceIds.size > 0)) {
|
|
34
|
+
reason = "no_match_contains_evidence";
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
if (reason || data.no_match === true) {
|
|
38
|
+
data[rowsKey] = [];
|
|
39
|
+
if (rowsKey === "results") data.total = 0;
|
|
40
|
+
data.no_match = true;
|
|
41
|
+
data.abstain_recommended = true;
|
|
42
|
+
data.query_confidence = 0;
|
|
43
|
+
data.evidence_ids = [];
|
|
44
|
+
data.evidence_claims = [];
|
|
45
|
+
if (reason) {
|
|
46
|
+
data.sdk_safety_reason = reason;
|
|
47
|
+
data.grounding = { status: "no_grounded_match", reason };
|
|
48
|
+
}
|
|
49
|
+
} else if (data.degraded === true || data.abstain_recommended === true) {
|
|
50
|
+
data.sdk_safety_reason = "degraded_evidence_preserved";
|
|
51
|
+
}
|
|
52
|
+
return data;
|
|
53
|
+
}
|
|
54
|
+
|
|
1
55
|
// src/resources.ts
|
|
2
56
|
var BaseResource = class {
|
|
3
57
|
constructor(client) {
|
|
@@ -77,14 +131,104 @@ var MemoriesResource = class extends BaseResource {
|
|
|
77
131
|
* Create a new memory
|
|
78
132
|
*/
|
|
79
133
|
async create(params) {
|
|
80
|
-
|
|
134
|
+
if (!params.content?.trim() && !params.messages?.length) {
|
|
135
|
+
throw new TypeError("content or messages must be provided");
|
|
136
|
+
}
|
|
137
|
+
const { idempotency_key, ...input } = params;
|
|
138
|
+
return this.client.request("POST", "/v1/memories", {
|
|
139
|
+
headers: idempotency_key ? { "Idempotency-Key": idempotency_key } : void 0,
|
|
140
|
+
body: JSON.stringify({
|
|
141
|
+
source_type: "text",
|
|
142
|
+
metadata: {},
|
|
143
|
+
infer: false,
|
|
144
|
+
wait_for_index: false,
|
|
145
|
+
...input
|
|
146
|
+
})
|
|
147
|
+
});
|
|
148
|
+
}
|
|
149
|
+
/**
|
|
150
|
+
* Create up to 100 memories with one unambiguous readiness contract.
|
|
151
|
+
* `wait_for_index=true` resolves only for a fully searchable batch; a server
|
|
152
|
+
* deadline or indexing failure rejects the request instead of returning a
|
|
153
|
+
* successful processing receipt.
|
|
154
|
+
*/
|
|
155
|
+
async createBatch(params) {
|
|
156
|
+
if (!params.memories?.length || params.memories.length > 100) {
|
|
157
|
+
throw new TypeError("memories must contain between 1 and 100 items");
|
|
158
|
+
}
|
|
159
|
+
if (params.memories.some((item) => !item.content?.trim())) {
|
|
160
|
+
throw new TypeError("every batch memory must contain non-empty content");
|
|
161
|
+
}
|
|
162
|
+
const { idempotency_key, signal, ...body } = params;
|
|
163
|
+
const receipt = await this.client.request(
|
|
164
|
+
"POST",
|
|
165
|
+
"/v1/memories/batch",
|
|
166
|
+
{
|
|
167
|
+
headers: idempotency_key ? { "Idempotency-Key": idempotency_key } : void 0,
|
|
168
|
+
body: JSON.stringify({ wait_for_index: false, ...body }),
|
|
169
|
+
signal
|
|
170
|
+
}
|
|
171
|
+
);
|
|
172
|
+
if (params.wait_for_index && !(receipt.searchable === true && receipt.processing_status === "completed")) {
|
|
173
|
+
throw new Error(
|
|
174
|
+
"wait_for_index batch response was not fully searchable; retry with the same Idempotency-Key"
|
|
175
|
+
);
|
|
176
|
+
}
|
|
177
|
+
return receipt;
|
|
178
|
+
}
|
|
179
|
+
/** Poll every item in an asynchronous batch receipt until it is searchable. */
|
|
180
|
+
async waitForBatchSearchable(receipt, options = {}) {
|
|
181
|
+
const ids = [...new Set(receipt.memory_ids || [])];
|
|
182
|
+
if (!ids.length) {
|
|
183
|
+
throw new Error("batch receipt does not contain memory_ids");
|
|
184
|
+
}
|
|
185
|
+
const timeoutMs = Math.max(0, options.timeoutMs ?? 6e4);
|
|
186
|
+
const pollIntervalMs = Math.max(50, options.pollIntervalMs ?? 500);
|
|
187
|
+
const deadline = Date.now() + timeoutMs;
|
|
188
|
+
while (true) {
|
|
189
|
+
if (options.signal?.aborted) {
|
|
190
|
+
throw options.signal.reason || new Error("batch readiness polling was aborted");
|
|
191
|
+
}
|
|
192
|
+
const rows = await Promise.all(ids.map((id) => this.get(id)));
|
|
193
|
+
const terminal = rows.find(
|
|
194
|
+
(row) => ["failed", "cancelled", "canceled"].includes(
|
|
195
|
+
String(row.processing_status || "").toLowerCase()
|
|
196
|
+
)
|
|
197
|
+
);
|
|
198
|
+
if (terminal) {
|
|
199
|
+
throw new Error(
|
|
200
|
+
`memory ${terminal.id} indexing reached terminal state ${terminal.processing_status}`
|
|
201
|
+
);
|
|
202
|
+
}
|
|
203
|
+
if (rows.every((row) => row.searchable === true)) {
|
|
204
|
+
return {
|
|
205
|
+
...receipt,
|
|
206
|
+
processing_status: "completed",
|
|
207
|
+
searchable: true,
|
|
208
|
+
results: ids.map((id) => ({
|
|
209
|
+
id,
|
|
210
|
+
memory_id: id,
|
|
211
|
+
processing_status: "completed"
|
|
212
|
+
}))
|
|
213
|
+
};
|
|
214
|
+
}
|
|
215
|
+
if (Date.now() >= deadline) {
|
|
216
|
+
throw new Error(`batch was not searchable within ${timeoutMs}ms`);
|
|
217
|
+
}
|
|
218
|
+
await new Promise((resolve) => setTimeout(resolve, pollIntervalMs));
|
|
219
|
+
}
|
|
81
220
|
}
|
|
82
221
|
/**
|
|
83
222
|
* List memories
|
|
84
223
|
*/
|
|
85
|
-
async
|
|
224
|
+
async listPage(params = {}) {
|
|
86
225
|
return this.client.get("/v1/memories", params);
|
|
87
226
|
}
|
|
227
|
+
/** Back-compatible one-page convenience; use listPage for cursor metadata. */
|
|
228
|
+
async list(params = {}) {
|
|
229
|
+
const page = await this.listPage(params);
|
|
230
|
+
return page.items;
|
|
231
|
+
}
|
|
88
232
|
/**
|
|
89
233
|
* Get a specific memory
|
|
90
234
|
*/
|
|
@@ -104,30 +248,79 @@ var MemoriesResource = class extends BaseResource {
|
|
|
104
248
|
await this.client.delete(`/v1/memories/${memoryId}`);
|
|
105
249
|
}
|
|
106
250
|
};
|
|
251
|
+
var MemoryJobsResource = class extends BaseResource {
|
|
252
|
+
async get(jobId) {
|
|
253
|
+
return this.client.get(`/v1/memory-jobs/${jobId}`);
|
|
254
|
+
}
|
|
255
|
+
async wait(jobId, options = {}) {
|
|
256
|
+
const timeoutMs = Math.max(0, options.timeoutMs ?? 6e4);
|
|
257
|
+
const pollIntervalMs = Math.max(50, options.pollIntervalMs ?? 500);
|
|
258
|
+
const deadline = Date.now() + timeoutMs;
|
|
259
|
+
while (true) {
|
|
260
|
+
const receipt = await this.get(jobId);
|
|
261
|
+
const status = String(receipt.status || "").toLowerCase();
|
|
262
|
+
if (["completed", "failed", "cancelled", "canceled"].includes(status)) {
|
|
263
|
+
return receipt;
|
|
264
|
+
}
|
|
265
|
+
if (Date.now() >= deadline) {
|
|
266
|
+
throw new Error(`memory job ${jobId} did not finish in ${timeoutMs}ms`);
|
|
267
|
+
}
|
|
268
|
+
await new Promise((resolve) => setTimeout(resolve, pollIntervalMs));
|
|
269
|
+
}
|
|
270
|
+
}
|
|
271
|
+
};
|
|
272
|
+
var CorrectionsResource = class extends BaseResource {
|
|
273
|
+
async create(params) {
|
|
274
|
+
const { idempotency_key, ...body } = params;
|
|
275
|
+
return this.client.request("POST", "/v1/corrections", {
|
|
276
|
+
headers: idempotency_key ? { "Idempotency-Key": idempotency_key } : void 0,
|
|
277
|
+
body: JSON.stringify({
|
|
278
|
+
correction_type: "preference",
|
|
279
|
+
confidence: 1,
|
|
280
|
+
...body
|
|
281
|
+
})
|
|
282
|
+
});
|
|
283
|
+
}
|
|
284
|
+
async relevant(params) {
|
|
285
|
+
return this.client.get("/v1/corrections/relevant", {
|
|
286
|
+
include_global: false,
|
|
287
|
+
limit: 10,
|
|
288
|
+
...params
|
|
289
|
+
});
|
|
290
|
+
}
|
|
291
|
+
async get(correctionId) {
|
|
292
|
+
return this.client.get(`/v1/corrections/${correctionId}`);
|
|
293
|
+
}
|
|
294
|
+
async delete(correctionId) {
|
|
295
|
+
return this.client.delete(`/v1/corrections/${correctionId}`);
|
|
296
|
+
}
|
|
297
|
+
};
|
|
107
298
|
var SearchResource = class extends BaseResource {
|
|
108
299
|
/**
|
|
109
300
|
* Search memories
|
|
110
301
|
*/
|
|
111
302
|
async search(params) {
|
|
112
|
-
const response = await this.
|
|
113
|
-
query: params.query,
|
|
114
|
-
collection_id: params.collection_id,
|
|
115
|
-
limit: params.limit || 10,
|
|
116
|
-
search_type: params.search_type || "hybrid",
|
|
117
|
-
filters: params.filters || {}
|
|
118
|
-
});
|
|
303
|
+
const response = await this.searchWithProof(params);
|
|
119
304
|
return response.results;
|
|
120
305
|
}
|
|
121
306
|
/** Search while preserving the automatic ProofLoop evidence context. */
|
|
122
307
|
async searchWithProof(params) {
|
|
123
|
-
|
|
308
|
+
const response = await this.client.post("/v1/search", {
|
|
124
309
|
query: params.query,
|
|
125
310
|
collection_id: params.collection_id,
|
|
126
311
|
user_id: params.user_id,
|
|
312
|
+
agent_id: params.agent_id,
|
|
313
|
+
run_id: params.run_id,
|
|
127
314
|
limit: params.limit || 10,
|
|
128
315
|
search_type: params.search_type || "hybrid",
|
|
129
|
-
filters: params.filters || {}
|
|
316
|
+
filters: params.filters || {},
|
|
317
|
+
fast: params.fast,
|
|
318
|
+
threshold: params.threshold,
|
|
319
|
+
include_low_confidence: params.include_low_confidence ?? false,
|
|
320
|
+
group_by_source: params.group_by_source ?? true,
|
|
321
|
+
debug: params.debug ?? false
|
|
130
322
|
});
|
|
323
|
+
return enforceSearchSafety(response);
|
|
131
324
|
}
|
|
132
325
|
/**
|
|
133
326
|
* Find similar memories
|
|
@@ -143,12 +336,20 @@ var SearchResource = class extends BaseResource {
|
|
|
143
336
|
* Perform reasoning over memories
|
|
144
337
|
*/
|
|
145
338
|
async reason(params) {
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
339
|
+
const response = await this.client.post(
|
|
340
|
+
"/v1/search/reason",
|
|
341
|
+
{
|
|
342
|
+
query: params.query,
|
|
343
|
+
collection_id: params.collection_id,
|
|
344
|
+
provider: params.provider,
|
|
345
|
+
include_steps: params.include_steps ?? false,
|
|
346
|
+
user_id: params.user_id,
|
|
347
|
+
agent_id: params.agent_id,
|
|
348
|
+
run_id: params.run_id,
|
|
349
|
+
facets: params.facets ?? []
|
|
350
|
+
}
|
|
351
|
+
);
|
|
352
|
+
return enforceSearchSafety(response, "sources");
|
|
152
353
|
}
|
|
153
354
|
};
|
|
154
355
|
var ProofLoopResource = class extends BaseResource {
|
|
@@ -168,11 +369,37 @@ var ProofLoopResource = class extends BaseResource {
|
|
|
168
369
|
...body
|
|
169
370
|
});
|
|
170
371
|
}
|
|
372
|
+
async getDecision(decisionId) {
|
|
373
|
+
return this.client.get(`/v1/learning/decisions/${decisionId}`);
|
|
374
|
+
}
|
|
375
|
+
async defineMetric(params) {
|
|
376
|
+
return this.client.post("/v1/learning/metrics", params);
|
|
377
|
+
}
|
|
378
|
+
async listMetrics(params = {}) {
|
|
379
|
+
return this.client.get("/v1/learning/metrics", params);
|
|
380
|
+
}
|
|
381
|
+
async policyInsights(policyKey, params = {}) {
|
|
382
|
+
return this.client.get(`/v1/learning/policies/${policyKey}/insights`, {
|
|
383
|
+
collection_id: params.collection_id,
|
|
384
|
+
user_id: params.user_id,
|
|
385
|
+
action_key: params.action_keys,
|
|
386
|
+
context: params.context ? JSON.stringify(params.context) : void 0
|
|
387
|
+
});
|
|
388
|
+
}
|
|
389
|
+
async evaluatePolicy(policyKey, params = {}) {
|
|
390
|
+
return this.client.post(`/v1/learning/policies/${policyKey}/evaluate`, {
|
|
391
|
+
collection_id: params.collection_id,
|
|
392
|
+
user_id: params.user_id,
|
|
393
|
+
limit: params.limit ?? 500
|
|
394
|
+
});
|
|
395
|
+
}
|
|
171
396
|
async proof(decisionId) {
|
|
172
397
|
return this.client.get(`/v1/learning/decisions/${decisionId}/proof`);
|
|
173
398
|
}
|
|
174
|
-
async publicKey() {
|
|
175
|
-
return this.client.get("/v1/learning/proof-key"
|
|
399
|
+
async publicKey(keyId) {
|
|
400
|
+
return this.client.get("/v1/learning/proof-key", {
|
|
401
|
+
key_id: keyId
|
|
402
|
+
});
|
|
176
403
|
}
|
|
177
404
|
};
|
|
178
405
|
var RLResource = class extends BaseResource {
|
|
@@ -213,56 +440,78 @@ var RLResource = class extends BaseResource {
|
|
|
213
440
|
}
|
|
214
441
|
};
|
|
215
442
|
var ProceduralResource = class extends BaseResource {
|
|
443
|
+
unwrapProcedure(response) {
|
|
444
|
+
if (response?.procedure) return response.procedure;
|
|
445
|
+
if (response?.procedure_id && !response?.id) {
|
|
446
|
+
return { ...response, id: response.procedure_id };
|
|
447
|
+
}
|
|
448
|
+
return response;
|
|
449
|
+
}
|
|
216
450
|
/**
|
|
217
451
|
* Create a new procedure
|
|
218
452
|
*/
|
|
219
453
|
async create(params) {
|
|
220
|
-
|
|
454
|
+
const response = await this.client.post("/v1/procedures", {
|
|
221
455
|
name: params.name,
|
|
222
456
|
description: params.description,
|
|
223
|
-
|
|
224
|
-
|
|
457
|
+
condition: { expression: params.trigger_condition },
|
|
458
|
+
action: { steps: params.action_sequence },
|
|
225
459
|
collection_id: params.collection_id,
|
|
226
460
|
category: params.category,
|
|
227
|
-
|
|
461
|
+
parameters: params.metadata || {}
|
|
228
462
|
});
|
|
463
|
+
return this.unwrapProcedure(response);
|
|
229
464
|
}
|
|
230
465
|
/**
|
|
231
466
|
* List procedures
|
|
232
467
|
*/
|
|
233
468
|
async list(params) {
|
|
234
|
-
|
|
469
|
+
const response = await this.client.get("/v1/procedures", {
|
|
235
470
|
collection_id: params?.collection_id,
|
|
236
471
|
category: params?.category,
|
|
237
472
|
skip: params?.skip || 0,
|
|
238
473
|
limit: params?.limit || 100
|
|
239
474
|
});
|
|
475
|
+
return Array.isArray(response) ? response : response?.procedures || [];
|
|
240
476
|
}
|
|
241
477
|
/**
|
|
242
478
|
* Get a specific procedure
|
|
243
479
|
*/
|
|
244
480
|
async get(procedureId) {
|
|
245
|
-
|
|
481
|
+
const response = await this.client.get(`/v1/procedures/${procedureId}`);
|
|
482
|
+
return this.unwrapProcedure(response);
|
|
246
483
|
}
|
|
247
484
|
/**
|
|
248
485
|
* Execute a procedure
|
|
249
486
|
*/
|
|
250
487
|
async execute(procedureId, context) {
|
|
251
|
-
|
|
252
|
-
|
|
488
|
+
const response = await this.client.post(`/v1/procedures/${procedureId}/execute`, {
|
|
489
|
+
input_state: context || {}
|
|
253
490
|
});
|
|
491
|
+
return response?.execution_result || response;
|
|
254
492
|
}
|
|
255
493
|
/**
|
|
256
494
|
* Update a procedure
|
|
257
495
|
*/
|
|
258
496
|
async update(procedureId, params) {
|
|
259
|
-
|
|
497
|
+
const body = {};
|
|
498
|
+
if (params.name !== void 0) body.name = params.name;
|
|
499
|
+
if (params.description !== void 0) body.description = params.description;
|
|
500
|
+
if (params.trigger_condition !== void 0) {
|
|
501
|
+
body.condition = { expression: params.trigger_condition };
|
|
502
|
+
}
|
|
503
|
+
if (params.action_sequence !== void 0) {
|
|
504
|
+
body.action = { steps: params.action_sequence };
|
|
505
|
+
}
|
|
506
|
+
if (params.metadata !== void 0) body.parameters = params.metadata;
|
|
507
|
+
const response = await this.client.patch(`/v1/procedures/${procedureId}`, body);
|
|
508
|
+
return this.unwrapProcedure(response);
|
|
260
509
|
}
|
|
261
510
|
/**
|
|
262
511
|
* Delete a procedure
|
|
263
512
|
*/
|
|
264
513
|
async delete(procedureId) {
|
|
265
|
-
await this.client.delete(`/
|
|
514
|
+
await this.client.delete(`/v1/procedures/${procedureId}`);
|
|
266
515
|
}
|
|
267
516
|
};
|
|
268
517
|
var TemporalResource = class extends BaseResource {
|
|
@@ -301,6 +550,10 @@ var TemporalResource = class extends BaseResource {
|
|
|
301
550
|
entity
|
|
302
551
|
});
|
|
303
552
|
}
|
|
553
|
+
/** Permanently delete a tenant-scoped temporal fact by stable ID. */
|
|
554
|
+
async deleteFact(factId) {
|
|
555
|
+
return this.client.delete(`/temporal/facts/${factId}`);
|
|
556
|
+
}
|
|
304
557
|
};
|
|
305
558
|
var WorkingMemoryResource = class extends BaseResource {
|
|
306
559
|
/**
|
|
@@ -469,6 +722,8 @@ var MemoryClient = class {
|
|
|
469
722
|
this.auth = new AuthResource(this);
|
|
470
723
|
this.collections = new CollectionsResource(this);
|
|
471
724
|
this.memories = new MemoriesResource(this);
|
|
725
|
+
this.memoryJobs = new MemoryJobsResource(this);
|
|
726
|
+
this.corrections = new CorrectionsResource(this);
|
|
472
727
|
this.searchResource = new SearchResource(this);
|
|
473
728
|
this.rl = new RLResource(this);
|
|
474
729
|
this.procedural = new ProceduralResource(this);
|
|
@@ -482,7 +737,7 @@ var MemoryClient = class {
|
|
|
482
737
|
getHeaders() {
|
|
483
738
|
const headers = {
|
|
484
739
|
"Content-Type": "application/json",
|
|
485
|
-
"User-Agent": "hebbrix-typescript/2.1
|
|
740
|
+
"User-Agent": "hebbrix-typescript/2.2.1"
|
|
486
741
|
};
|
|
487
742
|
if (this.apiKey) {
|
|
488
743
|
headers["Authorization"] = `Bearer ${this.apiKey}`;
|
|
@@ -491,7 +746,8 @@ var MemoryClient = class {
|
|
|
491
746
|
}
|
|
492
747
|
handleError(response, data) {
|
|
493
748
|
const statusCode = response.status;
|
|
494
|
-
const
|
|
749
|
+
const detail = data?.detail;
|
|
750
|
+
const message = data?.error?.message || (typeof detail === "string" ? detail : detail?.message) || response.statusText;
|
|
495
751
|
if (statusCode === 401) {
|
|
496
752
|
throw new AuthenticationError(message);
|
|
497
753
|
} else if (statusCode === 404) {
|
|
@@ -509,21 +765,29 @@ var MemoryClient = class {
|
|
|
509
765
|
}
|
|
510
766
|
async request(method, path, options = {}) {
|
|
511
767
|
const url = `${this.baseUrl}${path}`;
|
|
768
|
+
const { headers: requestHeaders, signal: requestSignal, ...requestOptions } = options;
|
|
512
769
|
const response = await fetch(url, {
|
|
770
|
+
...requestOptions,
|
|
513
771
|
method,
|
|
514
772
|
headers: {
|
|
515
773
|
...this.getHeaders(),
|
|
516
|
-
...
|
|
774
|
+
...requestHeaders || {}
|
|
517
775
|
},
|
|
518
|
-
|
|
519
|
-
signal: AbortSignal.timeout(this.timeout)
|
|
776
|
+
signal: requestSignal || AbortSignal.timeout(this.timeout)
|
|
520
777
|
});
|
|
521
|
-
let data;
|
|
778
|
+
let data = void 0;
|
|
522
779
|
const contentType = response.headers.get("content-type");
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
|
|
780
|
+
const responseText = await response.text();
|
|
781
|
+
if (responseText) {
|
|
782
|
+
if (contentType?.includes("application/json")) {
|
|
783
|
+
try {
|
|
784
|
+
data = JSON.parse(responseText);
|
|
785
|
+
} catch {
|
|
786
|
+
data = { detail: responseText };
|
|
787
|
+
}
|
|
788
|
+
} else {
|
|
789
|
+
data = responseText;
|
|
790
|
+
}
|
|
527
791
|
}
|
|
528
792
|
if (!response.ok) {
|
|
529
793
|
this.handleError(response, data);
|
|
@@ -536,7 +800,11 @@ var MemoryClient = class {
|
|
|
536
800
|
const searchParams = new URLSearchParams();
|
|
537
801
|
Object.entries(params).forEach(([key, value]) => {
|
|
538
802
|
if (value !== void 0 && value !== null) {
|
|
539
|
-
|
|
803
|
+
if (Array.isArray(value)) {
|
|
804
|
+
value.forEach((item) => searchParams.append(key, String(item)));
|
|
805
|
+
} else {
|
|
806
|
+
searchParams.append(key, String(value));
|
|
807
|
+
}
|
|
540
808
|
}
|
|
541
809
|
});
|
|
542
810
|
url += `?${searchParams.toString()}`;
|
|
@@ -572,9 +840,11 @@ export {
|
|
|
572
840
|
AuthenticationError,
|
|
573
841
|
CollectionsResource,
|
|
574
842
|
ConsolidationResource,
|
|
843
|
+
CorrectionsResource,
|
|
575
844
|
HebbrixError,
|
|
576
845
|
MemoriesResource,
|
|
577
846
|
MemoryClient,
|
|
847
|
+
MemoryJobsResource,
|
|
578
848
|
MemoryToolsResource,
|
|
579
849
|
NotFoundError,
|
|
580
850
|
ProceduralResource,
|
|
@@ -586,5 +856,6 @@ export {
|
|
|
586
856
|
TemporalResource,
|
|
587
857
|
ValidationError,
|
|
588
858
|
WorkingMemoryResource,
|
|
589
|
-
WorldModelResource
|
|
859
|
+
WorldModelResource,
|
|
860
|
+
enforceSearchSafety
|
|
590
861
|
};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "hebbrix",
|
|
3
|
-
"version": "2.1
|
|
3
|
+
"version": "2.2.1",
|
|
4
4
|
"description": "Advanced Memory API for AI Agents with Reinforcement Learning - TypeScript/JavaScript SDK",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"module": "dist/index.mjs",
|
|
@@ -14,12 +14,13 @@
|
|
|
14
14
|
},
|
|
15
15
|
"files": [
|
|
16
16
|
"dist",
|
|
17
|
-
"README.md"
|
|
17
|
+
"README.md",
|
|
18
|
+
"CHANGELOG.md"
|
|
18
19
|
],
|
|
19
20
|
"scripts": {
|
|
20
21
|
"build": "tsup src/index.ts --format cjs,esm --dts",
|
|
21
22
|
"dev": "tsup src/index.ts --format cjs,esm --dts --watch",
|
|
22
|
-
"test": "
|
|
23
|
+
"test": "npm run build && node --test tests/*.test.mjs",
|
|
23
24
|
"lint": "eslint src --ext .ts",
|
|
24
25
|
"format": "prettier --write \"src/**/*.ts\"",
|
|
25
26
|
"prepublishOnly": "npm run build"
|