qlogicagent 2.19.13 → 2.20.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/README.md +0 -1
- package/dist/agent-contract.js +1 -1
- package/dist/agent.js +31 -31
- package/dist/cli.js +1 -1
- package/dist/host-contract.js +1 -1
- package/dist/index.js +457 -453
- package/dist/orchestration.js +13 -13
- package/dist/project-memory-host.js +19 -18
- package/dist/protocol.js +1 -1
- package/dist/tunables.js +1 -1
- package/dist/types/cli/acp-extended-handlers.d.ts +5 -10
- package/dist/types/cli/acp-extended-host-adapter.d.ts +1 -1
- package/dist/types/cli/community-workflow-installer.d.ts +2 -2
- package/dist/types/cli/handlers/dream-handler.d.ts +6 -0
- package/dist/types/cli/handlers/goal-handler.d.ts +1 -13
- package/dist/types/cli/handlers/product-handler.d.ts +6 -9
- package/dist/types/cli/handlers/solo-handler.d.ts +3 -6
- package/dist/types/cli/handlers/workflow-compute-handler.d.ts +1 -1
- package/dist/types/cli/memory-coordinator.d.ts +0 -2
- package/dist/types/cli/multi-agent-handler-host.d.ts +1 -1
- package/dist/types/cli/orchestration-memory-context.d.ts +1 -0
- package/dist/types/cli/product-coordinator.d.ts +2 -5
- package/dist/types/cli/rpc-registry.d.ts +0 -3
- package/dist/types/cli/runtime-hook-bootstrap.d.ts +0 -2
- package/dist/types/cli/stdio-rpc-handler-hosts.d.ts +2 -1
- package/dist/types/cli/stdio-server.d.ts +2 -3
- package/dist/types/cli/task-distillation-coordinator.d.ts +0 -3
- package/dist/types/contracts/hooks.d.ts +2 -0
- package/dist/types/host-contract/index.d.ts +3 -13
- package/dist/types/index.d.ts +0 -1
- package/dist/types/orchestration/agent-instance.d.ts +30 -15
- package/dist/types/orchestration/agent-roster.d.ts +2 -2
- package/dist/types/orchestration/goal-loop-coordinator.d.ts +18 -8
- package/dist/types/orchestration/goal-mode-adapters.d.ts +6 -1
- package/dist/types/orchestration/goal-run-persistence.d.ts +12 -10
- package/dist/types/orchestration/goal-run-types.d.ts +3 -21
- package/dist/types/orchestration/index.d.ts +0 -1
- package/dist/types/orchestration/product-checkpoint.d.ts +10 -6
- package/dist/types/orchestration/product-persistence.d.ts +47 -20
- package/dist/types/orchestration/product-planner.d.ts +30 -10
- package/dist/types/orchestration/product-run-coordinator.d.ts +4 -3
- package/dist/types/orchestration/solo-evaluator.d.ts +10 -16
- package/dist/types/orchestration/solo-persistence.d.ts +10 -10
- package/dist/types/orchestration/workflow/budget-permission-gate.d.ts +1 -1
- package/dist/types/orchestration/workflow/capability-catalog.d.ts +11 -34
- package/dist/types/orchestration/workflow/host-executors.d.ts +3 -3
- package/dist/types/orchestration/workflow/n8n-import.d.ts +0 -1
- package/dist/types/orchestration/workflow/node-schema.d.ts +5 -18
- package/dist/types/orchestration/workflow/params-schema.d.ts +7 -16
- package/dist/types/orchestration/workflow/qla-executor-host.d.ts +4 -27
- package/dist/types/orchestration/workflow/workflow-bundle.d.ts +10 -28
- package/dist/types/orchestration/workflow/workflow-controller.d.ts +14 -8
- package/dist/types/orchestration/workflow/workflow-error.d.ts +1 -1
- package/dist/types/orchestration/workflow/workflow-render.d.ts +1 -1
- package/dist/types/orchestration/workflow/workflow-scheduler.d.ts +8 -8
- package/dist/types/orchestration/workflow/workflow-store.d.ts +7 -8
- package/dist/types/orchestration/workflow-chat-builder.d.ts +1 -1
- package/dist/types/protocol/agent-contract.d.ts +7 -7
- package/dist/types/protocol/methods.d.ts +1 -129
- package/dist/types/protocol/notifications.d.ts +1 -1
- package/dist/types/protocol/wire/acp-agent-management.d.ts +45 -24
- package/dist/types/protocol/wire/acp-protocol.d.ts +3 -8
- package/dist/types/protocol/wire/agent-methods.d.ts +2 -468
- package/dist/types/protocol/wire/index.d.ts +1 -1
- package/dist/types/protocol/wire/notification-payloads.d.ts +0 -6
- package/dist/types/protocol/wire/thread-protocol.d.ts +1 -1
- package/dist/types/runtime/config/tunable-defaults.d.ts +0 -9
- package/dist/types/runtime/hooks/memory-hooks.d.ts +11 -4
- package/dist/types/runtime/infra/acp-protocol-adapter.d.ts +1 -2
- package/dist/types/runtime/memory/implicit-extraction.d.ts +4 -1
- package/dist/types/runtime/memory/recall-category-filter.d.ts +0 -12
- package/dist/types/runtime/ports/memory-recall-source.d.ts +1 -0
- package/dist/types/runtime/ports/project-memory-store.d.ts +3 -0
- package/dist/types/skills/memory/host-memory-provider.d.ts +7 -0
- package/dist/types/skills/memory/memdir.d.ts +1 -2
- package/dist/types/skills/memory/task-distillation.d.ts +18 -4
- package/dist/types/skills/skill-system/skill-lifecycle.d.ts +0 -17
- package/dist/types/skills/skill-system/skill-validation.d.ts +1 -1
- package/dist/types/transport/acp-server.d.ts +1 -5
- package/dist/types/workflow-host.d.ts +2 -4
- package/dist/workflow-host.js +7 -9
- package/package.json +1 -1
- package/dist/types/cli/credential-vault.d.ts +0 -68
- package/dist/types/orchestration/skill-improvement.d.ts +0 -97
- package/dist/types/skills/memory/local-store-records.d.ts +0 -206
- package/dist/types/skills/memory/local-store.d.ts +0 -376
- package/dist/types/skills/memory/memory-attachment-store.d.ts +0 -62
- package/dist/types/skills/memory/memory-consolidation.d.ts +0 -64
- package/dist/types/skills/memory/memory-db-path.d.ts +0 -13
- package/dist/types/skills/memory/proposal-consumer.d.ts +0 -51
- package/dist/types/skills/memory/sqlite-memory-mappers.d.ts +0 -7
- package/dist/types/skills/memory/sqlite-memory-schema.d.ts +0 -11
|
@@ -1,376 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Local Memory Store - SQLite-backed persistence for qmemory.
|
|
3
|
-
*
|
|
4
|
-
* Ported from Python qmemory's memory_store.py + db.py.
|
|
5
|
-
* Uses better-sqlite3 for synchronous, fast, single-file persistence.
|
|
6
|
-
*
|
|
7
|
-
* Storage location:
|
|
8
|
-
* ~/.qlogicagent/profiles/<owner_user_id>/memory/memories.db
|
|
9
|
-
*
|
|
10
|
-
* Schema:
|
|
11
|
-
* - memories: core fact storage with optional embedding blob
|
|
12
|
-
* - memories_fts: FTS5 full-text index for keyword search
|
|
13
|
-
* - profiles: user profile KV (future)
|
|
14
|
-
*/
|
|
15
|
-
import type { MemoryAtlasResult, MemoryClaimInput, MemoryClaimRecord, MemoryClaimStatus, MemoryConflictRecord, MemoryInsertInput, MemoryObservationInput, MemoryProposalInput, MemoryProposalRecord, MemoryProposalStatus, MemoryRecord, MemorySearchHit, MemoryUpdateInput, SqliteDatabase } from "./local-store-records.js";
|
|
16
|
-
export { resolveMemoryDbPath } from "./memory-db-path.js";
|
|
17
|
-
export type { MemoryAtlasBucket, MemoryAtlasCluster, MemoryAtlasResult, MemoryAtlasWindowCursor, MemoryAttachmentRef, MemoryClaimInput, MemoryClaimRecord, MemoryClaimStatus, MemoryConflictRecord, MemoryInsertInput, MemoryObservationInput, MemoryObservationRecord, MemoryProposalInput, MemoryProposalRecord, MemoryProposalStatus, MemoryRecord, MemorySearchHit, MemorySourceKind, MemoryUpdateInput, SqliteDatabase, SqliteStatement, } from "./local-store-records.js";
|
|
18
|
-
/** Full attachment index row (DB-backed; file bytes live on disk under the attachments dir). */
|
|
19
|
-
export interface MemoryAttachmentRow {
|
|
20
|
-
id: string;
|
|
21
|
-
memoryId: string;
|
|
22
|
-
userId: string;
|
|
23
|
-
kind: string;
|
|
24
|
-
filename: string;
|
|
25
|
-
mimeType: string;
|
|
26
|
-
size: number;
|
|
27
|
-
relPath: string;
|
|
28
|
-
extractedText: string;
|
|
29
|
-
createdAt: number;
|
|
30
|
-
}
|
|
31
|
-
export interface MemoryAttachmentInsert {
|
|
32
|
-
id: string;
|
|
33
|
-
userId: string;
|
|
34
|
-
kind: string;
|
|
35
|
-
filename: string;
|
|
36
|
-
mimeType: string;
|
|
37
|
-
size: number;
|
|
38
|
-
relPath: string;
|
|
39
|
-
extractedText?: string;
|
|
40
|
-
memoryId?: string;
|
|
41
|
-
}
|
|
42
|
-
export declare class LocalMemoryStore {
|
|
43
|
-
private db;
|
|
44
|
-
/** Stamped onto rows whose embedding arrives without explicit provenance
|
|
45
|
-
* (the consolidation pipeline passes bare vectors). Set by the provider. */
|
|
46
|
-
private defaultEmbeddingModel;
|
|
47
|
-
constructor(db: SqliteDatabase);
|
|
48
|
-
setDefaultEmbeddingModel(model: string): void;
|
|
49
|
-
private initSchema;
|
|
50
|
-
/**
|
|
51
|
-
* Insert a new memory record. Returns the generated ID.
|
|
52
|
-
*/
|
|
53
|
-
insert(input: MemoryInsertInput): string;
|
|
54
|
-
/**
|
|
55
|
-
* Full-text search using FTS5. Returns ranked results.
|
|
56
|
-
*/
|
|
57
|
-
searchFts(query: string, userId: string, limit?: number): MemorySearchHit[];
|
|
58
|
-
/** One-shot flag: embedding provenance mismatches are traced once per store instance. */
|
|
59
|
-
private embeddingMismatchLogged;
|
|
60
|
-
/**
|
|
61
|
-
* Vector similarity search using pre-computed embeddings.
|
|
62
|
-
* Performs brute-force cosine similarity (efficient for <100k records per user).
|
|
63
|
-
*
|
|
64
|
-
* Rows whose embedding provenance (dims, and model when both sides are known)
|
|
65
|
-
* differs from the query's are SKIPPED, not scored: cosine between vectors of
|
|
66
|
-
* different models/dims is numeric noise, and truncated dot products silently
|
|
67
|
-
* corrupt ranking. Legacy rows (no provenance columns) are accepted when their
|
|
68
|
-
* dimension happens to match — dropping them all would blank historical recall.
|
|
69
|
-
*/
|
|
70
|
-
searchVector(queryEmbedding: Float32Array, userId: string, limit?: number, minScore?: number, expectedModel?: string): MemorySearchHit[];
|
|
71
|
-
/**
|
|
72
|
-
* Hybrid search: FTS5 + vector similarity, fused by rank-tempered RRF.
|
|
73
|
-
*
|
|
74
|
-
* Two currencies, each carrying signal the other cannot:
|
|
75
|
-
* - channel scores (0-1, isomorphic across FTS/vector) carry MAGNITUDE —
|
|
76
|
-
* an exact lexical hit must beat weak-consensus noise, which pure rank
|
|
77
|
-
* fusion cannot guarantee (rank ignores how strong a match is);
|
|
78
|
-
* - reciprocal ranks carry CONSENSUS and are scale-invariant — as the
|
|
79
|
-
* store grows, BM25 inflates until squashed top scores compress to
|
|
80
|
-
* near-ties and the two channels' score distributions drift apart;
|
|
81
|
-
* ranks keep differentiating where magnitudes saturate.
|
|
82
|
-
* fused = (1-w)*magnitude + w*rrfNorm keeps both properties. Magnitude of a
|
|
83
|
-
* dual hit is the stronger channel plus a fraction of the weaker (consensus
|
|
84
|
-
* also rewarded in score space); rrfNorm is the reciprocal-rank sum
|
|
85
|
-
* normalized so a dual #1 hit = 1.0. FTS ranks follow BM25 order, vector
|
|
86
|
-
* ranks follow the blended channel order — each channel's own relevance
|
|
87
|
-
* ordering. Rows found by FTS only (e.g. no embedding) compete in the same
|
|
88
|
-
* fused domain and remain reachable, not buried.
|
|
89
|
-
*/
|
|
90
|
-
searchHybrid(query: string, queryEmbedding: Float32Array | null, userId: string, limit?: number, expectedModel?: string): MemorySearchHit[];
|
|
91
|
-
/**
|
|
92
|
-
* Get all memories for a user (paginated).
|
|
93
|
-
*/
|
|
94
|
-
listByUser(userId: string, page?: number, pageSize?: number, activeOnly?: boolean): MemoryRecord[];
|
|
95
|
-
/**
|
|
96
|
-
* All active memories carrying a tag (LIKE match on the quoted JSON-array
|
|
97
|
-
* element). Tag consumers (resident refresh / onboarding replace-purge) need
|
|
98
|
-
* the COMPLETE tag set regardless of age — the windowed atlas read silently
|
|
99
|
-
* truncated them once history outgrew one page/time window. No LIMIT by
|
|
100
|
-
* design: a capped "complete" read is the same bug at a higher threshold
|
|
101
|
-
* (a purge that misses rows resurrects stale memories). Tag sets are small
|
|
102
|
-
* (one origin/resident group), and this is not a hot path.
|
|
103
|
-
*/
|
|
104
|
-
listByTag(userId: string, tag: string): MemoryRecord[];
|
|
105
|
-
/**
|
|
106
|
-
* Return a windowed atlas payload for large-history visualization.
|
|
107
|
-
*
|
|
108
|
-
* `records` are only the interactive window. `buckets` and `clusters` summarize
|
|
109
|
-
* the whole history so the UI can render distant history as star dust /
|
|
110
|
-
* aggregate galaxies without loading every memory as an interactive object.
|
|
111
|
-
*/
|
|
112
|
-
getAtlas(userId: string, options?: {
|
|
113
|
-
pageSize?: number;
|
|
114
|
-
windowStartAt?: number;
|
|
115
|
-
windowEndAt?: number;
|
|
116
|
-
windowCenterAt?: number;
|
|
117
|
-
bucketCount?: number;
|
|
118
|
-
clusterLimit?: number;
|
|
119
|
-
activeOnly?: boolean;
|
|
120
|
-
}): MemoryAtlasResult;
|
|
121
|
-
private getAtlasBuckets;
|
|
122
|
-
private getAtlasClusters;
|
|
123
|
-
/**
|
|
124
|
-
* Get a single memory by ID.
|
|
125
|
-
*/
|
|
126
|
-
getById(id: string): MemoryRecord | null;
|
|
127
|
-
/**
|
|
128
|
-
* Update memory text and bump updatedAt.
|
|
129
|
-
*/
|
|
130
|
-
updateText(id: string, text: string, embedding?: Float32Array, embeddingModel?: string): boolean;
|
|
131
|
-
/**
|
|
132
|
-
* Update editable memory fields and bump updatedAt.
|
|
133
|
-
*/
|
|
134
|
-
update(id: string, input: MemoryUpdateInput): boolean;
|
|
135
|
-
/**
|
|
136
|
-
* Delete a memory by ID.
|
|
137
|
-
*/
|
|
138
|
-
delete(id: string): boolean;
|
|
139
|
-
/**
|
|
140
|
-
* Archive a memory (soft-delete: set is_archived=1).
|
|
141
|
-
* Used by dedup gate when a similar but newer memory supersedes an older one.
|
|
142
|
-
*/
|
|
143
|
-
archive(id: string): boolean;
|
|
144
|
-
/** V3 demote(降格)恢复:archived procedure 回归召回池,与 archive 成对。 */
|
|
145
|
-
unarchive(id: string): boolean;
|
|
146
|
-
/**
|
|
147
|
-
* Temporal expiry: archive event/plan memories whose event_date has passed
|
|
148
|
-
* beyond a grace period (e.g., "meeting tomorrow" 3 days after it happened).
|
|
149
|
-
*/
|
|
150
|
-
decayTemporalExpiry(userId: string, graceDays?: number): number;
|
|
151
|
-
/**
|
|
152
|
-
* Staleness decay: reduce importance of memories not accessed in a long time.
|
|
153
|
-
* Memories accessed recently retain their importance; stale ones degrade.
|
|
154
|
-
*/
|
|
155
|
-
decayStaleness(userId: string, staleDays?: number, decayFactor?: number): number;
|
|
156
|
-
/**
|
|
157
|
-
* Noise archival: archive low-importance memories that never got accessed.
|
|
158
|
-
* Memories written by the agent but never recalled are likely noise.
|
|
159
|
-
*/
|
|
160
|
-
decayNoiseArchival(userId: string, minAgeDays?: number, maxImportance?: number): number;
|
|
161
|
-
/**
|
|
162
|
-
* Observation retention: memory_observations is an append-only audit trail
|
|
163
|
-
* (every propose/commit writes one) with NO reader of its own — without a
|
|
164
|
-
* retention window it grows forever, the same disease the proposals table
|
|
165
|
-
* had before the consumer existed. Delete rows older than the window that
|
|
166
|
-
* are NOT referenced by any claim's evidence_ids or proposal's
|
|
167
|
-
* observation_ids (referenced rows are live audit evidence and stay).
|
|
168
|
-
*/
|
|
169
|
-
decayObservations(userId: string, retentionDays?: number): number;
|
|
170
|
-
/**
|
|
171
|
-
* Resolved-proposal retention: terminal rows (accepted/merged/rejected/
|
|
172
|
-
* expired) are processing history, not memory — past the window they only
|
|
173
|
-
* grow the table. Rows carrying an idempotency_key are KEPT FOREVER: they
|
|
174
|
-
* are the crash-safe ledger that stops feedback distillation from
|
|
175
|
-
* re-proposing the same evidence cluster (deleting them would re-open the
|
|
176
|
-
* exact duplicate-write hole the key exists to close). Pending rows are
|
|
177
|
-
* never touched here — the consumer owns their TTL (status=expired).
|
|
178
|
-
*/
|
|
179
|
-
decayResolvedProposals(userId: string, retentionDays?: number): number;
|
|
180
|
-
/**
|
|
181
|
-
* Run all decay strategies. Returns total affected count.
|
|
182
|
-
*/
|
|
183
|
-
runFullDecay(userId: string, options?: {
|
|
184
|
-
temporalGraceDays?: number;
|
|
185
|
-
staleDays?: number;
|
|
186
|
-
staleDecayFactor?: number;
|
|
187
|
-
noiseMinAgeDays?: number;
|
|
188
|
-
noiseMaxImportance?: number;
|
|
189
|
-
}): {
|
|
190
|
-
temporal: number;
|
|
191
|
-
stale: number;
|
|
192
|
-
noise: number;
|
|
193
|
-
total: number;
|
|
194
|
-
};
|
|
195
|
-
/**
|
|
196
|
-
* Apply feedback signal to a memory, adjusting importance accordingly.
|
|
197
|
-
*
|
|
198
|
-
* Signals:
|
|
199
|
-
* - "useful" boosts importance by +0.15 (capped at 1.0)
|
|
200
|
-
* - "irrelevant" reduces importance by -0.2
|
|
201
|
-
* - "outdated" archives immediately
|
|
202
|
-
* - "wrong" deletes immediately
|
|
203
|
-
*/
|
|
204
|
-
applyFeedback(memoryId: string, signal: "useful" | "irrelevant" | "outdated" | "wrong"): boolean;
|
|
205
|
-
/**
|
|
206
|
-
* Get a profile value for a user.
|
|
207
|
-
*/
|
|
208
|
-
getProfile(userId: string, key: string): string | null;
|
|
209
|
-
/**
|
|
210
|
-
* Set a profile value (upsert).
|
|
211
|
-
*/
|
|
212
|
-
setProfile(userId: string, key: string, value: string): void;
|
|
213
|
-
/**
|
|
214
|
-
* Get all profile entries for a user.
|
|
215
|
-
*/
|
|
216
|
-
getAllProfiles(userId: string): Record<string, string>;
|
|
217
|
-
/**
|
|
218
|
-
* Delete a profile entry.
|
|
219
|
-
*/
|
|
220
|
-
deleteProfile(userId: string, key: string): boolean;
|
|
221
|
-
private profileTableCreated;
|
|
222
|
-
private ensureProfileTable;
|
|
223
|
-
/**
|
|
224
|
-
* Retrieve memories within a time range, grouped by day.
|
|
225
|
-
* Used for "what happened last week" type queries and dream synthesis.
|
|
226
|
-
*/
|
|
227
|
-
getTemporalSlice(userId: string, startMs: number, endMs: number, options?: {
|
|
228
|
-
category?: string;
|
|
229
|
-
limit?: number;
|
|
230
|
-
}): Array<{
|
|
231
|
-
date: string;
|
|
232
|
-
memories: Array<{
|
|
233
|
-
id: string;
|
|
234
|
-
text: string;
|
|
235
|
-
category: string;
|
|
236
|
-
importance: number;
|
|
237
|
-
}>;
|
|
238
|
-
}>;
|
|
239
|
-
/**
|
|
240
|
-
* Get memory activity summary over recent N days.
|
|
241
|
-
* Returns daily counts and high-importance entries used by temporal synthesis.
|
|
242
|
-
*/
|
|
243
|
-
getActivitySummary(userId: string, days?: number): {
|
|
244
|
-
dailyCounts: Array<{
|
|
245
|
-
date: string;
|
|
246
|
-
count: number;
|
|
247
|
-
}>;
|
|
248
|
-
highlights: Array<{
|
|
249
|
-
id: string;
|
|
250
|
-
text: string;
|
|
251
|
-
category: string;
|
|
252
|
-
importance: number;
|
|
253
|
-
date: string;
|
|
254
|
-
}>;
|
|
255
|
-
};
|
|
256
|
-
/**
|
|
257
|
-
* Record an access (for importance/relevance boosting).
|
|
258
|
-
*/
|
|
259
|
-
recordAccess(id: string): void;
|
|
260
|
-
/** Total active memory rows across ALL users (health reporting). */
|
|
261
|
-
countAll(): number;
|
|
262
|
-
/**
|
|
263
|
-
* Get total memory count for a user.
|
|
264
|
-
*/
|
|
265
|
-
count(userId: string, activeOnly?: boolean): number;
|
|
266
|
-
/**
|
|
267
|
-
* Delete ALL long-term memory state for a user — every table, not just
|
|
268
|
-
* `memories`. Claims carry entity/predicate/value facts in clear text and
|
|
269
|
-
* observations carry raw conversation excerpts; leaving them behind after a
|
|
270
|
-
* "clear my memory" is a broken privacy promise, not a smaller reset.
|
|
271
|
-
*
|
|
272
|
-
* Returns the attachment rel_paths so the caller can delete the on-disk
|
|
273
|
-
* files (the store only owns the index rows).
|
|
274
|
-
*/
|
|
275
|
-
resetUser(userId: string): {
|
|
276
|
-
memories: number;
|
|
277
|
-
observations: number;
|
|
278
|
-
proposals: number;
|
|
279
|
-
claims: number;
|
|
280
|
-
conflicts: number;
|
|
281
|
-
profiles: number;
|
|
282
|
-
attachmentRelPaths: string[];
|
|
283
|
-
};
|
|
284
|
-
/**
|
|
285
|
-
* Run SQLite VACUUM to reclaim space after deletions/archival.
|
|
286
|
-
* Should be called periodically (e.g. after decay cycles).
|
|
287
|
-
*/
|
|
288
|
-
vacuum(): void;
|
|
289
|
-
/**
|
|
290
|
-
* Get database size info for capacity monitoring.
|
|
291
|
-
*/
|
|
292
|
-
getStorageStats(): {
|
|
293
|
-
pageCount: number;
|
|
294
|
-
pageSize: number;
|
|
295
|
-
totalBytes: number;
|
|
296
|
-
freePages: number;
|
|
297
|
-
};
|
|
298
|
-
/**
|
|
299
|
-
* List the oldest archived memories for cold-storage export. Read-only:
|
|
300
|
-
* purging is a SEPARATE step (purgeMemoriesByIds) the caller performs only
|
|
301
|
-
* after the export has durably landed on disk. The old fused
|
|
302
|
-
* export-then-delete shape destroyed data whenever the caller dropped the
|
|
303
|
-
* return value.
|
|
304
|
-
*/
|
|
305
|
-
listArchivedForExport(userId: string, maxExport?: number): Array<{
|
|
306
|
-
id: string;
|
|
307
|
-
text: string;
|
|
308
|
-
category: string;
|
|
309
|
-
importance: number;
|
|
310
|
-
createdAt: number;
|
|
311
|
-
archivedAt: number;
|
|
312
|
-
tags: string[];
|
|
313
|
-
}>;
|
|
314
|
-
/** Physically delete memory rows by id (post-export purge step). */
|
|
315
|
-
purgeMemoriesByIds(ids: string[]): number;
|
|
316
|
-
/**
|
|
317
|
-
* Enforce capacity limit: if active memories exceed maxCount,
|
|
318
|
-
* archive the oldest lowest-importance ones.
|
|
319
|
-
*/
|
|
320
|
-
enforceCapacityLimit(userId: string, maxCount?: number): number;
|
|
321
|
-
insertObservation(input: MemoryObservationInput): string;
|
|
322
|
-
insertProposal(input: MemoryProposalInput): string;
|
|
323
|
-
/**
|
|
324
|
-
* Look up an existing proposal by its idempotency key (feedback distillation — §10). Returns the
|
|
325
|
-
* proposal id if one already exists for this user + key, else null, letting proposeExtracted skip
|
|
326
|
-
* a duplicate crash-safely (the key survives a worker restart mid-sweep).
|
|
327
|
-
*/
|
|
328
|
-
findProposalByIdempotencyKey(userId: string, idempotencyKey: string): string | null;
|
|
329
|
-
/**
|
|
330
|
-
* List proposals by status (oldest first) — the read side of the proposal
|
|
331
|
-
* consumer. Pending proposals from implicit-extract / feedback / dream used
|
|
332
|
-
* to have NO reader at all: they accumulated forever and never became
|
|
333
|
-
* searchable memories.
|
|
334
|
-
*/
|
|
335
|
-
listProposalsByStatus(userId: string, status: MemoryProposalStatus, limit?: number): MemoryProposalRecord[];
|
|
336
|
-
/** Bulk status transition for the proposal consumer (corroborated / expired). */
|
|
337
|
-
markProposalsStatus(ids: string[], status: MemoryProposalStatus): number;
|
|
338
|
-
updateProposalStatus(id: string, status: MemoryProposalStatus, relatedClaimIds?: string[]): boolean;
|
|
339
|
-
insertClaim(input: MemoryClaimInput): string;
|
|
340
|
-
listClaims(userId: string, statuses?: MemoryClaimStatus[]): MemoryClaimRecord[];
|
|
341
|
-
findClaimsByFact(userId: string, entity: string, predicate: string, validTime?: string): MemoryClaimRecord[];
|
|
342
|
-
mergeClaimEvidence(id: string, evidenceIds: string[], confidence: number, importance: number): boolean;
|
|
343
|
-
updateClaimsByMemoryId(memoryId: string, status: MemoryClaimStatus): number;
|
|
344
|
-
insertConflict(input: {
|
|
345
|
-
userId: string;
|
|
346
|
-
claimAId: string;
|
|
347
|
-
claimBId: string;
|
|
348
|
-
reason: string;
|
|
349
|
-
}): string;
|
|
350
|
-
listConflicts(userId: string): MemoryConflictRecord[];
|
|
351
|
-
getClaimById(id: string): MemoryClaimRecord | undefined;
|
|
352
|
-
setClaimStatus(id: string, status: MemoryClaimStatus): boolean;
|
|
353
|
-
/** Mark a conflict resolved (the resolver has already updated the claims). */
|
|
354
|
-
setConflictStatus(id: string, status: "open" | "resolved" | "dismissed"): boolean;
|
|
355
|
-
/** Open conflicts only (the ones needing resolution). */
|
|
356
|
-
listOpenConflicts(userId: string): MemoryConflictRecord[];
|
|
357
|
-
/**
|
|
358
|
-
* Promote pending_confirmation claims that have accumulated enough independent
|
|
359
|
-
* evidence to become active. Returns the number promoted.
|
|
360
|
-
*/
|
|
361
|
-
promotePendingClaims(userId: string, minEvidence: number): number;
|
|
362
|
-
insertAttachment(input: MemoryAttachmentInsert): void;
|
|
363
|
-
getAttachmentById(id: string): MemoryAttachmentRow | null;
|
|
364
|
-
listAttachmentsByMemoryId(memoryId: string): MemoryAttachmentRow[];
|
|
365
|
-
/** Batch-load attachments for many memories (for atlas windows). */
|
|
366
|
-
listAttachmentsByMemoryIds(memoryIds: string[]): Map<string, MemoryAttachmentRow[]>;
|
|
367
|
-
/** Link orphan/owned attachments to a committed memory. Returns linked count. */
|
|
368
|
-
linkAttachments(memoryId: string, attachmentIds: string[], userId: string): number;
|
|
369
|
-
setAttachmentExtractedText(id: string, text: string): boolean;
|
|
370
|
-
/** Delete attachment index rows for a memory; returns their rel paths for file cleanup. */
|
|
371
|
-
deleteAttachmentsByMemoryId(memoryId: string): string[];
|
|
372
|
-
/** Orphan attachments (uploaded but never saved to a memory) older than cutoff. */
|
|
373
|
-
listOrphanAttachments(cutoff: number): MemoryAttachmentRow[];
|
|
374
|
-
deleteAttachmentById(id: string): void;
|
|
375
|
-
close(): void;
|
|
376
|
-
}
|
|
@@ -1,62 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* MemoryAttachmentStore — persistent attachment storage for long-term memory.
|
|
3
|
-
*
|
|
4
|
-
* Files live beside the memory DB, with no expiry:
|
|
5
|
-
* ~/.qlogicagent/profiles/<owner>/memory/attachments/<id><ext>
|
|
6
|
-
* The DB (`memory_attachments` table, via LocalMemoryStore) is the index;
|
|
7
|
-
* this class owns the on-disk bytes + ties index rows to files.
|
|
8
|
-
*
|
|
9
|
-
* Lifecycle: an attachment is `adopt`ed at upload time (orphan, memory_id=''),
|
|
10
|
-
* then `link`ed to a memory at commit; on memory delete the files+rows are
|
|
11
|
-
* removed; long-orphaned uploads are purged.
|
|
12
|
-
*/
|
|
13
|
-
import type { LocalMemoryStore, MemoryAttachmentRef, MemoryAttachmentRow } from "./local-store.js";
|
|
14
|
-
export declare const MAX_ATTACHMENT_BYTES: number;
|
|
15
|
-
export type AttachmentKind = "image" | "audio" | "video" | "doc" | "file";
|
|
16
|
-
export declare function attachmentKindFromMime(mimeType: string, filename?: string): AttachmentKind;
|
|
17
|
-
export interface AdoptedAttachment {
|
|
18
|
-
id: string;
|
|
19
|
-
kind: AttachmentKind;
|
|
20
|
-
filename: string;
|
|
21
|
-
mimeType: string;
|
|
22
|
-
size: number;
|
|
23
|
-
url: string;
|
|
24
|
-
}
|
|
25
|
-
export interface AdoptInput {
|
|
26
|
-
/** Raw bytes (preferred). */
|
|
27
|
-
data?: Buffer;
|
|
28
|
-
/** Or a URL the store fetches (e.g. the gateway's temp MediaStore url). */
|
|
29
|
-
sourceUrl?: string;
|
|
30
|
-
filename: string;
|
|
31
|
-
mimeType: string;
|
|
32
|
-
userId: string;
|
|
33
|
-
}
|
|
34
|
-
export declare class MemoryAttachmentStore {
|
|
35
|
-
private readonly store;
|
|
36
|
-
private readonly dir;
|
|
37
|
-
constructor(store: LocalMemoryStore, dir: string);
|
|
38
|
-
urlFor(id: string): string;
|
|
39
|
-
toRef(row: MemoryAttachmentRow): MemoryAttachmentRef;
|
|
40
|
-
/** Persist an uploaded file + create an orphan index row (memory_id=''). */
|
|
41
|
-
adopt(input: AdoptInput): Promise<AdoptedAttachment>;
|
|
42
|
-
/** Read an attachment's bytes + mime (for multimodal understanding). */
|
|
43
|
-
readBytes(id: string): Promise<{
|
|
44
|
-
bytes: Buffer;
|
|
45
|
-
mimeType: string;
|
|
46
|
-
} | null>;
|
|
47
|
-
/** Resolve an attachment to an absolute on-disk path (for serving). Guards traversal. */
|
|
48
|
-
locate(id: string): Promise<{
|
|
49
|
-
absPath: string;
|
|
50
|
-
mimeType: string;
|
|
51
|
-
filename: string;
|
|
52
|
-
} | null>;
|
|
53
|
-
link(memoryId: string, attachmentIds: string[], userId: string): number;
|
|
54
|
-
setExtractedText(id: string, text: string): void;
|
|
55
|
-
refsForMemory(memoryId: string): MemoryAttachmentRef[];
|
|
56
|
-
/** Map of memoryId → refs, for atlas windows. */
|
|
57
|
-
refsForMemories(memoryIds: string[]): Map<string, MemoryAttachmentRef[]>;
|
|
58
|
-
/** Remove all files + index rows for a deleted memory. */
|
|
59
|
-
removeByMemoryId(memoryId: string): Promise<void>;
|
|
60
|
-
/** Purge uploads that were never linked to a saved memory. */
|
|
61
|
-
purgeOrphans(olderThanMs?: number): Promise<void>;
|
|
62
|
-
}
|
|
@@ -1,64 +0,0 @@
|
|
|
1
|
-
import { LocalMemoryStore } from "./local-store.js";
|
|
2
|
-
/** A pre-extracted memory item ready to be stored (no LLM needed). */
|
|
3
|
-
export interface ExtractedMemoryItem {
|
|
4
|
-
text: string;
|
|
5
|
-
category?: string;
|
|
6
|
-
importance?: number;
|
|
7
|
-
speaker?: string;
|
|
8
|
-
event_date?: string;
|
|
9
|
-
tags?: string[];
|
|
10
|
-
/** Ids of already-uploaded attachments to link to this memory on commit. */
|
|
11
|
-
attachmentIds?: string[];
|
|
12
|
-
/**
|
|
13
|
-
* Explicit confidence for evidence-bearing sources (feedback distillation — §10). When set,
|
|
14
|
-
* proposeExtracted uses it verbatim instead of the source-derived default. Other callers omit it.
|
|
15
|
-
*/
|
|
16
|
-
confidence?: number;
|
|
17
|
-
/**
|
|
18
|
-
* Evidence trail for distillation-style sources. `refs` (e.g. feedbackIds + turn:<id>) is stored
|
|
19
|
-
* on the observation for audit; `idempotencyKey` makes the proposal insert crash-safe + dedup'd.
|
|
20
|
-
*/
|
|
21
|
-
evidence?: {
|
|
22
|
-
kind: string;
|
|
23
|
-
refs: string[];
|
|
24
|
-
idempotencyKey: string;
|
|
25
|
-
};
|
|
26
|
-
}
|
|
27
|
-
export interface MemoryConsolidationOptions {
|
|
28
|
-
source?: string;
|
|
29
|
-
sessionId?: string;
|
|
30
|
-
}
|
|
31
|
-
export interface MemoryConsolidationResult {
|
|
32
|
-
observationsAdded: number;
|
|
33
|
-
proposalsAdded: number;
|
|
34
|
-
claimsAdded: number;
|
|
35
|
-
conflictsAdded: number;
|
|
36
|
-
memoriesAdded: number;
|
|
37
|
-
observationIds: string[];
|
|
38
|
-
proposalIds: string[];
|
|
39
|
-
claimIds: string[];
|
|
40
|
-
conflictIds: string[];
|
|
41
|
-
}
|
|
42
|
-
export declare class MemoryConsolidator {
|
|
43
|
-
private readonly store;
|
|
44
|
-
private readonly embed;
|
|
45
|
-
constructor(store: LocalMemoryStore, embed: (text: string) => Promise<Float32Array | undefined>);
|
|
46
|
-
observe(items: ExtractedMemoryItem[], userId: string, options?: MemoryConsolidationOptions): Promise<MemoryConsolidationResult>;
|
|
47
|
-
proposeExtracted(items: ExtractedMemoryItem[], userId: string, options?: MemoryConsolidationOptions): Promise<MemoryConsolidationResult>;
|
|
48
|
-
commitExtracted(items: ExtractedMemoryItem[], userId: string, options?: MemoryConsolidationOptions): Promise<MemoryConsolidationResult>;
|
|
49
|
-
/**
|
|
50
|
-
* Find an existing active memory that is a near-duplicate of `text`.
|
|
51
|
-
* Token containment (Latin/digit words + CJK bigrams) against recent
|
|
52
|
-
* memories; digit-bearing token mismatches veto the match because numbers
|
|
53
|
-
* and ids are precise facts, not phrasing variance.
|
|
54
|
-
*/
|
|
55
|
-
private findNearDuplicateMemory;
|
|
56
|
-
}
|
|
57
|
-
/** Containment threshold above which two texts count as the same memory.
|
|
58
|
-
* Exported: the proposal consumer uses the SAME bar to group same-fact proposals. */
|
|
59
|
-
export declare const NEAR_DUPLICATE_CONTAINMENT = 0.82;
|
|
60
|
-
/** Latin/digit words plus CJK character bigrams from normalized text. */
|
|
61
|
-
export declare function dedupTokens(text: string): Set<string>;
|
|
62
|
-
/** True when either side has a digit-bearing token the other side lacks. */
|
|
63
|
-
export declare function digitTokensDiffer(a: Set<string>, b: Set<string>): boolean;
|
|
64
|
-
export declare function sourcePriorityOf(source: string): number;
|
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
import type { PathService } from "../../runtime/ports/index.js";
|
|
2
|
-
/**
|
|
3
|
-
* Resolve the database file path for L2 vector memory storage.
|
|
4
|
-
* L2 vector memory is cross-project for one owner, but physically isolated by
|
|
5
|
-
* profile at ~/.qlogicagent/profiles/<owner_user_id>/memory/.
|
|
6
|
-
*/
|
|
7
|
-
export declare function resolveMemoryDbPath(ownerUserId?: string, pathService?: PathService): string;
|
|
8
|
-
/**
|
|
9
|
-
* Persistent attachment directory for long-term memory, beside the memory DB:
|
|
10
|
-
* ~/.qlogicagent/profiles/<owner_user_id>/memory/attachments/
|
|
11
|
-
* Files here live as long as the memories that reference them (no expiry).
|
|
12
|
-
*/
|
|
13
|
-
export declare function resolveMemoryAttachmentsDir(ownerUserId?: string, pathService?: PathService): string;
|
|
@@ -1,51 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Proposal consumer (P0 — the factual-memory half of the promotion ladder).
|
|
3
|
-
*
|
|
4
|
-
* implicit-extract / feedback-distillation / dream all write PROPOSALS
|
|
5
|
-
* (status=pending). Before this module existed nothing ever read them back:
|
|
6
|
-
* the three automatic learning paths burned model calls writing dead rows.
|
|
7
|
-
*
|
|
8
|
-
* Trust ladder — evidence gates autonomy, mirroring the V3 skill-promotion
|
|
9
|
-
* doctrine (automatic only when the data says so; visible; revertible):
|
|
10
|
-
* - CORROBORATED: the same fact proposed >=2 times from independent
|
|
11
|
-
* contexts (different session, or different source) -> auto-commit as
|
|
12
|
-
* source "corroborated" (priority 70, so it actually becomes an active
|
|
13
|
-
* searchable memory — committing with the original implicit-extract
|
|
14
|
-
* priority 40 would just create another pending claim, i.e. the black
|
|
15
|
-
* hole one level deeper).
|
|
16
|
-
* - feedback-distillation proposals commit ALONE: their >=2-evidence bar
|
|
17
|
-
* was already enforced upstream (MIN_EVIDENCE + idempotency key, §10).
|
|
18
|
-
* - dream-tier sources (priority <= 20) never commit alone; they only
|
|
19
|
-
* corroborate facts seen elsewhere.
|
|
20
|
-
* - Everything else waits, and past the TTL flips to status "expired" —
|
|
21
|
-
* a visible terminal state, not a silent delete; the memory surface can
|
|
22
|
-
* still show expired proposals for manual rescue.
|
|
23
|
-
*
|
|
24
|
-
* Pure planning logic — no I/O; the provider executes the plan.
|
|
25
|
-
*/
|
|
26
|
-
import type { MemoryProposalRecord } from "./local-store-records.js";
|
|
27
|
-
import type { ExtractedMemoryItem } from "./memory-consolidation.js";
|
|
28
|
-
/** Uncorroborated proposals older than this flip to "expired". */
|
|
29
|
-
export declare const PROPOSAL_TTL_MS: number;
|
|
30
|
-
/** Independent contexts required for auto-commit. */
|
|
31
|
-
export declare const PROPOSAL_MIN_CORROBORATION = 2;
|
|
32
|
-
/** Idle-pass work cap; the rest stays pending for the next pass. */
|
|
33
|
-
export declare const PROPOSAL_MAX_COMMITS_PER_PASS = 20;
|
|
34
|
-
/** Source stamped on corroborated commits — registered in sourcePriorityOf. */
|
|
35
|
-
export declare const CORROBORATED_SOURCE = "corroborated";
|
|
36
|
-
export interface ProposalCommitGroup {
|
|
37
|
-
proposalIds: string[];
|
|
38
|
-
item: ExtractedMemoryItem;
|
|
39
|
-
/** Source used for the commit (drives claim authority). */
|
|
40
|
-
source: string;
|
|
41
|
-
}
|
|
42
|
-
export interface ProposalConsumptionSummary {
|
|
43
|
-
commitGroups: ProposalCommitGroup[];
|
|
44
|
-
expiredIds: string[];
|
|
45
|
-
}
|
|
46
|
-
export interface ProposalConsumptionOptions {
|
|
47
|
-
now?: number;
|
|
48
|
-
ttlMs?: number;
|
|
49
|
-
maxCommitsPerPass?: number;
|
|
50
|
-
}
|
|
51
|
-
export declare function planProposalConsumption(pending: readonly MemoryProposalRecord[], opts?: ProposalConsumptionOptions): ProposalConsumptionSummary;
|
|
@@ -1,7 +0,0 @@
|
|
|
1
|
-
import type { MemoryClaimRecord, MemoryConflictRecord, MemoryProposalRecord, MemoryRecord } from "./local-store-records.js";
|
|
2
|
-
export declare function rowToRecord(row: unknown): MemoryRecord;
|
|
3
|
-
export declare function rowToClaimRecord(row: unknown): MemoryClaimRecord;
|
|
4
|
-
export declare function rowToProposalRecord(row: unknown): MemoryProposalRecord;
|
|
5
|
-
export declare function rowToConflictRecord(row: unknown): MemoryConflictRecord;
|
|
6
|
-
export declare function parseJsonObject(raw: unknown): Record<string, unknown>;
|
|
7
|
-
export declare function parseJsonArray(raw: unknown): string[];
|
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
import type { SqliteDatabase } from "./local-store-records.js";
|
|
2
|
-
export declare const MEMORY_SCHEMA_SQL = "\nCREATE TABLE IF NOT EXISTS memories (\n id TEXT PRIMARY KEY,\n text TEXT NOT NULL,\n user_id TEXT NOT NULL,\n category TEXT NOT NULL DEFAULT 'general',\n importance REAL NOT NULL DEFAULT 0.5,\n confidence REAL NOT NULL DEFAULT 1.0,\n source TEXT NOT NULL DEFAULT 'agent',\n session_id TEXT NOT NULL DEFAULT '',\n event_date TEXT NOT NULL DEFAULT '',\n tags TEXT NOT NULL DEFAULT '[]',\n embedding BLOB,\n created_at INTEGER NOT NULL,\n updated_at INTEGER NOT NULL,\n access_count INTEGER NOT NULL DEFAULT 0,\n last_accessed_at INTEGER NOT NULL DEFAULT 0,\n is_archived INTEGER NOT NULL DEFAULT 0,\n text_seg TEXT NOT NULL DEFAULT '',\n embedding_model TEXT NOT NULL DEFAULT '',\n embedding_dims INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE INDEX IF NOT EXISTS idx_memories_user ON memories(user_id);\nCREATE INDEX IF NOT EXISTS idx_memories_user_category ON memories(user_id, category);\nCREATE INDEX IF NOT EXISTS idx_memories_user_importance ON memories(user_id, importance DESC);\nCREATE INDEX IF NOT EXISTS idx_memories_created ON memories(created_at DESC);\n\nCREATE TABLE IF NOT EXISTS memory_observations (\n id TEXT PRIMARY KEY,\n user_id TEXT NOT NULL,\n text TEXT NOT NULL,\n source TEXT NOT NULL,\n source_priority INTEGER NOT NULL DEFAULT 0,\n session_id TEXT NOT NULL DEFAULT '',\n evidence_type TEXT NOT NULL DEFAULT 'text',\n payload TEXT NOT NULL DEFAULT '{}',\n created_at INTEGER NOT NULL\n);\n\nCREATE INDEX IF NOT EXISTS idx_memory_observations_user_created ON memory_observations(user_id, created_at DESC);\nCREATE INDEX IF NOT EXISTS idx_memory_observations_source ON memory_observations(user_id, source);\n\nCREATE TABLE IF NOT EXISTS memory_proposals (\n id TEXT PRIMARY KEY,\n user_id TEXT NOT NULL,\n observation_ids TEXT NOT NULL DEFAULT '[]',\n text TEXT NOT NULL,\n category TEXT NOT NULL DEFAULT 'general',\n importance REAL NOT NULL DEFAULT 0.5,\n confidence REAL NOT NULL DEFAULT 0.5,\n source TEXT NOT NULL DEFAULT 'agent',\n source_priority INTEGER NOT NULL DEFAULT 0,\n entity TEXT NOT NULL DEFAULT '',\n predicate TEXT NOT NULL DEFAULT '',\n value_json TEXT NOT NULL DEFAULT '{}',\n valid_time TEXT NOT NULL DEFAULT '',\n tags TEXT NOT NULL DEFAULT '[]',\n status TEXT NOT NULL DEFAULT 'pending',\n related_claim_ids TEXT NOT NULL DEFAULT '[]',\n idempotency_key TEXT,\n created_at INTEGER NOT NULL,\n updated_at INTEGER NOT NULL\n);\n\nCREATE INDEX IF NOT EXISTS idx_memory_proposals_user_status ON memory_proposals(user_id, status);\nCREATE INDEX IF NOT EXISTS idx_memory_proposals_fact ON memory_proposals(user_id, entity, predicate, valid_time);\n\nCREATE TABLE IF NOT EXISTS memory_claims (\n id TEXT PRIMARY KEY,\n memory_id TEXT NOT NULL DEFAULT '',\n user_id TEXT NOT NULL,\n entity TEXT NOT NULL DEFAULT '',\n predicate TEXT NOT NULL DEFAULT '',\n value_json TEXT NOT NULL DEFAULT '{}',\n text TEXT NOT NULL,\n category TEXT NOT NULL DEFAULT 'general',\n importance REAL NOT NULL DEFAULT 0.5,\n confidence REAL NOT NULL DEFAULT 0.5,\n source TEXT NOT NULL DEFAULT 'agent',\n source_priority INTEGER NOT NULL DEFAULT 0,\n status TEXT NOT NULL DEFAULT 'active',\n valid_time TEXT NOT NULL DEFAULT '',\n evidence_ids TEXT NOT NULL DEFAULT '[]',\n supersedes_claim_id TEXT NOT NULL DEFAULT '',\n conflict_group_id TEXT NOT NULL DEFAULT '',\n created_at INTEGER NOT NULL,\n updated_at INTEGER NOT NULL\n);\n\nCREATE INDEX IF NOT EXISTS idx_memory_claims_user_status ON memory_claims(user_id, status);\nCREATE INDEX IF NOT EXISTS idx_memory_claims_memory ON memory_claims(memory_id);\nCREATE INDEX IF NOT EXISTS idx_memory_claims_fact ON memory_claims(user_id, entity, predicate, valid_time);\n\nCREATE TABLE IF NOT EXISTS memory_conflicts (\n id TEXT PRIMARY KEY,\n user_id TEXT NOT NULL,\n claim_a_id TEXT NOT NULL,\n claim_b_id TEXT NOT NULL,\n reason TEXT NOT NULL,\n status TEXT NOT NULL DEFAULT 'open',\n created_at INTEGER NOT NULL,\n updated_at INTEGER NOT NULL\n);\n\nCREATE INDEX IF NOT EXISTS idx_memory_conflicts_user_status ON memory_conflicts(user_id, status);\n\nCREATE TABLE IF NOT EXISTS memory_attachments (\n id TEXT PRIMARY KEY,\n memory_id TEXT NOT NULL DEFAULT '',\n user_id TEXT NOT NULL,\n kind TEXT NOT NULL DEFAULT 'file',\n filename TEXT NOT NULL DEFAULT '',\n mime_type TEXT NOT NULL DEFAULT '',\n size INTEGER NOT NULL DEFAULT 0,\n rel_path TEXT NOT NULL,\n extracted_text TEXT NOT NULL DEFAULT '',\n created_at INTEGER NOT NULL\n);\n\nCREATE INDEX IF NOT EXISTS idx_memory_attachments_memory ON memory_attachments(memory_id);\nCREATE INDEX IF NOT EXISTS idx_memory_attachments_orphan ON memory_attachments(user_id, memory_id, created_at);\n\n";
|
|
3
|
-
/**
|
|
4
|
-
* FTS index + sync triggers, kept as a separate DDL block because the CJK
|
|
5
|
-
* migration below must DROP and re-create exactly this set — a second copy
|
|
6
|
-
* would drift. The index covers the pre-segmented shadow column `text_seg`
|
|
7
|
-
* (see fts-segment.ts), NOT raw `text`: unicode61 cannot segment CJK, so raw
|
|
8
|
-
* Chinese text is unsearchable by keyword.
|
|
9
|
-
*/
|
|
10
|
-
export declare const MEMORY_FTS_SCHEMA_SQL = "\nCREATE VIRTUAL TABLE IF NOT EXISTS memories_fts USING fts5(\n id UNINDEXED,\n user_id UNINDEXED,\n text_seg,\n category,\n tags,\n content=memories,\n content_rowid=rowid,\n tokenize='unicode61 remove_diacritics 2'\n);\n\nCREATE TRIGGER IF NOT EXISTS memories_ai AFTER INSERT ON memories BEGIN\n INSERT INTO memories_fts(rowid, id, user_id, text_seg, category, tags)\n VALUES (new.rowid, new.id, new.user_id, new.text_seg, new.category, new.tags);\nEND;\n\nCREATE TRIGGER IF NOT EXISTS memories_ad AFTER DELETE ON memories BEGIN\n INSERT INTO memories_fts(memories_fts, rowid, id, user_id, text_seg, category, tags)\n VALUES ('delete', old.rowid, old.id, old.user_id, old.text_seg, old.category, old.tags);\nEND;\n\nCREATE TRIGGER IF NOT EXISTS memories_au AFTER UPDATE ON memories BEGIN\n INSERT INTO memories_fts(memories_fts, rowid, id, user_id, text_seg, category, tags)\n VALUES ('delete', old.rowid, old.id, old.user_id, old.text_seg, old.category, old.tags);\n INSERT INTO memories_fts(rowid, id, user_id, text_seg, category, tags)\n VALUES (new.rowid, new.id, new.user_id, new.text_seg, new.category, new.tags);\nEND;\n";
|
|
11
|
-
export declare function initializeMemorySchema(db: SqliteDatabase): void;
|