syntaxai/tdd.md · main · src / b32_anchor_extract.test.ts
import { test, expect } from "bun:test";
import { extractAnchors } from "./b32_anchor_extract.ts";
test("extracts h2 with explicit id", () => {
const html = `<h2 id="getting-started">Getting started</h2>`;
expect(extractAnchors(html)).toEqual([
{ level: 2, text: "Getting started", id: "getting-started" },
]);
});
test("extracts h3 with explicit id", () => {
const html = `<h3 id="why">Why</h3>`;
expect(extractAnchors(html)).toEqual([
{ level: 3, text: "Why", id: "why" },
]);
});
test("ignores h1 and h4+", () => {
const html = `<h1 id="t">T</h1><h2 id="a">A</h2><h4 id="b">B</h4>`;
const anchors = extractAnchors(html);
expect(anchors.map((a) => a.id)).toEqual(["a"]);
});
test("slugifies when id attribute is missing", () => {
const html = `<h2>What this number does *not* measure</h2>`;
const anchors = extractAnchors(html);
expect(anchors[0]?.id).toBe("what-this-number-does-not-measure");
});
test("strips inline tags from text and id source", () => {
const html = `<h3><code>red:</code> phase</h3>`;
const anchors = extractAnchors(html);
expect(anchors[0]?.text).toBe("red: phase");
expect(anchors[0]?.id).toBe("red-phase");
});
test("returns multiple anchors in document order", () => {
const html = `<h2 id="one">One</h2><p>x</p><h3 id="two">Two</h3><h2 id="three">Three</h2>`;
const anchors = extractAnchors(html);
expect(anchors.map((a) => `${a.level}:${a.id}`)).toEqual([
"2:one",
"3:two",
"2:three",
]);
});
test("skips empty headings", () => {
const html = `<h2 id="empty"></h2><h2 id="real">Real</h2>`;
expect(extractAnchors(html).length).toBe(1);
});
test("handles HTML entities in text", () => {
const html = `<h2>Tom & Jerry</h2>`;
const anchors = extractAnchors(html);
expect(anchors[0]?.text).toBe("Tom & Jerry");
expect(anchors[0]?.id).toBe("tom-jerry");
});