@personize/sdk 0.6.4 → 0.6.5

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/README.md CHANGED
@@ -38,6 +38,7 @@ console.log(me.data.plan.limits);
38
38
  | **AI** | | |
39
39
  | POST | `/api/v1/ai/smart-guidelines` | `client.ai.smartGuidelines(opts)` |
40
40
  | POST | `/api/v1/prompt` | `client.ai.prompt(opts)` |
41
+ | POST | `/api/v1/prompt` (stream) | `client.ai.promptStream(opts)` |
41
42
  | **Memory** | | |
42
43
  | POST | `/api/v1/memorize` | `client.memory.memorize(opts)` |
43
44
  | POST | `/api/v1/smart-recall` | `client.memory.smartRecall(opts)` |
@@ -45,6 +46,7 @@ console.log(me.data.plan.limits);
45
46
  | POST | `/api/v1/search` | `client.memory.search(opts)` |
46
47
  | POST | `/api/v1/batch-memorize` | `client.memory.memorizeBatch(opts)` |
47
48
  | POST | `/api/v1/smart-memory-digest` | `client.memory.smartDigest(opts)` |
49
+ | POST | `/api/v1/memory/properties` | `client.memory.properties(opts)` |
48
50
  | **Guidelines** | | |
49
51
  | GET | `/api/v1/guidelines` | `client.guidelines.list()` |
50
52
  | POST | `/api/v1/guidelines` | `client.guidelines.create(payload)` |
@@ -185,6 +187,97 @@ console.log(research.data?.outputs?.company_profile);
185
187
  console.log(research.data?.evaluation?.finalScore);
186
188
  ```
187
189
 
190
+ ### Streaming Prompt Execution
191
+
192
+ `promptStream()` returns an async generator that yields Server-Sent Events as they arrive. Use this for real-time UI updates, progressive output delivery, or when you need structured outputs as soon as each one finishes generating.
193
+
194
+ ```typescript
195
+ import type { PromptSSEEvent } from '@personize/sdk';
196
+
197
+ // Stream with structured outputs — events arrive as each output closes
198
+ for await (const event of client.ai.promptStream({
199
+ prompt: 'Generate a hero section and social proof for our landing page',
200
+ outputs: [
201
+ { name: 'hero' },
202
+ { name: 'social_proof' },
203
+ ],
204
+ })) {
205
+ switch (event.type) {
206
+ case 'text':
207
+ // Raw LLM text chunks (everything outside <output> markers)
208
+ process.stdout.write(event.chunk);
209
+ break;
210
+
211
+ case 'output':
212
+ // A named output extracted — fired once per output as soon as </output> closes
213
+ // event.data is already parsed (JSON object or plain string)
214
+ console.log(`Output "${event.name}":`, event.data);
215
+ break;
216
+
217
+ case 'done':
218
+ // Final event — includes all outputs, evaluation, and metadata
219
+ console.log('All outputs:', event.outputs);
220
+ console.log('Metadata:', event.metadata);
221
+ break;
222
+
223
+ case 'error':
224
+ // Non-fatal error during streaming
225
+ console.error('Stream error:', event.message);
226
+ break;
227
+ }
228
+ }
229
+ ```
230
+
231
+ **SSE Event Types:**
232
+
233
+ | Event | Frequency | Description |
234
+ | :--- | :--- | :--- |
235
+ | `text` | Many per response | Plain text chunks from the LLM |
236
+ | `output` | Once per named output | Extracted output (JSON or string) — fired as soon as `</output>` closes |
237
+ | `step_complete` | Once per instruction step | Multi-step mode: step metadata |
238
+ | `done` | Once at end | Final reconciliation with all outputs + metadata |
239
+ | `error` | 0 or more | Non-fatal streaming errors |
240
+
241
+ **Options:**
242
+
243
+ | Option | Type | Default | Description |
244
+ | :--- | :--- | :--- | :--- |
245
+ | `streamTimeout` | number | `120000` | Overall stream timeout in ms |
246
+ | `signal` | AbortSignal | — | External abort signal for cancellation |
247
+
248
+ All other `PromptOptions` parameters (`outputs`, `context`, `instructions`, `tier`, `memorize`, `evaluate`, etc.) are supported.
249
+
250
+ **Cancellation:**
251
+
252
+ ```typescript
253
+ const controller = new AbortController();
254
+ setTimeout(() => controller.abort(), 5000); // cancel after 5s
255
+
256
+ for await (const event of client.ai.promptStream({
257
+ prompt: '...',
258
+ signal: controller.signal,
259
+ })) {
260
+ // ...
261
+ }
262
+ ```
263
+
264
+ #### Entity Identifiers
265
+
266
+ All memory endpoints support multiple CRM key types for entity scoping:
267
+
268
+ | Key | Use case |
269
+ |-----|----------|
270
+ | `email` | Contact lookup |
271
+ | `websiteUrl` | Company lookup |
272
+ | `recordId` | Direct record ID |
273
+ | `customKeyName` + `customKeyValue` | Custom CRM field (e.g. `hubspot_id`) |
274
+ | `phoneNumber` | Phone-based lookup |
275
+ | `postalCode` | Location-based lookup |
276
+ | `deviceId` | Device-based lookup |
277
+ | `contentId` | Content-based lookup |
278
+
279
+ You can pass multiple keys simultaneously for better matching.
280
+
188
281
  ### Memory (RAG)
189
282
 
190
283
  ```typescript
@@ -199,21 +292,20 @@ const memorized = await client.memory.memorize({
199
292
  });
200
293
  console.log(memorized.data?.recordId); // REC#<hex> — deterministic, use for recall/digest
201
294
 
202
- // Smart recall — advanced recall with reflection
295
+ // Smart recall — deep mode (default): reflection + answer generation, ~10-20s, 2 credits
203
296
  const results = await client.memory.smartRecall({
204
297
  query: 'What does John prefer?',
205
298
  limit: 5,
206
299
  minScore: 0.7,
207
- enable_reflection: true,
208
- generate_answer: true,
300
+ mode: 'deep',
209
301
  });
210
302
 
211
- // Fast recall — low-latency mode (~500ms), guaranteed min 10 results
303
+ // Smart recall — fast mode: skips reflection, ~500ms, 1 credit
212
304
  const fast = await client.memory.smartRecall({
213
305
  query: 'contact info for John',
214
306
  email: 'john@example.com',
215
- fast_mode: true,
216
- // min_results: 10 (default in fast_mode — always returns top N even below score threshold)
307
+ mode: 'fast',
308
+ // min_results: 10 (default in fast mode — always returns top N even below score threshold)
217
309
  });
218
310
 
219
311
  // Custom keys — bring your own identifier for any entity type
@@ -239,7 +331,7 @@ const student = await client.memory.smartRecall({
239
331
  type: 'Student',
240
332
  customKeyName: 'studentNumber',
241
333
  customKeyValue: 'S-2024-1234',
242
- fast_mode: true,
334
+ mode: 'fast',
243
335
  });
244
336
 
245
337
  // Direct recall — DynamoDB lookup: properties + freeform memories (no AI, type required)
@@ -377,6 +469,38 @@ console.log(digest.data?.compiledContext); // ready-to-use markdown for LLM prom
377
469
 
378
470
  ```
379
471
 
472
+ ### Get Record Properties
473
+
474
+ Fetch current property values for a record, joined with collection schema descriptions and the `update` flag.
475
+
476
+ ```typescript
477
+ // Get specific properties with schema info
478
+ const result = await client.memory.properties({
479
+ email: 'john@acme.com',
480
+ propertyNames: ['Tasks', 'Lifecycle Stage'],
481
+ nonEmpty: true,
482
+ });
483
+
484
+ for (const prop of result.data.properties) {
485
+ console.log(`${prop.name}: ${JSON.stringify(prop.value)}`);
486
+ console.log(` Type: ${prop.type}, Update: ${prop.update}`);
487
+ console.log(` Description: ${prop.description}`);
488
+ }
489
+ ```
490
+
491
+ Each property includes:
492
+ - `value` — current value
493
+ - `description` — from the collection schema, tells AI how to interpret/update
494
+ - `update` — `true` means replaceable (use `memory.update()` with `propertyValue`), `false` means append-only (use `arrayPush`)
495
+ - `type` — property type (`text`, `number`, `boolean`, `array`, `date`, `options`)
496
+ - `collectionName` — which collection this property belongs to
497
+
498
+ Options:
499
+ - `propertyNames` — filter to specific properties (recommended to save tokens)
500
+ - `includeDescriptions` — join with collection schema (default: `true`)
501
+ - `nonEmpty` — exclude null/empty values (default: `false`)
502
+ - Identifiers: `email`, `websiteUrl`, `recordId`, `customKeyName`+`customKeyValue`
503
+
380
504
  ### Agents
381
505
 
382
506
  ```typescript
@@ -456,12 +580,12 @@ console.log(evaluation.data.summary.propertiesOptimized);
456
580
 
457
581
  | Operation | Mode | Credits/Call |
458
582
  | :--- | :--- | :--- |
459
- | Smart Recall | `fast_mode: true` | 1 |
460
- | Smart Recall | `fast_mode: false` (deep) | 1 |
583
+ | Smart Recall | `mode: 'fast'` | 1 |
584
+ | Smart Recall | `mode: 'deep'` | 2 |
461
585
  | Smart Guidelines | `mode: 'fast'` | 1 |
462
586
  | Smart Guidelines | `mode: 'deep'` | 1 |
463
587
 
464
- All read operations (recall, smart recall, smart guidelines, smart context) charge a flat **1 credit per call** regardless of mode. Mode choice affects latency and depth, not cost.
588
+ Smart Recall cost depends on mode: fast = 1 credit, deep = 2 credits. All other read operations (recall, smart guidelines, smart context) charge a flat **1 credit per call**.
465
589
 
466
590
  1 credit = $0.01.
467
591
 
@@ -496,6 +620,33 @@ await client.ai.prompt({
496
620
 
497
621
  Response metadata includes `byok: true` and `creditsCharged` reflecting the flat 5-credit charge.
498
622
 
623
+ ## Smart Recall Modes
624
+
625
+ The `mode` parameter controls smart recall behavior:
626
+
627
+ | Mode | Latency | Credits | Description |
628
+ | :--- | :--- | :--- | :--- |
629
+ | `"fast"` | ~500ms | 1 | Skips reflection and answer generation. Returns raw vector results with guaranteed minimum count. |
630
+ | `"deep"` | ~10-20s | 2 | Enables reflection + answer generation for higher-quality, synthesized responses. |
631
+
632
+ Default is `"deep"`. The `mode` parameter takes precedence over the individual `enable_reflection`, `generate_answer`, and `fast_mode` flags. If `mode` is set, those flags are ignored.
633
+
634
+ #### Recency Bias
635
+
636
+ Use `prefer_recent` to boost recent memories with exponential decay:
637
+
638
+ ```typescript
639
+ const result = await client.memory.smartRecall({
640
+ query: "what changed on this contact recently?",
641
+ email: "john@acme.com",
642
+ mode: "deep",
643
+ prefer_recent: true,
644
+ recency_half_life_days: 30, // aggressive: 30-day half-life
645
+ });
646
+ ```
647
+
648
+ Default half-life is 90 days. A memory 90 days old scores ~37% of its original relevance. Set to 7-30 for "what happened this week/month" queries.
649
+
499
650
  ## Best Practices: Query Crafting for smartRecall
500
651
 
501
652
  The `smartRecall` endpoint uses vector similarity search. Query quality directly impacts result relevance. When building AI pipelines that call `smartRecall`, the **AI agent is responsible for crafting embedding-friendly queries**.
@@ -518,11 +669,11 @@ const bad = await client.memory.smartRecall({ query: 'Tell me about this contact
518
669
  const good = await client.memory.smartRecall({
519
670
  query: `${contactName} role company background interests preferences`,
520
671
  email,
521
- fast_mode: true,
672
+ mode: 'fast',
522
673
  });
523
674
  ```
524
675
 
525
- **Guaranteed minimum results:** In `fast_mode`, `smartRecall` guarantees at least 10 results (configurable via `min_results`) even when scores fall below the threshold. This ensures your AI workflow always has context to reason about — it can then decide whether the data is sufficient or not.
676
+ **Guaranteed minimum results:** In `mode: 'fast'`, `smartRecall` guarantees at least 10 results (configurable via `min_results`) even when scores fall below the threshold. This ensures your AI workflow always has context to reason about — it can then decide whether the data is sufficient or not.
526
677
 
527
678
  ## Configuration
528
679
 
@@ -543,23 +694,23 @@ const client = new Personize({
543
694
  });
544
695
  ```
545
696
 
546
- ## Migration from 0.6.2
547
-
548
- **New in 0.6.3:**
549
-
550
- | Feature | Details |
551
- | :--- | :--- |
552
- | `evaluationCriteria` on `PromptOptions` | Compatibility alias for `evaluate: { criteria, serverSide: true }` |
553
- | `message` on `RecallOptions` / `SmartRecallOptions` | Compatibility alias for `query` |
554
- | Legacy `memory.recall()` routing | If you call `recall()` with legacy advanced-recall-style inputs (`message`, `limit`, omitted `type`, collection-name scoping), the SDK routes to `/smart-recall` automatically |
555
- | Shorthand semantic `memory.search()` | `search({ query, limit, collectionName })` is accepted and routed to `/smart-recall` when no filter groups are provided |
556
- | `collectionName` / `collectionNames` on `memorize()` | Collection names are resolved client-side into `collectionIds` |
557
- | Legacy collection payload aliases | `collections.create()` now accepts `name`, `slug`, `description`, array `options`, and `updateSemantics` |
558
- | `records` shorthand on `memorizeBatch()` | Accepts record-style input and normalizes it client-side into `memorize()` + `/batch-memorize` calls |
559
-
560
- See [SDK_0_6_3_COMPATIBILITY_CHANGES.md](SDK_0_6_3_COMPATIBILITY_CHANGES.md) for the full design notes and tradeoffs.
561
-
562
- ## Migration from 0.5.x
697
+ ## Migration from 0.6.2
698
+
699
+ **New in 0.6.3:**
700
+
701
+ | Feature | Details |
702
+ | :--- | :--- |
703
+ | `evaluationCriteria` on `PromptOptions` | Compatibility alias for `evaluate: { criteria, serverSide: true }` |
704
+ | `message` on `RecallOptions` / `SmartRecallOptions` | Compatibility alias for `query` |
705
+ | Legacy `memory.recall()` routing | If you call `recall()` with legacy advanced-recall-style inputs (`message`, `limit`, omitted `type`, collection-name scoping), the SDK routes to `/smart-recall` automatically |
706
+ | Shorthand semantic `memory.search()` | `search({ query, limit, collectionName })` is accepted and routed to `/smart-recall` when no filter groups are provided |
707
+ | `collectionName` / `collectionNames` on `memorize()` | Collection names are resolved client-side into `collectionIds` |
708
+ | Legacy collection payload aliases | `collections.create()` now accepts `name`, `slug`, `description`, array `options`, and `updateSemantics` |
709
+ | `records` shorthand on `memorizeBatch()` | Accepts record-style input and normalizes it client-side into `memorize()` + `/batch-memorize` calls |
710
+
711
+ See [SDK_0_6_3_COMPATIBILITY_CHANGES.md](SDK_0_6_3_COMPATIBILITY_CHANGES.md) for the full design notes and tradeoffs.
712
+
713
+ ## Migration from 0.5.x
563
714
 
564
715
  **New in 0.6.0:**
565
716
 
package/dist/client.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { PersonizeConfig, ApiResponse, MeResponse, TestResponse, ListOptions, GuidelinesResponse, GuidelineSectionOptions, GuidelineUpdatePayload, GuidelineCreatePayload, GuidelineHistoryResponse, GuidelineHistoryOptions, CollectionsResponse, CollectionCreatePayload, CollectionUpdatePayload, CollectionHistoryOptions, CollectionHistoryResponse, SmartGuidelinesOptions, SmartGuidelinesResponse, PromptOptions, PromptResponse, AgentRunOptions, AgentResponse, MemorizeOptions, SmartRecallOptions, RecallOptions, RecallResponse, SearchOptions, SearchResponse, BatchMemorizeOptions, SmartDigestOptions, SmartDigestResponse, EvaluateMemorizationOptions, EvaluateMemorizationResponse } from './types';
1
+ import { PersonizeConfig, ApiResponse, MeResponse, TestResponse, ListOptions, GuidelinesResponse, GuidelineSectionOptions, GuidelineUpdatePayload, GuidelineCreatePayload, GuidelineHistoryResponse, GuidelineHistoryOptions, CollectionsResponse, CollectionCreatePayload, CollectionUpdatePayload, CollectionHistoryOptions, CollectionHistoryResponse, SmartGuidelinesOptions, SmartGuidelinesResponse, PromptOptions, PromptResponse, PromptStreamOptions, PromptSSEEvent, AgentRunOptions, AgentResponse, MemorizeOptions, SmartRecallOptions, RecallOptions, RecallResponse, SearchOptions, SearchResponse, BatchMemorizeOptions, SmartDigestOptions, SmartDigestResponse, EvaluateMemorizationOptions, EvaluateMemorizationResponse, UpdatePropertyOptions, UpdateResult, BulkUpdateOptions, BulkUpdateResult, PropertyHistoryOptions, PropertyHistoryResult, QueryPropertiesOptions, QueryPropertiesResult, DeleteMemoriesOptions, DeleteRecordOptions, DeletionResult, CancelDeletionOptions, CancelDeletionResult, FilterByPropertyOptions, FilterByPropertyResult, GetPropertiesOptions, GetPropertiesResponse } from './types';
2
2
  export declare class Personize {
3
3
  private client;
4
4
  private _organizationId?;
@@ -105,6 +105,28 @@ export declare class Personize {
105
105
  * Use `memorize` to auto-save outputs and tool results to memory.
106
106
  */
107
107
  prompt: (options: PromptOptions) => Promise<ApiResponse<PromptResponse>>;
108
+ /**
109
+ * POST /api/v1/prompt (stream: true) — Stream prompt execution as Server-Sent Events.
110
+ *
111
+ * Returns an async generator that yields SSE events as they arrive:
112
+ * - `text`: plain text chunks from the LLM
113
+ * - `output`: a named output extracted when its </output> marker closes
114
+ * - `step_complete`: fired after each instruction step (multi-step mode)
115
+ * - `done`: final event with all outputs, evaluation, and metadata
116
+ * - `error`: non-fatal error during streaming
117
+ *
118
+ * @example
119
+ * ```ts
120
+ * for await (const event of personize.ai.promptStream({
121
+ * prompt: 'Write a hero section',
122
+ * outputs: [{ name: 'headline' }, { name: 'subtitle' }],
123
+ * })) {
124
+ * if (event.type === 'output') console.log(event.name, event.data);
125
+ * if (event.type === 'done') console.log('Finished:', event.metadata);
126
+ * }
127
+ * ```
128
+ */
129
+ promptStream: (options: PromptStreamOptions) => AsyncGenerator<PromptSSEEvent>;
108
130
  };
109
131
  agents: {
110
132
  /**
@@ -152,6 +174,61 @@ export declare class Personize {
152
174
  * Combines DynamoDB properties + LanceDB memories into a token-budgeted markdown block.
153
175
  */
154
176
  smartDigest: (data: SmartDigestOptions) => Promise<ApiResponse<SmartDigestResponse>>;
177
+ /**
178
+ * POST /api/v1/memory/update — Update a single property or freeform memory.
179
+ *
180
+ * For property updates: pass `propertyName` + `propertyValue` (or array operations).
181
+ * For freeform edits: pass `memoryId` + `text`.
182
+ * Use `expectedVersion` for optimistic concurrency (409 on mismatch).
183
+ */
184
+ update: (data: UpdatePropertyOptions) => Promise<ApiResponse<UpdateResult>>;
185
+ /**
186
+ * POST /api/v1/memory/bulk-update — Update multiple properties on a record in one request.
187
+ * Use `expectedVersion` for optimistic concurrency (checked before any writes).
188
+ */
189
+ bulkUpdate: (data: BulkUpdateOptions) => Promise<ApiResponse<BulkUpdateResult>>;
190
+ /**
191
+ * POST /api/v1/memory/delete — Soft-delete memories (30-day recovery window).
192
+ * Deleted items are excluded from all reads. Use `cancelDeletion` to restore.
193
+ */
194
+ delete: (data: DeleteMemoriesOptions) => Promise<ApiResponse<DeletionResult>>;
195
+ /**
196
+ * POST /api/v1/memory/delete-record — Soft-delete all memories for a record (30-day recovery).
197
+ */
198
+ deleteRecord: (data: DeleteRecordOptions) => Promise<ApiResponse<DeletionResult>>;
199
+ /**
200
+ * POST /api/v1/memory/cancel-deletion — Cancel a pending soft-delete within the 30-day window.
201
+ * Returns 409 DELETION_FINALIZED if the window has expired.
202
+ */
203
+ cancelDeletion: (data: CancelDeletionOptions) => Promise<ApiResponse<CancelDeletionResult>>;
204
+ /**
205
+ * POST /api/v1/memory/property-history — Query property change history for a record.
206
+ * Supports filtering by property name, time range, and cursor-based pagination.
207
+ */
208
+ propertyHistory: (data: PropertyHistoryOptions) => Promise<ApiResponse<PropertyHistoryResult>>;
209
+ /**
210
+ * POST /api/v1/memory/query-properties — LLM-powered search across property values.
211
+ * Finds records where a property value matches a natural-language query.
212
+ */
213
+ queryProperties: (data: QueryPropertiesOptions) => Promise<ApiResponse<QueryPropertiesResult>>;
214
+ /**
215
+ * POST /api/v1/memory/filter-by-property — Deterministic property filter (no LLM, no token cost).
216
+ * Finds records where property values match structured conditions.
217
+ *
218
+ * @example
219
+ * ```ts
220
+ * const result = await client.memory.filterByProperty({
221
+ * conditions: [{ propertyName: 'deal_stage', operator: 'equals', value: 'closed_won' }],
222
+ * type: 'Company',
223
+ * limit: 100,
224
+ * });
225
+ * ```
226
+ */
227
+ filterByProperty: (data: FilterByPropertyOptions) => Promise<ApiResponse<FilterByPropertyResult>>;
228
+ /**
229
+ * POST /api/v1/properties — Get record properties with schema descriptions.
230
+ */
231
+ properties: (data: GetPropertiesOptions) => Promise<ApiResponse<GetPropertiesResponse>>;
155
232
  };
156
233
  evaluate: {
157
234
  /**
package/dist/client.js CHANGED
@@ -169,6 +169,34 @@ class Personize {
169
169
  const response = await this.client.post('/api/v1/prompt', normalizedOptions);
170
170
  return response.data;
171
171
  },
172
+ /**
173
+ * POST /api/v1/prompt (stream: true) — Stream prompt execution as Server-Sent Events.
174
+ *
175
+ * Returns an async generator that yields SSE events as they arrive:
176
+ * - `text`: plain text chunks from the LLM
177
+ * - `output`: a named output extracted when its </output> marker closes
178
+ * - `step_complete`: fired after each instruction step (multi-step mode)
179
+ * - `done`: final event with all outputs, evaluation, and metadata
180
+ * - `error`: non-fatal error during streaming
181
+ *
182
+ * @example
183
+ * ```ts
184
+ * for await (const event of personize.ai.promptStream({
185
+ * prompt: 'Write a hero section',
186
+ * outputs: [{ name: 'headline' }, { name: 'subtitle' }],
187
+ * })) {
188
+ * if (event.type === 'output') console.log(event.name, event.data);
189
+ * if (event.type === 'done') console.log('Finished:', event.metadata);
190
+ * }
191
+ * ```
192
+ */
193
+ promptStream: (options) => {
194
+ const normalizedOptions = this.normalizePromptOptions({ ...options, stream: true });
195
+ const baseURL = this.client.defaults.baseURL || 'https://agent.personize.ai';
196
+ const authHeader = this.client.defaults.headers?.['Authorization'];
197
+ const streamTimeout = options.streamTimeout ?? 120000;
198
+ return streamPromptSSE(baseURL, authHeader, normalizedOptions, streamTimeout, options.signal);
199
+ },
172
200
  };
173
201
  this.agents = {
174
202
  /**
@@ -330,6 +358,98 @@ class Personize {
330
358
  const response = await this.client.post('/api/v1/smart-memory-digest', data);
331
359
  return response.data;
332
360
  },
361
+ /**
362
+ * POST /api/v1/memory/update — Update a single property or freeform memory.
363
+ *
364
+ * For property updates: pass `propertyName` + `propertyValue` (or array operations).
365
+ * For freeform edits: pass `memoryId` + `text`.
366
+ * Use `expectedVersion` for optimistic concurrency (409 on mismatch).
367
+ */
368
+ update: async (data) => {
369
+ const response = await this.client.post('/api/v1/memory/update', data);
370
+ return response.data;
371
+ },
372
+ /**
373
+ * POST /api/v1/memory/bulk-update — Update multiple properties on a record in one request.
374
+ * Use `expectedVersion` for optimistic concurrency (checked before any writes).
375
+ */
376
+ bulkUpdate: async (data) => {
377
+ const response = await this.client.post('/api/v1/memory/bulk-update', data);
378
+ return response.data;
379
+ },
380
+ /**
381
+ * POST /api/v1/memory/delete — Soft-delete memories (30-day recovery window).
382
+ * Deleted items are excluded from all reads. Use `cancelDeletion` to restore.
383
+ */
384
+ delete: async (data) => {
385
+ const response = await this.client.post('/api/v1/memory/delete', data);
386
+ return response.data;
387
+ },
388
+ /**
389
+ * POST /api/v1/memory/delete-record — Soft-delete all memories for a record (30-day recovery).
390
+ */
391
+ deleteRecord: async (data) => {
392
+ const response = await this.client.post('/api/v1/memory/delete-record', data);
393
+ return response.data;
394
+ },
395
+ /**
396
+ * POST /api/v1/memory/cancel-deletion — Cancel a pending soft-delete within the 30-day window.
397
+ * Returns 409 DELETION_FINALIZED if the window has expired.
398
+ */
399
+ cancelDeletion: async (data) => {
400
+ const response = await this.client.post('/api/v1/memory/cancel-deletion', data);
401
+ return response.data;
402
+ },
403
+ /**
404
+ * POST /api/v1/memory/property-history — Query property change history for a record.
405
+ * Supports filtering by property name, time range, and cursor-based pagination.
406
+ */
407
+ propertyHistory: async (data) => {
408
+ const response = await this.client.post('/api/v1/memory/property-history', data);
409
+ return response.data;
410
+ },
411
+ /**
412
+ * POST /api/v1/memory/query-properties — LLM-powered search across property values.
413
+ * Finds records where a property value matches a natural-language query.
414
+ */
415
+ queryProperties: async (data) => {
416
+ const response = await this.client.post('/api/v1/memory/query-properties', data);
417
+ return response.data;
418
+ },
419
+ /**
420
+ * POST /api/v1/memory/filter-by-property — Deterministic property filter (no LLM, no token cost).
421
+ * Finds records where property values match structured conditions.
422
+ *
423
+ * @example
424
+ * ```ts
425
+ * const result = await client.memory.filterByProperty({
426
+ * conditions: [{ propertyName: 'deal_stage', operator: 'equals', value: 'closed_won' }],
427
+ * type: 'Company',
428
+ * limit: 100,
429
+ * });
430
+ * ```
431
+ */
432
+ filterByProperty: async (data) => {
433
+ const response = await this.client.post('/api/v1/memory/filter-by-property', data);
434
+ return response.data;
435
+ },
436
+ /**
437
+ * POST /api/v1/properties — Get record properties with schema descriptions.
438
+ */
439
+ properties: async (data) => {
440
+ const response = await this.client.post('/api/v1/properties', {
441
+ email: data.email,
442
+ websiteUrl: data.websiteUrl || data.website_url,
443
+ recordId: data.recordId || data.record_id,
444
+ type: data.type,
445
+ customKeyName: data.customKeyName,
446
+ customKeyValue: data.customKeyValue,
447
+ propertyNames: data.propertyNames,
448
+ includeDescriptions: data.includeDescriptions,
449
+ nonEmpty: data.nonEmpty,
450
+ });
451
+ return response.data;
452
+ },
333
453
  };
334
454
  this.evaluate = {
335
455
  /**
@@ -487,7 +607,7 @@ class Personize {
487
607
  }
488
608
  normalizePromptOptions(options) {
489
609
  if (!options.evaluationCriteria || options.evaluate) {
490
- const { evaluationCriteria, ...rest } = options;
610
+ const { evaluationCriteria: _ec, ...rest } = options;
491
611
  return rest;
492
612
  }
493
613
  const { evaluationCriteria, ...rest } = options;
@@ -550,7 +670,7 @@ class Personize {
550
670
  };
551
671
  }
552
672
  normalizeRecallOptions(data) {
553
- const { message, limit, collectionName, collectionNames, ...rest } = data;
673
+ const { message, limit: _limit, collectionName: _collectionName, collectionNames: _collectionNames, ...rest } = data;
554
674
  return {
555
675
  ...rest,
556
676
  query: data.query || message || '',
@@ -790,3 +910,124 @@ class Personize {
790
910
  }
791
911
  }
792
912
  exports.Personize = Personize;
913
+ // ────────────────────────────── SSE Stream Parser ──────────────────────────────
914
+ /**
915
+ * Initiates a streaming prompt request and yields SSE events.
916
+ * Extracted as a standalone function to avoid `this` binding issues with async generators.
917
+ */
918
+ async function* streamPromptSSE(baseURL, authHeader, options, streamTimeout, signal) {
919
+ const controller = new AbortController();
920
+ const timeoutId = setTimeout(() => controller.abort(), streamTimeout);
921
+ // Link external signal if provided
922
+ if (signal) {
923
+ if (signal.aborted) {
924
+ clearTimeout(timeoutId);
925
+ controller.abort();
926
+ }
927
+ else {
928
+ signal.addEventListener('abort', () => controller.abort(), { once: true });
929
+ }
930
+ }
931
+ let response;
932
+ try {
933
+ response = await fetch(`${baseURL}/api/v1/prompt`, {
934
+ method: 'POST',
935
+ headers: {
936
+ 'Authorization': authHeader,
937
+ 'Content-Type': 'application/json',
938
+ },
939
+ body: JSON.stringify(options),
940
+ signal: controller.signal,
941
+ });
942
+ }
943
+ catch (err) {
944
+ clearTimeout(timeoutId);
945
+ throw new Error(`Prompt stream connection failed: ${err instanceof Error ? err.message : err}`);
946
+ }
947
+ if (!response.ok) {
948
+ clearTimeout(timeoutId);
949
+ const errorBody = await response.text().catch(() => '');
950
+ throw new Error(`Prompt stream failed (${response.status}): ${errorBody}`);
951
+ }
952
+ if (!response.body) {
953
+ clearTimeout(timeoutId);
954
+ throw new Error('Prompt stream: response body is null');
955
+ }
956
+ try {
957
+ yield* parseSSEStream(response.body);
958
+ }
959
+ finally {
960
+ clearTimeout(timeoutId);
961
+ }
962
+ }
963
+ /**
964
+ * Parses a ReadableStream of SSE bytes into typed PromptSSEEvent objects.
965
+ *
966
+ * Handles:
967
+ * - Partial chunks split across reads
968
+ * - Multi-line `data:` fields (accumulated per event)
969
+ * - Empty lines as event separators
970
+ * - Graceful end-of-stream
971
+ */
972
+ async function* parseSSEStream(body) {
973
+ const reader = body.getReader();
974
+ const decoder = new TextDecoder();
975
+ let buffer = '';
976
+ try {
977
+ while (true) {
978
+ const { done, value } = await reader.read();
979
+ if (done)
980
+ break;
981
+ buffer += decoder.decode(value, { stream: true });
982
+ // Process complete events (separated by double newline)
983
+ const parts = buffer.split('\n\n');
984
+ // Last part may be incomplete — keep it in buffer
985
+ buffer = parts.pop() || '';
986
+ for (const part of parts) {
987
+ const dataLines = [];
988
+ for (const line of part.split('\n')) {
989
+ if (line.startsWith('data: ')) {
990
+ dataLines.push(line.slice(6));
991
+ }
992
+ else if (line.startsWith('data:')) {
993
+ dataLines.push(line.slice(5));
994
+ }
995
+ // Ignore lines starting with ':' (comments/keepalive)
996
+ // Ignore 'event:', 'id:', 'retry:' — we only use unnamed data events
997
+ }
998
+ if (dataLines.length === 0)
999
+ continue;
1000
+ const jsonStr = dataLines.join('\n');
1001
+ try {
1002
+ const event = JSON.parse(jsonStr);
1003
+ yield event;
1004
+ }
1005
+ catch {
1006
+ // Non-JSON data line — skip (could be a keepalive or malformed chunk)
1007
+ }
1008
+ }
1009
+ }
1010
+ // Flush remaining buffer
1011
+ if (buffer.trim()) {
1012
+ const dataLines = [];
1013
+ for (const line of buffer.split('\n')) {
1014
+ if (line.startsWith('data: '))
1015
+ dataLines.push(line.slice(6));
1016
+ else if (line.startsWith('data:'))
1017
+ dataLines.push(line.slice(5));
1018
+ }
1019
+ if (dataLines.length > 0) {
1020
+ try {
1021
+ const event = JSON.parse(dataLines.join('\n'));
1022
+ yield event;
1023
+ }
1024
+ catch {
1025
+ // Ignore incomplete final chunk
1026
+ }
1027
+ }
1028
+ }
1029
+ }
1030
+ finally {
1031
+ reader.releaseLock();
1032
+ }
1033
+ }
package/dist/types.d.ts CHANGED
@@ -537,6 +537,48 @@ export interface PromptResponse {
537
537
  stepsExecuted: number;
538
538
  }>;
539
539
  }
540
+ /** Text chunk from the LLM stream. Many of these per response. */
541
+ export interface SSETextEvent {
542
+ type: 'text';
543
+ chunk: string;
544
+ }
545
+ /** A named output extracted from the stream when its </output> tag closes. One per output. */
546
+ export interface SSEOutputEvent {
547
+ type: 'output';
548
+ name: string;
549
+ data: unknown;
550
+ }
551
+ /** Fired after each instruction step completes (multi-step mode). */
552
+ export interface SSEStepCompleteEvent {
553
+ type: 'step_complete';
554
+ instructionIndex: number;
555
+ text: string;
556
+ toolCalls: Array<{
557
+ toolName: string;
558
+ }>;
559
+ }
560
+ /** Final event — includes all outputs, evaluation, and metadata. */
561
+ export interface SSEDoneEvent {
562
+ type: 'done';
563
+ outputs?: Record<string, unknown>;
564
+ toolOutputs?: Record<string, unknown>;
565
+ evaluation?: unknown;
566
+ metadata?: unknown;
567
+ }
568
+ /** Non-fatal error during streaming. */
569
+ export interface SSEErrorEvent {
570
+ type: 'error';
571
+ message: string;
572
+ }
573
+ /** Union of all SSE event types emitted by the /prompt streaming endpoint. */
574
+ export type PromptSSEEvent = SSETextEvent | SSEOutputEvent | SSEStepCompleteEvent | SSEDoneEvent | SSEErrorEvent;
575
+ /** Options for promptStream(). Extends PromptOptions but forces stream: true. */
576
+ export interface PromptStreamOptions extends Omit<PromptOptions, 'stream'> {
577
+ /** Timeout in milliseconds for the overall stream (default: 120000). */
578
+ streamTimeout?: number;
579
+ /** Abort signal for cancellation. */
580
+ signal?: AbortSignal;
581
+ }
540
582
  export interface TestResponse {
541
583
  timestamp: string;
542
584
  ip: string;
@@ -624,6 +666,14 @@ export interface MemorizeOptions {
624
666
  skipDualWrite?: boolean;
625
667
  /** If true, skip property selection step. */
626
668
  skipPropertySelection?: boolean;
669
+ /** Phone number for entity scoping. */
670
+ phoneNumber?: string;
671
+ /** Postal code for entity scoping. */
672
+ postalCode?: string;
673
+ /** Device ID for entity scoping. */
674
+ deviceId?: string;
675
+ /** Content ID for entity scoping. */
676
+ contentId?: string;
627
677
  }
628
678
  /** @deprecated Use MemorizeOptions instead. */
629
679
  export type MemorizeProOptions = MemorizeOptions;
@@ -632,6 +682,8 @@ export interface SmartRecallOptions {
632
682
  query: string;
633
683
  /** Compatibility alias for query. */
634
684
  message?: string;
685
+ /** Retrieval mode. "fast" skips reflection (~500ms, 1 credit). "deep" enables reflection + answer (~10-20s, 2 credits). Default: "deep". */
686
+ mode?: 'fast' | 'deep';
635
687
  /** Max results to return (default: 10). */
636
688
  limit?: number;
637
689
  /** Minimum similarity score threshold. */
@@ -648,6 +700,22 @@ export interface SmartRecallOptions {
648
700
  websiteUrl?: string;
649
701
  /** Entity type filter (e.g. 'Contact', 'Company'). */
650
702
  type?: string;
703
+ /** Phone number for entity scoping. */
704
+ phoneNumber?: string;
705
+ /** Phone number (snake_case alias). */
706
+ phone_number?: string;
707
+ /** Postal code for entity scoping. */
708
+ postalCode?: string;
709
+ /** Postal code (snake_case alias). */
710
+ postal_code?: string;
711
+ /** Device ID for entity scoping. */
712
+ deviceId?: string;
713
+ /** Device ID (snake_case alias). */
714
+ device_id?: string;
715
+ /** Content ID for entity scoping. */
716
+ contentId?: string;
717
+ /** Content ID (snake_case alias). */
718
+ content_id?: string;
651
719
  /** Custom key name — for entity types with domain-specific unique IDs. */
652
720
  customKeyName?: string;
653
721
  /** Custom key value — the unique identifier value. */
@@ -682,6 +750,10 @@ export interface SmartRecallOptions {
682
750
  * In fast_mode, defaults to 10. Set to 0 to disable (strict score cutoff).
683
751
  */
684
752
  min_results?: number;
753
+ /** Apply exponential recency decay to scores. Recent memories rank higher. */
754
+ prefer_recent?: boolean;
755
+ /** Half-life in days for recency decay (default: 90). A memory this many days old has its score multiplied by ~0.37. */
756
+ recency_half_life_days?: number;
685
757
  /** Metadata filters for narrowing results. */
686
758
  filters?: Record<string, unknown>;
687
759
  }
@@ -710,8 +782,18 @@ export interface RecallOptions {
710
782
  customKeyName?: string;
711
783
  /** Custom key value — the unique identifier value. */
712
784
  customKeyValue?: string;
785
+ /** Phone number for entity scoping. */
786
+ phoneNumber?: string;
787
+ /** Postal code for entity scoping. */
788
+ postalCode?: string;
789
+ /** Device ID for entity scoping. */
790
+ deviceId?: string;
791
+ /** Content ID for entity scoping. */
792
+ contentId?: string;
713
793
  /** Additional filters. */
714
794
  filters?: Record<string, unknown>;
795
+ /** Scope results to specific collections by ID. */
796
+ collectionIds?: string[];
715
797
  /** Compatibility alias for a single collection name. */
716
798
  collectionName?: string;
717
799
  /** Compatibility alias for collection scoping by name. */
@@ -811,6 +893,45 @@ export interface BatchMemorizeRecord {
811
893
  timestamp?: string;
812
894
  speaker?: string;
813
895
  }
896
+ export interface GetPropertiesOptions {
897
+ /** Contact email. */
898
+ email?: string;
899
+ /** Company website URL. */
900
+ websiteUrl?: string;
901
+ /** Website URL (snake_case alias). */
902
+ website_url?: string;
903
+ /** CRM record ID. */
904
+ recordId?: string;
905
+ /** CRM record ID (snake_case alias). */
906
+ record_id?: string;
907
+ /** Entity type. */
908
+ type?: string;
909
+ /** Custom CRM key field name. */
910
+ customKeyName?: string;
911
+ /** Custom CRM key field value. */
912
+ customKeyValue?: string;
913
+ /** Filter to specific properties by name. */
914
+ propertyNames?: string[];
915
+ /** Include collection schema descriptions (default: true). */
916
+ includeDescriptions?: boolean;
917
+ /** Only return non-empty properties (default: false). */
918
+ nonEmpty?: boolean;
919
+ }
920
+ export interface PropertyItem {
921
+ name: string;
922
+ value: unknown;
923
+ type?: string;
924
+ description?: string;
925
+ /** true = replaceable (set), false = append-only (push only). */
926
+ update?: boolean;
927
+ collectionId?: string;
928
+ collectionName?: string;
929
+ }
930
+ export interface GetPropertiesResponse {
931
+ recordId: string;
932
+ type: string;
933
+ properties: PropertyItem[];
934
+ }
814
935
  export interface SmartDigestOptions {
815
936
  /** CRM record ID */
816
937
  record_id?: string;
@@ -840,6 +961,14 @@ export interface SmartDigestOptions {
840
961
  include_memories?: boolean;
841
962
  /** Include memories (camelCase alias). */
842
963
  includeMemories?: boolean;
964
+ /** Phone number for entity scoping. */
965
+ phoneNumber?: string;
966
+ /** Postal code for entity scoping. */
967
+ postalCode?: string;
968
+ /** Device ID for entity scoping. */
969
+ deviceId?: string;
970
+ /** Content ID for entity scoping. */
971
+ contentId?: string;
843
972
  }
844
973
  export interface SmartDigestResponse {
845
974
  success: boolean;
@@ -961,6 +1090,223 @@ export interface SearchResponse extends Array<SearchResultItem> {
961
1090
  }
962
1091
  /** @deprecated Use SearchResponse instead. */
963
1092
  export type ExportResponse = SearchResponse;
1093
+ export interface UpdatePropertyOptions {
1094
+ /** Target record ID. */
1095
+ recordId: string;
1096
+ /** Entity type (default: 'contact'). */
1097
+ type?: string;
1098
+ /** Property to update. Required for property updates (mutually exclusive with memoryId+text). */
1099
+ propertyName?: string;
1100
+ /** New property value. Required unless using array operations. */
1101
+ propertyValue?: any;
1102
+ /** Collection ID for the property. */
1103
+ collectionId?: string;
1104
+ /** Confidence score for this value. */
1105
+ confidence?: number;
1106
+ /** Reason for the change (logged in property history). */
1107
+ reason?: string;
1108
+ /** Who made the change (auto-set from API key if omitted). */
1109
+ updatedBy?: string;
1110
+ /** Idempotency key to prevent duplicate writes. */
1111
+ idempotencyKey?: string;
1112
+ /** Optimistic concurrency guard. If set, returns 409 if the record's current version differs. */
1113
+ expectedVersion?: number;
1114
+ /** Append items to an array property. With `unique: true`, skips duplicates. */
1115
+ arrayPush?: {
1116
+ items: any[];
1117
+ unique?: boolean;
1118
+ };
1119
+ /** Remove items from an array property by value or index. */
1120
+ arrayRemove?: {
1121
+ items?: any[];
1122
+ indices?: number[];
1123
+ };
1124
+ /** Update matching objects inside an array property. */
1125
+ arrayPatch?: {
1126
+ match: Record<string, any>;
1127
+ set: Record<string, any>;
1128
+ };
1129
+ /** Freeform memory UUID to edit. */
1130
+ memoryId?: string;
1131
+ /** New text for the freeform memory. */
1132
+ text?: string;
1133
+ }
1134
+ export interface UpdateResult {
1135
+ success: boolean;
1136
+ previousValue?: any;
1137
+ newValue: any;
1138
+ version?: number;
1139
+ stores: {
1140
+ snapshot: 'updated' | 'skipped';
1141
+ lancedb: 'updated' | 'skipped';
1142
+ freeform: 'updated' | 'skipped';
1143
+ };
1144
+ }
1145
+ export interface BulkUpdateOptions {
1146
+ /** Target record ID. */
1147
+ recordId: string;
1148
+ /** Entity type (default: 'contact'). */
1149
+ type?: string;
1150
+ /** Array of property updates. */
1151
+ updates: Array<{
1152
+ propertyName: string;
1153
+ propertyValue: any;
1154
+ collectionId?: string;
1155
+ confidence?: number;
1156
+ }>;
1157
+ /** Who made the changes. */
1158
+ updatedBy?: string;
1159
+ /** Idempotency key to prevent duplicate writes. */
1160
+ idempotencyKey?: string;
1161
+ /** Optimistic concurrency guard. Checked before any writes; 409 if mismatch. */
1162
+ expectedVersion?: number;
1163
+ }
1164
+ export interface BulkUpdateResult {
1165
+ success: boolean;
1166
+ results: Array<{
1167
+ propertyName: string;
1168
+ previousValue?: any;
1169
+ newValue: any;
1170
+ status: 'updated' | 'failed';
1171
+ error?: string;
1172
+ }>;
1173
+ version?: number;
1174
+ }
1175
+ export interface PropertyHistoryOptions {
1176
+ /** Target record ID. */
1177
+ recordId: string;
1178
+ /** Filter to a specific property. */
1179
+ propertyName?: string;
1180
+ /** ISO-8601 lower bound. */
1181
+ from?: string;
1182
+ /** ISO-8601 upper bound. */
1183
+ to?: string;
1184
+ /** Max entries to return (default: 50, max: 200). */
1185
+ limit?: number;
1186
+ /** Pagination cursor from previous response. */
1187
+ nextToken?: string;
1188
+ }
1189
+ export interface PropertyHistoryEntry {
1190
+ entryId: string;
1191
+ propertyName: string;
1192
+ propertyValue: any;
1193
+ collectionId: string;
1194
+ collectionName?: string;
1195
+ updatedBy: string;
1196
+ createdAt: string;
1197
+ source?: string;
1198
+ }
1199
+ export interface PropertyHistoryResult {
1200
+ entries: PropertyHistoryEntry[];
1201
+ nextToken?: string;
1202
+ }
1203
+ export interface QueryPropertiesOptions {
1204
+ /** Which property to search across. */
1205
+ propertyName: string;
1206
+ /** Natural language query. */
1207
+ query: string;
1208
+ /** Limit to single record. */
1209
+ recordId?: string;
1210
+ /** Entity type filter (default: 'contact'). */
1211
+ type?: string;
1212
+ /** Max results (default: 100, max: 200). */
1213
+ limit?: number;
1214
+ }
1215
+ export interface QueryPropertiesResult {
1216
+ matches: Array<{
1217
+ recordId: string;
1218
+ propertyValue: any;
1219
+ matchReason: string;
1220
+ }>;
1221
+ processedCount: number;
1222
+ totalAvailable: number;
1223
+ truncated: boolean;
1224
+ capMessage?: string;
1225
+ }
1226
+ export interface DeleteMemoriesOptions {
1227
+ /** Memory UUIDs to delete. */
1228
+ ids?: string[];
1229
+ /** CRM identifiers for scoping. */
1230
+ crmKeys?: {
1231
+ recordId?: string;
1232
+ email?: string;
1233
+ websiteUrl?: string;
1234
+ };
1235
+ /** ISO date — delete memories older than this. */
1236
+ olderThan?: string;
1237
+ }
1238
+ export interface DeleteRecordOptions {
1239
+ /** Record ID to delete. */
1240
+ recordId: string;
1241
+ /** Entity type (required). */
1242
+ type: string;
1243
+ /** CRM identifiers for additional LanceDB filtering. */
1244
+ crmKeys?: {
1245
+ recordId?: string;
1246
+ email?: string;
1247
+ websiteUrl?: string;
1248
+ };
1249
+ /** Reason for deletion. */
1250
+ reason?: string;
1251
+ /** Who performed the deletion. */
1252
+ performedBy?: string;
1253
+ }
1254
+ export interface DeletionResult {
1255
+ success: boolean;
1256
+ deletedCount?: number;
1257
+ hardDeleteAt?: string;
1258
+ }
1259
+ export interface CancelDeletionOptions {
1260
+ /** Record ID to restore. */
1261
+ recordId: string;
1262
+ /** Entity type (default: 'contact'). */
1263
+ type?: string;
1264
+ /** Who performed the restoration. */
1265
+ performedBy?: string;
1266
+ }
1267
+ export interface CancelDeletionResult {
1268
+ success: boolean;
1269
+ restoredCounts: {
1270
+ snapshot: 'restored' | 'already_gone';
1271
+ freeform: 'restored' | 'already_gone';
1272
+ lancedb: 'restored' | 'already_gone';
1273
+ };
1274
+ warning?: string;
1275
+ }
1276
+ /** Comparison operators for deterministic property filters. */
1277
+ export type FilterOperator = 'equals' | 'notEquals' | 'contains' | 'gt' | 'lt' | 'gte' | 'lte' | 'exists' | 'isEmpty';
1278
+ export interface PropertyFilterCondition {
1279
+ /** Property to filter on. */
1280
+ propertyName: string;
1281
+ /** Comparison operator. */
1282
+ operator: FilterOperator;
1283
+ /** Value to compare against. Not needed for 'exists'/'isEmpty'. */
1284
+ value?: any;
1285
+ }
1286
+ export interface FilterByPropertyOptions {
1287
+ /** Entity type (default: 'contact'). */
1288
+ type?: string;
1289
+ /** Filter conditions. */
1290
+ conditions: PropertyFilterCondition[];
1291
+ /** Combine conditions with AND (default) or OR. */
1292
+ logic?: 'AND' | 'OR';
1293
+ /** Max results (default: 50, max: 200). */
1294
+ limit?: number;
1295
+ /** Pagination cursor. */
1296
+ nextToken?: string;
1297
+ }
1298
+ export interface FilterByPropertyResult {
1299
+ records: Array<{
1300
+ recordId: string;
1301
+ type: string;
1302
+ matchedProperties: Record<string, any>;
1303
+ lastUpdatedAt?: number;
1304
+ }>;
1305
+ totalMatched: number;
1306
+ nextToken?: string;
1307
+ }
1308
+ /** Webhook event types fired by memory CRUD operations. */
1309
+ export type MemoryWebhookEvent = 'memory.property.updated' | 'memory.properties.bulk_updated' | 'memory.updated' | 'memory.deleted' | 'memory.record.deleted' | 'memory.record.deletion_cancelled';
964
1310
  export interface EvaluateMemorizationOptions {
965
1311
  /** Collection to evaluate against. */
966
1312
  collectionId: string;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@personize/sdk",
3
- "version": "0.6.4",
3
+ "version": "0.6.5",
4
4
  "description": "Official Personize SDK",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",