evidence-anchor/src/selectors/resolve.dom.test.ts

77 lines
2.7 KiB
TypeScript
Raw Normal View History

import { describe, expect, it } from "vitest";
import type { DocumentRepresentation } from "@citation-evidence/engine/shared";
import type { DocumentId, RepresentationId } from "@citation-evidence/engine/shared";
import type { Selector } from "@citation-evidence/engine/shared";
import { resolveSelectors } from "./resolve";
const blockText = "The quick brown fox jumps over the lazy dog.";
const text = `## Section\n\n${blockText}`;
function repr(structureStart = text.indexOf(blockText)): DocumentRepresentation {
return {
id: "rep_dom" as RepresentationId,
documentId: "doc_dom" as DocumentId,
representationType: "markdown-rendered",
contentHash: "test",
canonicalText: text,
structureMap: [
{
globalStart: structureStart,
globalEnd: structureStart + blockText.length,
path: [{ kind: "section", index: 0, label: "Section" }],
containerPath: [0, 1, 0],
},
],
generatedAt: "2026-07-09T00:00:00.000Z",
};
}
describe("resolveSelectors (dom)", () => {
it("resolves DomRangeSelector via structureMap", () => {
const foxStart = text.indexOf("brown fox");
const selectors: Selector[] = [
{
type: "DomRangeSelector",
startPath: [0, 1, 0],
startOffset: foxStart - text.indexOf(blockText),
endPath: [0, 1, 0],
endOffset: foxStart - text.indexOf(blockText) + "brown fox".length,
},
];
const r = resolveSelectors(selectors, repr());
expect(r.status).toBe("resolved");
expect(r.confidence).toBe(0.75);
expect(r.candidates[0]?.textPosition?.start).toBe(foxStart);
});
it("resolves StructuralSelector when offsets shift within the block", () => {
const shifted = "The quick brown fox jumps over a sleepy dog.";
const shiftedDoc = `## Section\n\n${shifted}`;
const blockStart = shiftedDoc.indexOf(shifted);
const selectors: Selector[] = [
{
type: "StructuralSelector",
path: [{ kind: "section", index: 0, label: "Section" }],
startOffset: blockText.indexOf("brown fox"),
endOffset: blockText.indexOf("brown fox") + "brown fox".length,
},
];
const representation: DocumentRepresentation = {
...repr(blockStart),
canonicalText: shiftedDoc,
structureMap: [
{
globalStart: blockStart,
globalEnd: blockStart + shifted.length,
path: [{ kind: "section", index: 0, label: "Section" }],
},
],
};
const r = resolveSelectors(selectors, representation);
expect(r.status).toBe("resolved");
expect(r.confidence).toBe(0.65);
expect(r.candidates[0]?.textPosition?.start).toBe(
representation.canonicalText!.indexOf("brown fox"),
);
});
});