• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1import { html, type TreeAdapterTypeMap, type TreeAdapter } from 'parse5';
2
3function createFragmentContext<T extends TreeAdapterTypeMap>(
4    tagName: string | undefined,
5    treeAdapter: TreeAdapter<T>
6): T['element'] | null {
7    if (!tagName) {
8        return null;
9    }
10
11    let namespace = html.NS.HTML;
12    const parts = tagName.split(' ');
13
14    if (parts.length > 1) {
15        tagName = parts[1];
16
17        if (parts[0] === 'svg') {
18            namespace = html.NS.SVG;
19        } else if (parts[0] === 'math') {
20            namespace = html.NS.MATHML;
21        }
22    }
23
24    return treeAdapter.createElement(tagName, namespace, []);
25}
26
27export interface DatFile<T extends TreeAdapterTypeMap> {
28    input: string;
29    expected: string;
30    expectedErrors: string[];
31    disableEntitiesDecoding: boolean;
32    lineNum: number;
33    scriptingEnabled: boolean;
34    fragmentContext: T['element'] | null;
35}
36
37export function parseDatFile<T extends TreeAdapterTypeMap>(testSet: string, treeAdapter: TreeAdapter<T>): DatFile<T>[] {
38    const testDescrs: Record<string, number | string[]>[] = [];
39    let curDirective = '';
40    let curDescr: Record<string, number | string[]> = {};
41
42    for (const [idx, line] of testSet.split(/\r?\n/).entries()) {
43        if (line === '#data') {
44            curDescr = { '#line': idx + 1 };
45            testDescrs.push(curDescr);
46        }
47
48        if (line[0] === '#') {
49            curDirective = line;
50            curDescr[curDirective] = [];
51        } else {
52            (curDescr[curDirective] as string[]).push(line);
53        }
54    }
55
56    return testDescrs.map((descr) => {
57        const fragmentContextTagName = (descr['#document-fragment'] as string[] | undefined)?.[0];
58
59        return {
60            input: (descr['#data'] as string[]).join('\n'),
61            expected: (descr['#document'] as string[]).join('\n'),
62            expectedErrors: descr['#new-errors'] || [],
63            disableEntitiesDecoding: !!descr['#disable-html-entities-decoding'],
64            lineNum: descr['#line'],
65            scriptingEnabled: !descr['#script-off'],
66            fragmentContext: createFragmentContext<T>(fragmentContextTagName, treeAdapter),
67        } as DatFile<T>;
68    });
69}
70