@pyxmate/memory 1.2.0 → 1.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/agent-contract.d.ts +1 -1
- package/dist/agent-contract.mjs +1 -1
- package/dist/{chunk-3SDKJ5TB.mjs → chunk-BS6K64SA.mjs} +140 -4
- package/dist/{chunk-XHEVB23R.mjs → chunk-ML6VKYAL.mjs} +3 -2
- package/dist/{chunk-3PBLTOBR.mjs → chunk-MZF55IUR.mjs} +1 -1
- package/dist/cli/pyx-mem.mjs +221 -810
- package/dist/dashboard.mjs +2 -3
- package/dist/index.mjs +4 -6
- package/dist/react.mjs +2 -3
- package/package.json +1 -1
- package/dist/chunk-X6AYWXW7.mjs +0 -143
package/dist/agent-contract.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
declare const PYX_MEMORY_INSTRUCTIONS = "Use pyx-memory
|
|
1
|
+
declare const PYX_MEMORY_INSTRUCTIONS = "Use pyx-memory for durable memory across sessions, proactively \u2014 do not wait to be told. SEARCH before assuming: at the start of a task, and before proposing an approach or re-deriving a past decision, search memory for the project and topic; resolve relative times (\"last year\", \"\uB450 \uB2EC \uC804\") to an absolute ISO-8601 anchorTime so results rank by proximity to that time. STORE once a fact is settled: corrections, bug fixes (root cause + fix), design/architecture decisions (with reasoning), integration/API/auth/endpoint details, gotchas, explicit preferences, and \"remember this\" requests \u2014 concise facts not deliberation, each with topic and project. Pass eventTime (ISO-8601, when the fact took effect) for anything that can change or go stale; recency ordering, \"as of\" queries, and stale-vs-current resolution all key off it. After a memory informs your work, call reinforce so it stays in the quick/medium tiers (idle never revives it). When the user corrects you, call record_correction; before a task, call fetch_applicable_corrections (pyx never auto-applies them). When content names people, organizations, tools, places, events, or key concepts, pass entities and relationships \u2014 you build the graph, the server does not extract it; a multi-entity store with no connecting edge is refused. Match search effort to need: quick (default, strongest) for routine recall, deep for full/archived history; use lineage to trace how a fact changed. userId/teamId/agentId and callerAccessLevel are attribution filters and sensitivity redaction, not a security isolation boundary \u2014 for tenant/namespace/ReBAC detail see the installed Persistent Memory rule.";
|
|
2
2
|
declare const PERSISTENT_MEMORY_SECTION: string;
|
|
3
3
|
declare function buildDesignGuide({ appName }: {
|
|
4
4
|
appName: string;
|
package/dist/agent-contract.mjs
CHANGED
|
@@ -1,7 +1,129 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
1
|
+
// ../shared/src/constants/defaults.ts
|
|
2
|
+
var DEFAULTS = {
|
|
3
|
+
DATA_DIR: "./data",
|
|
4
|
+
VECTOR_PROVIDER: "lancedb",
|
|
5
|
+
MEMORY_SERVER_PORT: 7822
|
|
6
|
+
};
|
|
7
|
+
|
|
8
|
+
// ../shared/src/graph/extraction.ts
|
|
9
|
+
function normalizeGraphLabel(value, fallback) {
|
|
10
|
+
const normalized = value.trim().toUpperCase().replace(/[^A-Z0-9]+/g, "_").replace(/^_+|_+$/g, "");
|
|
11
|
+
return normalized.length > 0 ? normalized : fallback;
|
|
12
|
+
}
|
|
13
|
+
function normalizeNameKey(name) {
|
|
14
|
+
return name.trim().toLowerCase().replace(/\s+/g, " ");
|
|
15
|
+
}
|
|
16
|
+
function relationshipKey(relationship) {
|
|
17
|
+
return [
|
|
18
|
+
relationship.source.trim().toLowerCase(),
|
|
19
|
+
relationship.target.trim().toLowerCase(),
|
|
20
|
+
normalizeGraphLabel(relationship.type, "RELATED_TO")
|
|
21
|
+
].join("\0");
|
|
22
|
+
}
|
|
23
|
+
function mergeExtractedEntities(callerEntities, callerRelationships, extracted) {
|
|
24
|
+
const entities = [...callerEntities ?? []];
|
|
25
|
+
const relationships = [...callerRelationships ?? []];
|
|
26
|
+
const nameByLowercase = /* @__PURE__ */ new Map();
|
|
27
|
+
for (const entity of entities) {
|
|
28
|
+
const key = entity.name.toLowerCase();
|
|
29
|
+
if (!nameByLowercase.has(key)) nameByLowercase.set(key, entity.name);
|
|
30
|
+
}
|
|
31
|
+
for (const entity of extracted.entities) {
|
|
32
|
+
const key = entity.name.toLowerCase();
|
|
33
|
+
if (nameByLowercase.has(key)) continue;
|
|
34
|
+
entities.push({ ...entity, type: normalizeGraphLabel(entity.type, "CONCEPT") });
|
|
35
|
+
nameByLowercase.set(key, entity.name);
|
|
36
|
+
}
|
|
37
|
+
for (const relationship of extracted.relations) {
|
|
38
|
+
const source = nameByLowercase.get(relationship.source.toLowerCase());
|
|
39
|
+
const target = nameByLowercase.get(relationship.target.toLowerCase());
|
|
40
|
+
if (source && target) {
|
|
41
|
+
relationships.push({
|
|
42
|
+
...relationship,
|
|
43
|
+
source,
|
|
44
|
+
target,
|
|
45
|
+
type: normalizeGraphLabel(relationship.type, "RELATED_TO")
|
|
46
|
+
});
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
const seenRelationships = /* @__PURE__ */ new Set();
|
|
50
|
+
const dedupedRelationships = [];
|
|
51
|
+
for (const relationship of relationships) {
|
|
52
|
+
const key = relationshipKey(relationship);
|
|
53
|
+
if (seenRelationships.has(key)) continue;
|
|
54
|
+
seenRelationships.add(key);
|
|
55
|
+
dedupedRelationships.push(relationship);
|
|
56
|
+
}
|
|
57
|
+
return { entities, relationships: dedupedRelationships };
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
// ../shared/src/types/isolation.ts
|
|
61
|
+
var NamespaceIsolation = {
|
|
62
|
+
SHARED: "shared",
|
|
63
|
+
STRICT: "strict"
|
|
64
|
+
};
|
|
65
|
+
|
|
66
|
+
// ../shared/src/types/memory.ts
|
|
67
|
+
var MemoryType = {
|
|
68
|
+
SHORT_TERM: "short-term",
|
|
69
|
+
LONG_TERM: "long-term",
|
|
70
|
+
WORKING: "working",
|
|
71
|
+
EPISODIC: "episodic",
|
|
72
|
+
SUMMARY: "summary"
|
|
73
|
+
};
|
|
74
|
+
var SensitivityLevel = {
|
|
75
|
+
PUBLIC: "public",
|
|
76
|
+
INTERNAL: "internal",
|
|
77
|
+
SECRET: "secret"
|
|
78
|
+
};
|
|
79
|
+
var RAGStrategy = {
|
|
80
|
+
NAIVE: "naive",
|
|
81
|
+
GRAPH: "graph",
|
|
82
|
+
HYBRID: "hybrid"
|
|
83
|
+
};
|
|
84
|
+
var DEPRECATED_RAG_STRATEGIES = /* @__PURE__ */ new Map([
|
|
85
|
+
["agentic", "strategy.deprecated:agentic \u2014 removed in v0.26, use hybrid"]
|
|
86
|
+
]);
|
|
87
|
+
var VectorProvider = {
|
|
88
|
+
LANCEDB: "lancedb"
|
|
89
|
+
};
|
|
90
|
+
var EmbeddingProviderName = {
|
|
91
|
+
STUB: "stub",
|
|
92
|
+
/** @deprecated Vestigial — pyx-memory uses internal EmbeddingGemma embeddings. */
|
|
93
|
+
ANTHROPIC: "anthropic",
|
|
94
|
+
/** @deprecated Vestigial — pyx-memory uses internal EmbeddingGemma embeddings. */
|
|
95
|
+
OPENAI: "openai",
|
|
96
|
+
/** In-process ONNX model (default: EmbeddingGemma-300M). */
|
|
97
|
+
LOCAL: "local",
|
|
98
|
+
/** Remote OpenAI-compatible embedding service (pyx-cloud shared, custom, etc.). */
|
|
99
|
+
HTTP: "http"
|
|
100
|
+
};
|
|
101
|
+
var StoreTarget = {
|
|
102
|
+
SQLITE: "sqlite",
|
|
103
|
+
VECTOR: "vector",
|
|
104
|
+
GRAPH: "graph"
|
|
105
|
+
};
|
|
106
|
+
|
|
107
|
+
// ../shared/src/types/move.ts
|
|
108
|
+
var MoveFailureReason = {
|
|
109
|
+
/** Entry not found in the caller's tenant. */
|
|
110
|
+
NOT_FOUND: "not_found",
|
|
111
|
+
/** Move would cross tenant boundary (always forbidden). */
|
|
112
|
+
CROSS_TENANT_FORBIDDEN: "cross_tenant_forbidden",
|
|
113
|
+
/** Target namespace ID does not exist in the caller's tenant. */
|
|
114
|
+
TARGET_NAMESPACE_NOT_FOUND: "target_namespace_not_found",
|
|
115
|
+
/** SQLite metadata update failed; no compensation needed. */
|
|
116
|
+
SQLITE_UPDATE_FAILED: "sqlite_update_failed",
|
|
117
|
+
/** Vector store metadata update failed; SQLite reverted. */
|
|
118
|
+
VECTOR_UPDATE_FAILED: "vector_update_failed",
|
|
119
|
+
/** Graph edge namespace update failed; SQLite + vector reverted. */
|
|
120
|
+
GRAPH_UPDATE_FAILED: "graph_update_failed",
|
|
121
|
+
/** Compensation itself failed — manual intervention required. */
|
|
122
|
+
COMPENSATION_FAILED: "compensation_failed"
|
|
123
|
+
};
|
|
124
|
+
|
|
125
|
+
// ../shared/src/types/principal.ts
|
|
126
|
+
var SINGLE_TENANT_ID = "_single";
|
|
5
127
|
|
|
6
128
|
// ../client/src/disabled-memory.ts
|
|
7
129
|
var DEFAULT_PAGE_LIMIT = 20;
|
|
@@ -850,6 +972,20 @@ var MemoryClient = class {
|
|
|
850
972
|
};
|
|
851
973
|
|
|
852
974
|
export {
|
|
975
|
+
DEFAULTS,
|
|
976
|
+
normalizeGraphLabel,
|
|
977
|
+
normalizeNameKey,
|
|
978
|
+
mergeExtractedEntities,
|
|
979
|
+
NamespaceIsolation,
|
|
980
|
+
MemoryType,
|
|
981
|
+
SensitivityLevel,
|
|
982
|
+
RAGStrategy,
|
|
983
|
+
DEPRECATED_RAG_STRATEGIES,
|
|
984
|
+
VectorProvider,
|
|
985
|
+
EmbeddingProviderName,
|
|
986
|
+
StoreTarget,
|
|
987
|
+
MoveFailureReason,
|
|
988
|
+
SINGLE_TENANT_ID,
|
|
853
989
|
DisabledMemory,
|
|
854
990
|
MemoryServerError,
|
|
855
991
|
MemoryClient
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
// src/contract/index.ts
|
|
2
|
-
var PYX_MEMORY_INSTRUCTIONS = `Use pyx-memory
|
|
2
|
+
var PYX_MEMORY_INSTRUCTIONS = `Use pyx-memory for durable memory across sessions, proactively \u2014 do not wait to be told. SEARCH before assuming: at the start of a task, and before proposing an approach or re-deriving a past decision, search memory for the project and topic; resolve relative times ("last year", "\uB450 \uB2EC \uC804") to an absolute ISO-8601 anchorTime so results rank by proximity to that time. STORE once a fact is settled: corrections, bug fixes (root cause + fix), design/architecture decisions (with reasoning), integration/API/auth/endpoint details, gotchas, explicit preferences, and "remember this" requests \u2014 concise facts not deliberation, each with topic and project. Pass eventTime (ISO-8601, when the fact took effect) for anything that can change or go stale; recency ordering, "as of" queries, and stale-vs-current resolution all key off it. After a memory informs your work, call reinforce so it stays in the quick/medium tiers (idle never revives it). When the user corrects you, call record_correction; before a task, call fetch_applicable_corrections (pyx never auto-applies them). When content names people, organizations, tools, places, events, or key concepts, pass entities and relationships \u2014 you build the graph, the server does not extract it; a multi-entity store with no connecting edge is refused. Match search effort to need: quick (default, strongest) for routine recall, deep for full/archived history; use lineage to trace how a fact changed. userId/teamId/agentId and callerAccessLevel are attribution filters and sensitivity redaction, not a security isolation boundary \u2014 for tenant/namespace/ReBAC detail see the installed Persistent Memory rule.`;
|
|
3
3
|
var PERSISTENT_MEMORY_SECTION = [
|
|
4
4
|
"## Persistent Memory",
|
|
5
5
|
"",
|
|
@@ -142,7 +142,8 @@ function buildAgentSnippet() {
|
|
|
142
142
|
...targetLines,
|
|
143
143
|
"",
|
|
144
144
|
"Conflict policy:",
|
|
145
|
-
"- If
|
|
145
|
+
"- If a pyx-memory managed block (between `<!-- pyx-memory:begin \u2026 -->` and `<!-- pyx-memory:end -->`) is already present \u2014 `pyx-mem mcp install` may have written it \u2014 leave it exactly as-is and do NOT add a second copy.",
|
|
146
|
+
"- Else if an existing `Persistent Memory` section references the `pyx-memory` MCP tools, REPLACE it with the version below \u2014 this is the newer canonical rule set for the same system, not a duplicate.",
|
|
146
147
|
"- If an existing `Persistent Memory` section uses a different memory tool, append this one underneath instead. Do not delete, rewrite, or summarize the other tool's instructions.",
|
|
147
148
|
"",
|
|
148
149
|
"Install only the section below, verbatim. After writing, tell the user which file you updated.",
|