@anuma/sdk 6.40.0 → 6.42.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/expo/index.cjs +169 -83
- package/dist/expo/index.d.mts +38 -1
- package/dist/expo/index.d.ts +38 -1
- package/dist/expo/index.mjs +166 -83
- package/dist/memory/context.d.mts +2 -0
- package/dist/memory/context.d.ts +2 -0
- package/dist/react/index.cjs +131 -43
- package/dist/react/index.d.mts +38 -1
- package/dist/react/index.d.ts +38 -1
- package/dist/react/index.mjs +128 -43
- package/dist/server/index.cjs +108 -40
- package/dist/server/index.d.mts +16 -0
- package/dist/server/index.d.ts +16 -0
- package/dist/server/index.mjs +108 -40
- package/package.json +1 -1
package/dist/server/index.mjs
CHANGED
|
@@ -25703,6 +25703,10 @@ var ENTITY_KINDS = [
|
|
|
25703
25703
|
function normalizeEntityName(name) {
|
|
25704
25704
|
return name.trim().toLowerCase();
|
|
25705
25705
|
}
|
|
25706
|
+
var TOPIC_SALIENCE_WEIGHTS = { primary: 1, secondary: 0.6, mention: 0.3 };
|
|
25707
|
+
function parseTopicWeight(value) {
|
|
25708
|
+
return typeof value === "number" && value > 0 && value <= 1 ? value : void 0;
|
|
25709
|
+
}
|
|
25706
25710
|
function serializeTopics(topics) {
|
|
25707
25711
|
return JSON.stringify(topics);
|
|
25708
25712
|
}
|
|
@@ -25718,12 +25722,14 @@ function parseTopics(value) {
|
|
|
25718
25722
|
const out = [];
|
|
25719
25723
|
for (const raw of parsed) {
|
|
25720
25724
|
if (typeof raw !== "object" || raw === null) continue;
|
|
25721
|
-
const { name, kind, source } = raw;
|
|
25725
|
+
const { name, kind, source, weight } = raw;
|
|
25722
25726
|
if (typeof name !== "string" || name.trim().length === 0) continue;
|
|
25727
|
+
const parsedWeight = parseTopicWeight(weight);
|
|
25723
25728
|
out.push({
|
|
25724
25729
|
name,
|
|
25725
25730
|
...typeof kind === "string" && kind.length > 0 ? { kind } : {},
|
|
25726
|
-
source: source === "user" ? "user" : "auto"
|
|
25731
|
+
source: source === "user" ? "user" : "auto",
|
|
25732
|
+
...parsedWeight !== void 0 ? { weight: parsedWeight } : {}
|
|
25727
25733
|
});
|
|
25728
25734
|
}
|
|
25729
25735
|
return out;
|
|
@@ -25810,21 +25816,47 @@ function displayNamesOf(entities) {
|
|
|
25810
25816
|
}
|
|
25811
25817
|
function topicsEqual(stored, computed) {
|
|
25812
25818
|
if (stored === null || stored.length !== computed.length) return false;
|
|
25813
|
-
const key = (t) => JSON.stringify([t.name, t.kind ?? null, t.source]);
|
|
25819
|
+
const key = (t) => JSON.stringify([t.name, t.kind ?? null, t.source, t.weight ?? null]);
|
|
25814
25820
|
const storedKeys = stored.map(key).sort();
|
|
25815
25821
|
const computedKeys = computed.map(key).sort();
|
|
25816
25822
|
return storedKeys.every((k, i) => k === computedKeys[i]);
|
|
25817
25823
|
}
|
|
25818
|
-
function resolveTopicsWrite(row, linked,
|
|
25824
|
+
function resolveTopicsWrite(row, linked, inputs, source, mode) {
|
|
25819
25825
|
if (row === null || source === null) return null;
|
|
25820
|
-
const
|
|
25821
|
-
|
|
25826
|
+
const stored = parseTopics(row.topics);
|
|
25827
|
+
const carried = mode === "merge" ? stored : null;
|
|
25828
|
+
const weights = source === "auto" ? weightsOf(carried, inputs) : null;
|
|
25829
|
+
const displayNames = displayNamesOf([...inputs, ...carried ?? []]);
|
|
25830
|
+
const topics = topicsForEntities(linked, displayNames, source, weights);
|
|
25831
|
+
if (topicsEqual(stored, topics)) return null;
|
|
25822
25832
|
return { row, topics };
|
|
25823
25833
|
}
|
|
25824
|
-
function
|
|
25834
|
+
function weightsOf(stored, inputs) {
|
|
25835
|
+
const out = /* @__PURE__ */ new Map();
|
|
25836
|
+
for (const topic of stored ?? []) out.set(normalizeEntityName(topic.name), topic.weight);
|
|
25837
|
+
for (const input of inputs) {
|
|
25838
|
+
const weight = parseTopicWeight(input.weight);
|
|
25839
|
+
if (weight === void 0) continue;
|
|
25840
|
+
const name = normalizeEntityName(input.name);
|
|
25841
|
+
if (!out.has(name)) {
|
|
25842
|
+
out.set(name, weight);
|
|
25843
|
+
continue;
|
|
25844
|
+
}
|
|
25845
|
+
const current = out.get(name);
|
|
25846
|
+
if (current !== void 0 && weight > current) out.set(name, weight);
|
|
25847
|
+
}
|
|
25848
|
+
return out;
|
|
25849
|
+
}
|
|
25850
|
+
function topicsForEntities(entities, displayNames, source, weights) {
|
|
25825
25851
|
return entities.map((e) => {
|
|
25826
25852
|
const name = displayNames.get(e.canonicalName) ?? e.canonicalName;
|
|
25827
|
-
|
|
25853
|
+
const weight = weights?.get(e.canonicalName);
|
|
25854
|
+
return {
|
|
25855
|
+
name,
|
|
25856
|
+
...e.kind ? { kind: e.kind } : {},
|
|
25857
|
+
source,
|
|
25858
|
+
...weight !== void 0 ? { weight } : {}
|
|
25859
|
+
};
|
|
25828
25860
|
});
|
|
25829
25861
|
}
|
|
25830
25862
|
function toEntityObjects(entityInputs) {
|
|
@@ -25832,7 +25864,7 @@ function toEntityObjects(entityInputs) {
|
|
|
25832
25864
|
}
|
|
25833
25865
|
async function resolveMemoryTopicsWrite(ctx, memoryId, linked, inputs, source) {
|
|
25834
25866
|
const row = await findVaultRowInWrite(ctx, memoryId);
|
|
25835
|
-
return resolveTopicsWrite(row, linked,
|
|
25867
|
+
return resolveTopicsWrite(row, linked, toEntityObjects(inputs), source, "replace");
|
|
25836
25868
|
}
|
|
25837
25869
|
function prepareMemoryTopicsUpdate(write) {
|
|
25838
25870
|
return prepareTopicsUpdate(write.row, write.topics, Date.now());
|
|
@@ -25870,8 +25902,9 @@ async function linkMemoryEntitiesOp(ctx, memoryId, entityInputs, options) {
|
|
|
25870
25902
|
const topicsWrite = resolveTopicsWrite(
|
|
25871
25903
|
vaultRow,
|
|
25872
25904
|
[...carriedOver, ...entities],
|
|
25873
|
-
|
|
25874
|
-
options?.topicsSource ?? "auto"
|
|
25905
|
+
normalized,
|
|
25906
|
+
options?.topicsSource ?? "auto",
|
|
25907
|
+
"merge"
|
|
25875
25908
|
);
|
|
25876
25909
|
if (entityOps.length === 0 && kindBackfills.length === 0 && toCreate.length === 0 && topicsWrite === null) {
|
|
25877
25910
|
return;
|
|
@@ -25937,8 +25970,9 @@ async function replaceMemoryEntities(ctx, memoryId, entityInputs, options) {
|
|
|
25937
25970
|
const topicsWrite = resolveTopicsWrite(
|
|
25938
25971
|
vaultRow,
|
|
25939
25972
|
entities,
|
|
25940
|
-
|
|
25941
|
-
options.topicsSource
|
|
25973
|
+
normalized,
|
|
25974
|
+
options.topicsSource,
|
|
25975
|
+
"replace"
|
|
25942
25976
|
);
|
|
25943
25977
|
if (entityOps.length === 0 && kindBackfills.length === 0 && toCreate.length === 0 && toDestroy.length === 0 && topicsWrite === null) {
|
|
25944
25978
|
return;
|
|
@@ -30897,9 +30931,9 @@ For each durable fact, output:
|
|
|
30897
30931
|
- type: one of identity | preference | relationship | plan | ongoing_context | constraint | other
|
|
30898
30932
|
- confidence: 0.0-1.0; how sure you are this is durable AND true. Only include facts >= 0.7.
|
|
30899
30933
|
- sourceMessageIds: which message IDs from the conversation contained the evidence
|
|
30900
|
-
- entities: named entities mentioned, each as an object { "name": string, "kind": one of "person" | "organization" | "place" | "event" | "product" | "thing" | "concept" | "other" }. Optional \u2014 include only NAMED entities, skip generic/common nouns. ${ENTITY_KIND_GUIDELINES} Examples:
|
|
30901
|
-
- "started a new job at Hollowpoint Labs and I'm learning Haskell for it" \u2192 entities: [{ "name": "Hollowpoint Labs", "kind": "organization" }, { "name": "Haskell", "kind": "concept" }]
|
|
30902
|
-
- "running the Berlin Half in May and I track workouts in Whoop" \u2192 entities: [{ "name": "Berlin Half", "kind": "event" }, { "name": "Whoop", "kind": "product" }]
|
|
30934
|
+
- entities: named entities mentioned, each as an object { "name": string, "kind": one of "person" | "organization" | "place" | "event" | "product" | "thing" | "concept" | "other", "salience": one of "primary" | "secondary" | "mention" }. Optional \u2014 include only NAMED entities, skip generic/common nouns. ${ENTITY_KIND_GUIDELINES} Salience is how central the entity is to the fact: "primary" = the fact is ABOUT it (usually exactly one per fact), "secondary" = a meaningful part of it, "mention" = named in passing. Examples:
|
|
30935
|
+
- "started a new job at Hollowpoint Labs and I'm learning Haskell for it" \u2192 entities: [{ "name": "Hollowpoint Labs", "kind": "organization", "salience": "primary" }, { "name": "Haskell", "kind": "concept", "salience": "secondary" }]
|
|
30936
|
+
- "running the Berlin Half in May and I track workouts in Whoop" \u2192 entities: [{ "name": "Berlin Half", "kind": "event", "salience": "primary" }, { "name": "Whoop", "kind": "product", "salience": "mention" }]
|
|
30903
30937
|
- eventTime: when the event in this fact occurs/occurred. Resolve relative phrases ("yesterday", "next week") against the current date given in the user message. Output one of:
|
|
30904
30938
|
- { "kind": "point", "start": "YYYY-MM-DD" } for a single date ("met Sara on March 14, 2026")
|
|
30905
30939
|
- { "kind": "range", "start": "YYYY-MM-DD", "end": "YYYY-MM-DD" } for a span ("Japan trip May 4\u201315, 2026")
|
|
@@ -30980,9 +31014,10 @@ function restoreCandidates(candidates, redactor, ownNames) {
|
|
|
30980
31014
|
candidate: {
|
|
30981
31015
|
...c,
|
|
30982
31016
|
content: content.text,
|
|
30983
|
-
entities: c.entities.
|
|
30984
|
-
|
|
30985
|
-
|
|
31017
|
+
entities: c.entities.flatMap((e) => {
|
|
31018
|
+
const restored = redactor.restoreForStorage(e.name);
|
|
31019
|
+
return restored.unresolved ? [] : [{ ...e, name: restored.text }];
|
|
31020
|
+
})
|
|
30986
31021
|
},
|
|
30987
31022
|
unresolved: content.unresolved
|
|
30988
31023
|
};
|
|
@@ -31211,7 +31246,12 @@ function parseEntities(raw) {
|
|
|
31211
31246
|
const name = typeof obj.name === "string" ? obj.name.trim() : "";
|
|
31212
31247
|
if (name.length === 0 || isGenericEntityName(name)) continue;
|
|
31213
31248
|
const kind = typeof obj.kind === "string" && ENTITY_KINDS.includes(obj.kind) ? obj.kind : void 0;
|
|
31214
|
-
|
|
31249
|
+
const weight = typeof obj.salience === "string" && Object.keys(TOPIC_SALIENCE_WEIGHTS).includes(obj.salience) ? TOPIC_SALIENCE_WEIGHTS[obj.salience] : void 0;
|
|
31250
|
+
out.push({
|
|
31251
|
+
name,
|
|
31252
|
+
...kind !== void 0 ? { kind } : {},
|
|
31253
|
+
...weight !== void 0 ? { weight } : {}
|
|
31254
|
+
});
|
|
31215
31255
|
}
|
|
31216
31256
|
return out;
|
|
31217
31257
|
}
|
|
@@ -33170,7 +33210,13 @@ Include only NAMED entities, skip generic/common nouns. A topic must identify a
|
|
|
33170
33210
|
- Prefer 0 entities over a weak one. A memory whose only candidate is a generic noun has NO entities.
|
|
33171
33211
|
${ENTITY_KIND_GUIDELINES}
|
|
33172
33212
|
|
|
33173
|
-
|
|
33213
|
+
Give each entity a "salience" \u2014 how central it is to the memory:
|
|
33214
|
+
- "primary": the memory is ABOUT it. A memory with entities usually has exactly one primary; never more than two.
|
|
33215
|
+
- "secondary": a meaningful part of the memory, but not its subject.
|
|
33216
|
+
- "mention": named in passing; the memory would say much the same without it.
|
|
33217
|
+
Example: "Ran the Chicago Marathon with my sister Ana in 3:41" \u2192 Chicago Marathon primary, Ana secondary.
|
|
33218
|
+
|
|
33219
|
+
Each memory below is written as "<id>: <text>". Output strict JSON: {"memories": [{"id": string, "entities": [{"name": string, "kind": string, "salience": "primary" | "secondary" | "mention"}]}]}
|
|
33174
33220
|
- exactly one element per input memory; copy its id EXACTLY as written (the token before the first ": "), with no brackets, quotes, or extra characters
|
|
33175
33221
|
- "entities" may be empty when a memory mentions no named entities \u2014 most short memories have 0-3
|
|
33176
33222
|
No prose.`;
|
|
@@ -33241,9 +33287,10 @@ List each memory's named entities.`,
|
|
|
33241
33287
|
return out;
|
|
33242
33288
|
}
|
|
33243
33289
|
function restoreEntities(entities, redactor) {
|
|
33244
|
-
return entities.
|
|
33245
|
-
|
|
33246
|
-
|
|
33290
|
+
return entities.flatMap((e) => {
|
|
33291
|
+
const restored = redactor.restoreForStorage(e.name);
|
|
33292
|
+
return restored.unresolved ? [] : [{ ...e, name: restored.text }];
|
|
33293
|
+
});
|
|
33247
33294
|
}
|
|
33248
33295
|
function parseTopicResponse(parsed, validIds) {
|
|
33249
33296
|
if (typeof parsed !== "object" || parsed === null) return null;
|
|
@@ -33639,12 +33686,19 @@ var FACET_STRUCTURED_RESPONSE_HINT = {
|
|
|
33639
33686
|
interests: `, "interests": <the same interests as an array of at most ${NEARBY_MAX_INTERESTS} strings of at most ${NEARBY_MAX_INTEREST_CODEPOINTS} characters each, e.g. ["trail running", "film photography"], or []>`
|
|
33640
33687
|
};
|
|
33641
33688
|
async function synthesizeProfile(ctx, options = {}) {
|
|
33642
|
-
|
|
33643
|
-
|
|
33689
|
+
const { store } = options;
|
|
33690
|
+
const vaultCtx = ctx.vaultCtx;
|
|
33691
|
+
if (!store && !vaultCtx) {
|
|
33692
|
+
throw new Error(
|
|
33693
|
+
"synthesizeProfile requires options.store or ctx.vaultCtx (vault-backed facts)."
|
|
33694
|
+
);
|
|
33644
33695
|
}
|
|
33645
|
-
if (!ctx.vaultCache) {
|
|
33646
|
-
throw new Error(
|
|
33696
|
+
if (!store && !ctx.vaultCache) {
|
|
33697
|
+
throw new Error(
|
|
33698
|
+
"synthesizeProfile requires options.store or ctx.vaultCache (semantic fact recall)."
|
|
33699
|
+
);
|
|
33647
33700
|
}
|
|
33701
|
+
const recallCtx = store ? { embeddingOptions: ctx.embeddingOptions, factSource: store.factSource } : ctx;
|
|
33648
33702
|
const facets = options.facets ?? DEFAULT_PROFILE_FACETS;
|
|
33649
33703
|
const scopes = options.scopes ?? DEFAULT_SCOPES;
|
|
33650
33704
|
const config = {
|
|
@@ -33655,11 +33709,8 @@ async function synthesizeProfile(ctx, options = {}) {
|
|
|
33655
33709
|
reviewedMemoryIdsSignature: reviewedMemoryIdsSignature(options.reviewedMemoryIds)
|
|
33656
33710
|
};
|
|
33657
33711
|
const previous = options.previous && options.previous.version === PROFILE_DOC_VERSION && configMatches(options.previous.config, config) ? options.previous : void 0;
|
|
33658
|
-
const
|
|
33659
|
-
|
|
33660
|
-
includeDeleted: true,
|
|
33661
|
-
includeSuperseded: true
|
|
33662
|
-
});
|
|
33712
|
+
const listOptions = { scopes, includeDeleted: true, includeSuperseded: true };
|
|
33713
|
+
const [memories, projections] = store ? await Promise.all([store.list(listOptions), store.listProjections(listOptions)]) : [await getAllVaultMemoriesOp(vaultCtx, listOptions), []];
|
|
33663
33714
|
const watermark = computeVaultWatermark(memories);
|
|
33664
33715
|
const observationTrends = summarizeObservationTrends(
|
|
33665
33716
|
memories.filter((m) => !m.isDeleted && m.supersededBy === null).map((m) => ({
|
|
@@ -33669,11 +33720,14 @@ async function synthesizeProfile(ctx, options = {}) {
|
|
|
33669
33720
|
}))
|
|
33670
33721
|
);
|
|
33671
33722
|
const presentIds = new Set(memories.map((m) => m.uniqueId));
|
|
33723
|
+
const unreadableMemoryIds = projections.map((p) => p.uniqueId).filter((id) => !presentIds.has(id)).sort();
|
|
33724
|
+
const previousUnreadable = new Set(previous?.unreadableMemoryIds ?? []);
|
|
33725
|
+
const sameUnreadable = unreadableMemoryIds.length === previousUnreadable.size && unreadableMemoryIds.every((id) => previousUnreadable.has(id));
|
|
33672
33726
|
const hasStaleSections = previous?.sections.some((s) => s.stale);
|
|
33673
33727
|
const citesMissingFact = previous?.sections.some(
|
|
33674
33728
|
(s) => s.sourceMemoryIds.some((id) => !presentIds.has(id))
|
|
33675
33729
|
);
|
|
33676
|
-
if (previous && previous.vaultWatermark === watermark && !hasStaleSections && !citesMissingFact) {
|
|
33730
|
+
if (previous && previous.vaultWatermark === watermark && !hasStaleSections && !citesMissingFact && sameUnreadable) {
|
|
33677
33731
|
const sameOrder = previous.sections.length === facets.length && facets.every((f, i) => previous.sections[i]?.key === f.key);
|
|
33678
33732
|
if (sameOrder) {
|
|
33679
33733
|
if (trendsEqual(previous.observationTrends, observationTrends)) return previous;
|
|
@@ -33686,12 +33740,13 @@ async function synthesizeProfile(ctx, options = {}) {
|
|
|
33686
33740
|
};
|
|
33687
33741
|
}
|
|
33688
33742
|
const staleKeys = await computeStaleFacetKeys(
|
|
33689
|
-
|
|
33743
|
+
recallCtx,
|
|
33690
33744
|
memories,
|
|
33691
33745
|
facets,
|
|
33692
33746
|
previous,
|
|
33693
33747
|
watermark,
|
|
33694
|
-
options.reviewedMemoryIds
|
|
33748
|
+
options.reviewedMemoryIds,
|
|
33749
|
+
previousUnreadable
|
|
33695
33750
|
);
|
|
33696
33751
|
const memoriesById = new Map(memories.map((memory) => [memory.uniqueId, memory]));
|
|
33697
33752
|
const fallbackPriors = /* @__PURE__ */ new Map();
|
|
@@ -33711,7 +33766,7 @@ async function synthesizeProfile(ctx, options = {}) {
|
|
|
33711
33766
|
if (prior && !staleKeys.has(facet.key)) {
|
|
33712
33767
|
return prior;
|
|
33713
33768
|
}
|
|
33714
|
-
return synthesizeFacet(facet,
|
|
33769
|
+
return synthesizeFacet(facet, recallCtx, options, fallbackPriors.get(facet.key));
|
|
33715
33770
|
})
|
|
33716
33771
|
);
|
|
33717
33772
|
const sections = settled.map((r, i) => {
|
|
@@ -33726,12 +33781,18 @@ async function synthesizeProfile(ctx, options = {}) {
|
|
|
33726
33781
|
);
|
|
33727
33782
|
return fallbackSection(facet, fallbackPriors.get(facet.key));
|
|
33728
33783
|
});
|
|
33784
|
+
if (!sameUnreadable && unreadableMemoryIds.length > 0) {
|
|
33785
|
+
getLogger().warn("[memory/synthesizeProfile] some memories could not be read", {
|
|
33786
|
+
unreadable: unreadableMemoryIds.length
|
|
33787
|
+
});
|
|
33788
|
+
}
|
|
33729
33789
|
return {
|
|
33730
33790
|
version: PROFILE_DOC_VERSION,
|
|
33731
33791
|
sections,
|
|
33732
33792
|
vaultWatermark: watermark,
|
|
33733
33793
|
config,
|
|
33734
33794
|
observationTrends,
|
|
33795
|
+
...unreadableMemoryIds.length > 0 && { unreadableMemoryIds },
|
|
33735
33796
|
generatedAt: Date.now()
|
|
33736
33797
|
};
|
|
33737
33798
|
}
|
|
@@ -33765,11 +33826,13 @@ function computeVaultWatermark(memories) {
|
|
|
33765
33826
|
}
|
|
33766
33827
|
return max;
|
|
33767
33828
|
}
|
|
33768
|
-
async function computeStaleFacetKeys(ctx, memories, facets, previous, watermark, reviewedMemoryIds) {
|
|
33829
|
+
async function computeStaleFacetKeys(ctx, memories, facets, previous, watermark, reviewedMemoryIds, previouslyUnreadable) {
|
|
33769
33830
|
const allKeys = new Set(facets.map((f) => f.key));
|
|
33770
33831
|
if (previous && watermark < previous.vaultWatermark) return allKeys;
|
|
33771
33832
|
if (!previous) return allKeys;
|
|
33772
|
-
const changed = memories.filter(
|
|
33833
|
+
const changed = memories.filter(
|
|
33834
|
+
(m) => changeTime(m) > previous.vaultWatermark || previouslyUnreadable.has(m.uniqueId)
|
|
33835
|
+
);
|
|
33773
33836
|
const changedIds = new Set(changed.map((m) => m.uniqueId));
|
|
33774
33837
|
const presentIds = new Set(memories.map((m) => m.uniqueId));
|
|
33775
33838
|
const stale = /* @__PURE__ */ new Set();
|
|
@@ -33843,7 +33906,12 @@ async function attributeFacts(ctx, candidates, facets) {
|
|
|
33843
33906
|
for (const fv of factVectors) {
|
|
33844
33907
|
let matchedAny = false;
|
|
33845
33908
|
for (let i = 0; i < facets.length; i++) {
|
|
33846
|
-
|
|
33909
|
+
const query = queryVectors[i];
|
|
33910
|
+
const similarity = cosineSimilarity(
|
|
33911
|
+
fv,
|
|
33912
|
+
fv.length < query.length ? query.slice(0, fv.length) : query
|
|
33913
|
+
);
|
|
33914
|
+
if (similarity >= NEW_FACT_ATTRIBUTION_MIN_SCORE) {
|
|
33847
33915
|
keys.add(facets[i].key);
|
|
33848
33916
|
matchedAny = true;
|
|
33849
33917
|
}
|