mirror of
https://github.com/Youzini-afk/ST-Bionic-Memory-Ecology.git
synced 2026-06-13 18:31:16 +08:00
feat(vector): send vector space metadata to Authority apply
This commit is contained in:
@@ -33,6 +33,7 @@ const {
|
||||
isAuthorityVectorConfig,
|
||||
normalizeAuthorityVectorConfig,
|
||||
queryAuthorityTriviumNeighbors,
|
||||
applyAuthorityBmeVectorManifest,
|
||||
} = await import("../vector/authority-vector-primary-adapter.js");
|
||||
const {
|
||||
findSimilarNodesByText: findSimilarNodesByTextFromIndex,
|
||||
@@ -244,10 +245,36 @@ assert.equal(isAuthorityVectorConfig(config), true);
|
||||
const applyCall = triviumClient.calls.find(([name]) => name === "bmeVectorApply")?.[1];
|
||||
assert.equal(applyCall.items.length, 2);
|
||||
assert.equal(applyCall.links.length, 1);
|
||||
assert.equal(applyCall.observedDim, 2);
|
||||
assert.equal(String(applyCall.vectorSpaceId || "").startsWith("vs_"), true);
|
||||
assert.equal(applyCall.items.every((item) => item.payload?.vectorSpaceId === applyCall.vectorSpaceId), true);
|
||||
assert.equal(applyCall.items.every((item) => item.payload?.observedDim === 2), true);
|
||||
assert.equal(applyCall.items.every((item) => Array.isArray(item.vector) && item.vector.length > 0), true);
|
||||
assert.equal(result.timings.authorityDiagnostics.upsert.operation, "bmeVectorApply");
|
||||
}
|
||||
|
||||
{
|
||||
const { graph } = createAuthorityVectorGraph();
|
||||
const triviumClient = createMockTriviumClient();
|
||||
const entries = [
|
||||
{ nodeId: "node-a", text: "a", hash: "hash-a", index: 0 },
|
||||
{ nodeId: "node-b", text: "b", hash: "hash-b", index: 1 },
|
||||
];
|
||||
graph.nodes[0].embedding = [1, 0, 0];
|
||||
graph.nodes[1].embedding = [1, 0];
|
||||
await assert.rejects(
|
||||
() => applyAuthorityBmeVectorManifest(graph, { ...config, bmeVectorApplyReady: true }, entries, {
|
||||
namespace: "st-bme::chat-authority-vector",
|
||||
collectionId: "st-bme::chat-authority-vector",
|
||||
chatId: "chat-authority-vector",
|
||||
modelScope: "scope",
|
||||
triviumClient,
|
||||
}),
|
||||
/single vector dimension/,
|
||||
);
|
||||
assert.equal(triviumClient.calls.some(([name]) => name === "bmeVectorApply"), false);
|
||||
}
|
||||
|
||||
{
|
||||
const { graph } = createAuthorityVectorGraph();
|
||||
const triviumClient = createMockTriviumClient({ failBmeVectorApply: true });
|
||||
|
||||
@@ -5,6 +5,7 @@ import {
|
||||
AuthorityHttpError,
|
||||
} from "../runtime/authority-http-client.js";
|
||||
import { embedBatch } from "./embedding.js";
|
||||
import { deriveVectorSpace } from "./vector-space.js";
|
||||
|
||||
export const AUTHORITY_VECTOR_MODE = "authority";
|
||||
export const AUTHORITY_VECTOR_SOURCE = "authority-trivium";
|
||||
@@ -872,7 +873,7 @@ export async function upsertAuthorityTriviumEntries(graph, config = {}, entries
|
||||
}
|
||||
|
||||
export async function applyAuthorityBmeVectorManifest(graph, config = {}, entries = [], options = {}) {
|
||||
const items = buildAuthorityVectorItems(graph, entries, options);
|
||||
let items = buildAuthorityVectorItems(graph, entries, options);
|
||||
const links = buildAuthorityLinkItems(graph, options).map((link) => ({
|
||||
src: buildNodeReference(link.fromId, options.namespace),
|
||||
dst: buildNodeReference(link.toId, options.namespace),
|
||||
@@ -883,6 +884,29 @@ export async function applyAuthorityBmeVectorManifest(graph, config = {}, entrie
|
||||
if (missingVector) {
|
||||
throw new Error("BME vector apply requires vector for every item");
|
||||
}
|
||||
const observedDim = items.reduce((dim, item) => {
|
||||
const vectorDim = normalizeVector(item?.vector || item?.embedding).length;
|
||||
if (!vectorDim) return dim;
|
||||
if (!dim) return vectorDim;
|
||||
return dim === vectorDim ? dim : -1;
|
||||
}, 0);
|
||||
if (observedDim < 0) {
|
||||
const error = new Error("BME vector apply requires a single vector dimension per batch");
|
||||
error.errorCategory = "vector-dimension-mismatch";
|
||||
error.errorDomain = "embedding";
|
||||
throw error;
|
||||
}
|
||||
const vectorSpace = observedDim > 0 ? deriveVectorSpace(config, observedDim) : null;
|
||||
if (vectorSpace?.vectorSpaceId) {
|
||||
items = items.map((item) => ({
|
||||
...item,
|
||||
payload: {
|
||||
...(item.payload || {}),
|
||||
vectorSpaceId: vectorSpace.vectorSpaceId,
|
||||
observedDim: vectorSpace.observedDim,
|
||||
},
|
||||
}));
|
||||
}
|
||||
throwIfAborted(options.signal);
|
||||
const client = createAuthorityTriviumClient(config, options);
|
||||
const startedAt = nowMs();
|
||||
@@ -900,6 +924,8 @@ export async function applyAuthorityBmeVectorManifest(graph, config = {}, entrie
|
||||
graphRevision: Math.max(0, Math.floor(Number(options.revision) || 0)),
|
||||
modelScope: String(options.modelScope || ""),
|
||||
embeddingMode: config.embeddingMode || "client",
|
||||
...(vectorSpace?.vectorSpaceId ? { vectorSpaceId: vectorSpace.vectorSpaceId } : {}),
|
||||
...(observedDim > 0 ? { observedDim } : {}),
|
||||
items,
|
||||
links,
|
||||
idempotencyKey: [
|
||||
|
||||
Reference in New Issue
Block a user