


























@@ -5,11 +5,11 @@
55 * across re-parses. OcPath round-trip via the AST (slugs in OcPath
66 * must round-trip back to the resolved node).
77 */
8-import { describe, expect, it } from 'vitest';
9-import { emitMd } from '../../emit.js';
10-import { formatOcPath, parseOcPath } from '../../oc-path.js';
11-import { parseMd } from '../../parse.js';
12-import { resolveMdOcPath as resolveOcPath } from '../../resolve.js';
8+import { describe, expect, it } from "vitest";
9+import { emitMd } from "../../emit.js";
10+import { formatOcPath, parseOcPath } from "../../oc-path.js";
11+import { parseMd } from "../../parse.js";
12+import { resolveMdOcPath as resolveOcPath } from "../../resolve.js";
13131414const SAMPLE = `---
1515name: github
@@ -29,60 +29,60 @@ Preamble.
2929- curl: HTTP client
3030`;
313132-describe('wave-13 cross-cutting', () => {
33-it('CC-01 parse → resolve → emit pipeline (block)', () => {
32+describe("wave-13 cross-cutting", () => {
33+it("CC-01 parse → resolve → emit pipeline (block)", () => {
3434const { ast } = parseMd(SAMPLE);
35-const m = resolveOcPath(ast, { file: 'AGENTS.md', section: 'boundaries' });
36-expect(m?.kind).toBe('block');
35+const m = resolveOcPath(ast, { file: "AGENTS.md", section: "boundaries" });
36+expect(m?.kind).toBe("block");
3737expect(emitMd(ast)).toBe(SAMPLE);
3838});
393940-it('CC-02 OcPath round-trip via AST: parse + resolve + format', () => {
40+it("CC-02 OcPath round-trip via AST: parse + resolve + format", () => {
4141const { ast } = parseMd(SAMPLE);
4242for (const block of ast.blocks) {
4343const path = parseOcPath(`oc://AGENTS.md/${block.slug}`);
4444const m = resolveOcPath(ast, path);
45-expect(m?.kind, `block ${block.slug} should resolve`).toBe('block');
45+expect(m?.kind, `block ${block.slug} should resolve`).toBe("block");
4646// Format the same path back; slug → URI shape should be stable.
4747expect(formatOcPath(path)).toBe(`oc://AGENTS.md/${block.slug}`);
4848}
4949});
505051-it('CC-03 every item in every block is OcPath-addressable', () => {
51+it("CC-03 every item in every block is OcPath-addressable", () => {
5252const { ast } = parseMd(SAMPLE);
5353for (const block of ast.blocks) {
5454for (const item of block.items) {
5555const path = parseOcPath(`oc://AGENTS.md/${block.slug}/${item.slug}`);
5656const m = resolveOcPath(ast, path);
57-expect(m?.kind, `${block.slug}/${item.slug} should resolve`).toBe('item');
57+expect(m?.kind, `${block.slug}/${item.slug} should resolve`).toBe("item");
5858}
5959}
6060});
616162-it('CC-04 every kv item field is OcPath-addressable', () => {
62+it("CC-04 every kv item field is OcPath-addressable", () => {
6363const { ast } = parseMd(SAMPLE);
6464for (const block of ast.blocks) {
6565for (const item of block.items) {
66-if (!item.kv) {continue;}
67-const path = parseOcPath(
68- `oc://AGENTS.md/${block.slug}/${item.slug}/${item.kv.key}`,
69-);
66+if (!item.kv) {
67+ continue;
68+}
69+const path = parseOcPath(`oc://AGENTS.md/${block.slug}/${item.slug}/${item.kv.key}`);
7070const m = resolveOcPath(ast, path);
71-expect(m?.kind).toBe('item-field');
71+expect(m?.kind).toBe("item-field");
7272}
7373}
7474});
757576-it('CC-05 every frontmatter entry is OcPath-addressable', () => {
76+it("CC-05 every frontmatter entry is OcPath-addressable", () => {
7777const { ast } = parseMd(SAMPLE);
7878for (const fm of ast.frontmatter) {
7979const path = parseOcPath(`oc://AGENTS.md/[frontmatter]/${fm.key}`);
8080const m = resolveOcPath(ast, path);
81-expect(m?.kind).toBe('frontmatter');
81+expect(m?.kind).toBe("frontmatter");
8282}
8383});
848485-it('CC-06 slugs are stable across re-parses (deterministic)', () => {
85+it("CC-06 slugs are stable across re-parses (deterministic)", () => {
8686const a1 = parseMd(SAMPLE).ast;
8787const a2 = parseMd(SAMPLE).ast;
8888expect(a1.blocks.map((b) => b.slug)).toEqual(a2.blocks.map((b) => b.slug));
@@ -91,49 +91,49 @@ describe('wave-13 cross-cutting', () => {
9191);
9292});
939394-it('CC-07 modifying raw + re-parse produces consistent AST shape', () => {
94+it("CC-07 modifying raw + re-parse produces consistent AST shape", () => {
9595const a1 = parseMd(SAMPLE).ast;
96-const modified = SAMPLE.replace('GitHub CLI', 'GitHub command-line interface');
96+const modified = SAMPLE.replace("GitHub CLI", "GitHub command-line interface");
9797const a2 = parseMd(modified).ast;
9898// Block + item count + slugs unchanged.
9999expect(a2.blocks.length).toBe(a1.blocks.length);
100-const a1Tools = a1.blocks.find((b) => b.slug === 'tools');
101-const a2Tools = a2.blocks.find((b) => b.slug === 'tools');
100+const a1Tools = a1.blocks.find((b) => b.slug === "tools");
101+const a2Tools = a2.blocks.find((b) => b.slug === "tools");
102102expect(a2Tools?.items.length).toBe(a1Tools?.items.length);
103103// KV value reflects the change.
104-const ghItem = a2Tools?.items.find((i) => i.kv?.key === 'gh');
105-expect(ghItem?.kv?.value).toBe('GitHub command-line interface');
104+const ghItem = a2Tools?.items.find((i) => i.kv?.key === "gh");
105+expect(ghItem?.kv?.value).toBe("GitHub command-line interface");
106106});
107107108-it('CC-08 unknown OcPath returns null without affecting subsequent valid resolves', () => {
108+it("CC-08 unknown OcPath returns null without affecting subsequent valid resolves", () => {
109109const { ast } = parseMd(SAMPLE);
110-expect(resolveOcPath(ast, { file: 'X.md', section: 'nonexistent' })).toBeNull();
111-expect(resolveOcPath(ast, { file: 'X.md', section: 'tools' })?.kind).toBe('block');
110+expect(resolveOcPath(ast, { file: "X.md", section: "nonexistent" })).toBeNull();
111+expect(resolveOcPath(ast, { file: "X.md", section: "tools" })?.kind).toBe("block");
112112});
113113114-it('CC-09 resolve does not depend on file segment matching', () => {
114+it("CC-09 resolve does not depend on file segment matching", () => {
115115const { ast } = parseMd(SAMPLE);
116-const a = resolveOcPath(ast, { file: 'A.md', section: 'tools' });
117-const b = resolveOcPath(ast, { file: 'B.md', section: 'tools' });
116+const a = resolveOcPath(ast, { file: "A.md", section: "tools" });
117+const b = resolveOcPath(ast, { file: "B.md", section: "tools" });
118118expect(a?.kind).toBe(b?.kind);
119119});
120120121-it('CC-10 round-trip across all 9 valid OcPath shapes', () => {
121+it("CC-10 round-trip across all 9 valid OcPath shapes", () => {
122122const { ast } = parseMd(SAMPLE);
123123const cases = [
124-{ file: 'X.md' },
125-{ file: 'X.md', section: 'tools' },
126-{ file: 'X.md', section: 'tools', item: 'gh' },
127-{ file: 'X.md', section: 'tools', item: 'gh', field: 'gh' },
128-{ file: 'X.md', section: '[frontmatter]', field: 'name' },
129-{ file: 'X.md', section: 'boundaries' },
130-{ file: 'X.md', section: 'boundaries', item: 'never-write-to-etc' },
131-{ file: 'X.md', section: 'boundaries', item: 'always-confirm' },
132-{ file: 'X.md', section: '[frontmatter]', field: 'description' },
124+{ file: "X.md" },
125+{ file: "X.md", section: "tools" },
126+{ file: "X.md", section: "tools", item: "gh" },
127+{ file: "X.md", section: "tools", item: "gh", field: "gh" },
128+{ file: "X.md", section: "[frontmatter]", field: "name" },
129+{ file: "X.md", section: "boundaries" },
130+{ file: "X.md", section: "boundaries", item: "never-write-to-etc" },
131+{ file: "X.md", section: "boundaries", item: "always-confirm" },
132+{ file: "X.md", section: "[frontmatter]", field: "description" },
133133];
134134for (const path of cases) {
135135const m = resolveOcPath(ast, path);
136-expect(m, `failed for ${JSON.stringify(path)}`).not.toBeNull();
136+expect(m, `failed for ${JSON.stringify(path)}`).toEqual(expect.any(Object));
137137}
138138});
139139});
此内容由惯性聚合(RSS阅读器)自动聚合整理,仅供阅读参考。 原文来自 — 版权归原作者所有。