@markuplint/parser-utils 4.0.0-dev.20 → 4.0.0-dev.23
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +1 -1
- package/lib/attr-tokenizer.d.ts +16 -4
- package/lib/attr-tokenizer.js +164 -70
- package/lib/debugger.d.ts +3 -2
- package/lib/debugger.js +35 -19
- package/lib/enums.d.ts +16 -0
- package/lib/enums.js +18 -0
- package/lib/get-location.d.ts +4 -13
- package/lib/get-location.js +10 -21
- package/lib/ignore-block.d.ts +3 -2
- package/lib/ignore-block.js +62 -124
- package/lib/ignore-front-matter.d.ts +4 -1
- package/lib/ignore-front-matter.js +12 -3
- package/lib/index.d.ts +3 -16
- package/lib/index.js +3 -16
- package/lib/parser-error.d.ts +1 -0
- package/lib/parser-error.js +1 -0
- package/lib/parser.d.ts +108 -0
- package/lib/parser.js +1076 -0
- package/lib/script-parser.d.ts +1 -1
- package/lib/script-parser.js +1 -1
- package/lib/sort-nodes.d.ts +2 -0
- package/lib/sort-nodes.js +18 -0
- package/lib/types.d.ts +34 -0
- package/package.json +9 -5
- package/lib/attr-parser.d.ts +0 -25
- package/lib/attr-parser.js +0 -188
- package/lib/create-token.d.ts +0 -4
- package/lib/create-token.js +0 -29
- package/lib/flatten-nodes.d.ts +0 -2
- package/lib/flatten-nodes.js +0 -247
- package/lib/get-space-before.d.ts +0 -1
- package/lib/get-space-before.js +0 -8
- package/lib/parse-attr.d.ts +0 -24
- package/lib/parse-attr.js +0 -144
- package/lib/remove-deprecated-node.d.ts +0 -7
- package/lib/remove-deprecated-node.js +0 -39
- package/lib/siblings-correction.d.ts +0 -9
- package/lib/siblings-correction.js +0 -21
- package/lib/tag-parser.d.ts +0 -10
- package/lib/tag-parser.js +0 -152
- package/lib/tag-splitter.d.ts +0 -7
- package/lib/tag-splitter.js +0 -96
- package/lib/walker.d.ts +0 -2
- package/lib/walker.js +0 -18
package/LICENSE
CHANGED
package/lib/attr-tokenizer.d.ts
CHANGED
|
@@ -1,6 +1,18 @@
|
|
|
1
1
|
import type { QuoteSet } from './types.js';
|
|
2
|
-
import
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
2
|
+
import { AttrState } from './enums.js';
|
|
3
|
+
/**
|
|
4
|
+
* @see https://html.spec.whatwg.org/multipage/parsing.html#tag-name-state
|
|
5
|
+
* @see https://html.spec.whatwg.org/multipage/parsing.html#before-attribute-name-state
|
|
6
|
+
* @see https://html.spec.whatwg.org/multipage/parsing.html#attribute-name-state
|
|
7
|
+
*/
|
|
8
|
+
export declare function attrTokenizer(raw: string, quoteSet?: readonly QuoteSet[], startState?: AttrState, quoteInValueChars?: ReadonlyArray<QuoteSet>, endOfUnquotedValueChars?: ReadonlyArray<string>): {
|
|
9
|
+
spacesBeforeAttrName: string;
|
|
10
|
+
attrName: string;
|
|
11
|
+
spacesBeforeEqual: string;
|
|
12
|
+
equal: string;
|
|
13
|
+
spacesAfterEqual: string;
|
|
14
|
+
quoteStart: string;
|
|
15
|
+
attrValue: string;
|
|
16
|
+
quoteEnd: string;
|
|
17
|
+
leftover: string;
|
|
6
18
|
};
|
package/lib/attr-tokenizer.js
CHANGED
|
@@ -1,75 +1,169 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
const
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
1
|
+
import { defaultSpaces } from './const.js';
|
|
2
|
+
import { AttrState } from './enums.js';
|
|
3
|
+
const defaultQuoteSet = [
|
|
4
|
+
{ start: '"', end: '"' },
|
|
5
|
+
{ start: "'", end: "'" },
|
|
6
|
+
];
|
|
7
|
+
const defaultQuoteInValueChars = [];
|
|
8
|
+
const spaces = defaultSpaces;
|
|
9
|
+
const EQUAL = '=';
|
|
10
|
+
/**
|
|
11
|
+
* @see https://html.spec.whatwg.org/multipage/parsing.html#tag-name-state
|
|
12
|
+
* @see https://html.spec.whatwg.org/multipage/parsing.html#before-attribute-name-state
|
|
13
|
+
* @see https://html.spec.whatwg.org/multipage/parsing.html#attribute-name-state
|
|
14
|
+
*/
|
|
15
|
+
export function attrTokenizer(raw, quoteSet = defaultQuoteSet, startState = AttrState.BeforeName, quoteInValueChars = defaultQuoteInValueChars, endOfUnquotedValueChars = [...defaultSpaces, '/', '>']) {
|
|
16
|
+
let state = startState;
|
|
17
|
+
let spacesBeforeAttrName = '';
|
|
18
|
+
let attrName = '';
|
|
19
|
+
let spacesBeforeEqual = '';
|
|
20
|
+
let equal = '';
|
|
21
|
+
let spacesAfterEqual = '';
|
|
22
|
+
let quoteTypeIndex = -1;
|
|
23
|
+
let quoteStart = '';
|
|
24
|
+
let attrValue = '';
|
|
25
|
+
let quoteEnd = '';
|
|
26
|
+
const isBeforeValueStarted = startState === AttrState.BeforeValue;
|
|
27
|
+
const quoteModeStack = [];
|
|
28
|
+
const chars = [...raw];
|
|
29
|
+
while (chars.length > 0) {
|
|
30
|
+
if (state === AttrState.AfterValue) {
|
|
31
|
+
break;
|
|
32
|
+
}
|
|
33
|
+
const char = chars.shift();
|
|
34
|
+
switch (state) {
|
|
35
|
+
case AttrState.BeforeName: {
|
|
36
|
+
if (char === '>') {
|
|
37
|
+
chars.unshift(char);
|
|
38
|
+
state = AttrState.AfterValue;
|
|
39
|
+
break;
|
|
40
|
+
}
|
|
41
|
+
if (char === '/') {
|
|
42
|
+
chars.unshift(char);
|
|
43
|
+
state = AttrState.AfterValue;
|
|
44
|
+
break;
|
|
45
|
+
}
|
|
46
|
+
if (spaces.includes(char)) {
|
|
47
|
+
spacesBeforeAttrName += char;
|
|
48
|
+
break;
|
|
49
|
+
}
|
|
50
|
+
attrName += char;
|
|
51
|
+
state = AttrState.Name;
|
|
52
|
+
break;
|
|
53
|
+
}
|
|
54
|
+
case AttrState.Name: {
|
|
55
|
+
if (char === '>') {
|
|
56
|
+
chars.unshift(char);
|
|
57
|
+
state = AttrState.AfterValue;
|
|
58
|
+
break;
|
|
59
|
+
}
|
|
60
|
+
if (char === '/') {
|
|
61
|
+
chars.unshift(char);
|
|
62
|
+
state = AttrState.AfterValue;
|
|
63
|
+
break;
|
|
64
|
+
}
|
|
65
|
+
if (spaces.includes(char)) {
|
|
66
|
+
spacesBeforeEqual += char;
|
|
67
|
+
state = AttrState.Equal;
|
|
68
|
+
break;
|
|
69
|
+
}
|
|
70
|
+
if (char === EQUAL) {
|
|
71
|
+
equal += char;
|
|
72
|
+
state = AttrState.BeforeValue;
|
|
73
|
+
break;
|
|
74
|
+
}
|
|
75
|
+
attrName += char;
|
|
76
|
+
break;
|
|
77
|
+
}
|
|
78
|
+
case AttrState.Equal: {
|
|
79
|
+
if (spaces.includes(char)) {
|
|
80
|
+
spacesBeforeEqual += char;
|
|
81
|
+
break;
|
|
82
|
+
}
|
|
83
|
+
if (char === EQUAL) {
|
|
84
|
+
equal += char;
|
|
85
|
+
state = AttrState.BeforeValue;
|
|
86
|
+
break;
|
|
87
|
+
}
|
|
88
|
+
// End of attribute
|
|
89
|
+
chars.unshift(spacesBeforeEqual, char);
|
|
90
|
+
spacesBeforeEqual = '';
|
|
91
|
+
state = AttrState.AfterValue;
|
|
92
|
+
break;
|
|
93
|
+
}
|
|
94
|
+
case AttrState.BeforeValue: {
|
|
95
|
+
if (endOfUnquotedValueChars.includes(char) && spaces.includes(char)) {
|
|
96
|
+
if (isBeforeValueStarted) {
|
|
97
|
+
spacesBeforeAttrName += char;
|
|
98
|
+
break;
|
|
99
|
+
}
|
|
100
|
+
spacesAfterEqual += char;
|
|
101
|
+
break;
|
|
102
|
+
}
|
|
103
|
+
quoteTypeIndex = quoteSet.findIndex(quote => quote.start === char);
|
|
104
|
+
const quote = quoteSet[quoteTypeIndex];
|
|
105
|
+
if (quote) {
|
|
106
|
+
quoteStart = quote.start;
|
|
107
|
+
state = AttrState.Value;
|
|
108
|
+
break;
|
|
109
|
+
}
|
|
110
|
+
const raw = char + chars.join('');
|
|
111
|
+
const inQuote = quoteInValueChars.find(quote => raw.startsWith(quote.start));
|
|
112
|
+
if (inQuote) {
|
|
113
|
+
quoteModeStack.push(inQuote);
|
|
114
|
+
attrValue += inQuote.start;
|
|
115
|
+
chars.splice(0, inQuote.start.length - 1);
|
|
116
|
+
state = AttrState.Value;
|
|
117
|
+
break;
|
|
118
|
+
}
|
|
119
|
+
chars.unshift(char);
|
|
120
|
+
state = AttrState.Value;
|
|
121
|
+
break;
|
|
122
|
+
}
|
|
123
|
+
case AttrState.Value: {
|
|
124
|
+
if (!quoteSet[quoteTypeIndex] && endOfUnquotedValueChars.includes(char)) {
|
|
125
|
+
chars.unshift(char);
|
|
126
|
+
state = AttrState.AfterValue;
|
|
127
|
+
break;
|
|
128
|
+
}
|
|
129
|
+
if (quoteModeStack.length === 0 && char === quoteSet[quoteTypeIndex]?.end) {
|
|
130
|
+
quoteEnd = char;
|
|
131
|
+
state = AttrState.AfterValue;
|
|
132
|
+
break;
|
|
133
|
+
}
|
|
134
|
+
const raw = char + chars.join('');
|
|
135
|
+
const inQuoteEnd = quoteModeStack.at(-1);
|
|
136
|
+
if (inQuoteEnd && raw.startsWith(inQuoteEnd.end)) {
|
|
137
|
+
quoteModeStack.pop();
|
|
138
|
+
attrValue += inQuoteEnd.end;
|
|
139
|
+
chars.splice(0, inQuoteEnd.end.length - 1);
|
|
140
|
+
break;
|
|
141
|
+
}
|
|
142
|
+
const inQuoteStart = quoteInValueChars.find(quote => raw.startsWith(quote.start));
|
|
143
|
+
if (inQuoteStart) {
|
|
144
|
+
quoteModeStack.push(inQuoteStart);
|
|
145
|
+
attrValue += inQuoteStart.start;
|
|
146
|
+
chars.splice(0, inQuoteStart.start.length - 1);
|
|
147
|
+
break;
|
|
148
|
+
}
|
|
149
|
+
attrValue += char;
|
|
150
|
+
break;
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
if (state === AttrState.Value && quoteTypeIndex !== -1) {
|
|
155
|
+
throw new SyntaxError(`Unclosed attribute value: ${raw}`);
|
|
156
|
+
}
|
|
157
|
+
const leftover = chars.join('');
|
|
158
|
+
return {
|
|
159
|
+
spacesBeforeAttrName,
|
|
160
|
+
attrName,
|
|
54
161
|
spacesBeforeEqual,
|
|
55
162
|
equal,
|
|
56
163
|
spacesAfterEqual,
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
nodeName: name.raw,
|
|
62
|
-
parentNode: null,
|
|
63
|
-
prevNode: null,
|
|
64
|
-
nextNode: null,
|
|
65
|
-
isFragment: false,
|
|
66
|
-
isGhost: false,
|
|
164
|
+
quoteStart,
|
|
165
|
+
attrValue,
|
|
166
|
+
quoteEnd,
|
|
167
|
+
leftover,
|
|
67
168
|
};
|
|
68
|
-
if (parsed.leftover) {
|
|
69
|
-
return {
|
|
70
|
-
...result,
|
|
71
|
-
__leftover: parsed.leftover,
|
|
72
|
-
};
|
|
73
|
-
}
|
|
74
|
-
return result;
|
|
75
169
|
}
|
package/lib/debugger.d.ts
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
1
|
import type { MLASTAttr, MLASTNode } from '@markuplint/ml-ast';
|
|
2
|
-
export declare function nodeListToDebugMaps(nodeList: MLASTNode[], withAttr?: boolean): string[];
|
|
3
|
-
export declare function attributesToDebugMaps(attributes: MLASTAttr[]): string[][];
|
|
2
|
+
export declare function nodeListToDebugMaps(nodeList: readonly (MLASTNode | null)[], withAttr?: boolean): string[];
|
|
3
|
+
export declare function attributesToDebugMaps(attributes: readonly MLASTAttr[]): string[][];
|
|
4
|
+
export declare function nodeTreeDebugView(nodeTree: readonly MLASTNode[]): (string | undefined)[];
|
package/lib/debugger.js
CHANGED
|
@@ -1,46 +1,62 @@
|
|
|
1
|
-
export function nodeListToDebugMaps(
|
|
2
|
-
// eslint-disable-next-line @typescript-eslint/prefer-readonly-parameter-types
|
|
3
|
-
nodeList, withAttr = false) {
|
|
1
|
+
export function nodeListToDebugMaps(nodeList, withAttr = false) {
|
|
4
2
|
return nodeList.flatMap(n => {
|
|
5
3
|
const r = [];
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
else {
|
|
10
|
-
r.push(tokenDebug(n));
|
|
11
|
-
if (withAttr && 'attributes' in n) {
|
|
12
|
-
r.push(...attributesToDebugMaps(n.attributes).flat());
|
|
13
|
-
}
|
|
4
|
+
r.push(tokenDebug(n));
|
|
5
|
+
if (withAttr && n && n.type === 'starttag') {
|
|
6
|
+
r.push(...attributesToDebugMaps(n.attributes).flat());
|
|
14
7
|
}
|
|
15
8
|
return r;
|
|
16
9
|
});
|
|
17
10
|
}
|
|
18
|
-
export function attributesToDebugMaps(
|
|
19
|
-
// eslint-disable-next-line @typescript-eslint/prefer-readonly-parameter-types
|
|
20
|
-
attributes) {
|
|
11
|
+
export function attributesToDebugMaps(attributes) {
|
|
21
12
|
return attributes.map(n => {
|
|
22
13
|
const r = [
|
|
23
14
|
tokenDebug({
|
|
24
15
|
...n,
|
|
25
|
-
name: n.type === '
|
|
16
|
+
name: n.type === 'attr' ? n.name.raw : n.raw,
|
|
26
17
|
}),
|
|
27
18
|
];
|
|
28
|
-
if (n.type === '
|
|
29
|
-
r.push(`
|
|
19
|
+
if (n.type === 'spread') {
|
|
20
|
+
r.push(` #spread: ${visibleWhiteSpace(n.raw)}`);
|
|
21
|
+
return r;
|
|
30
22
|
}
|
|
23
|
+
r.push(` ${tokenDebug(n.spacesBeforeName, 'bN')}`, ` ${tokenDebug(n.name, 'name')}`, ` ${tokenDebug(n.spacesBeforeEqual, 'bE')}`, ` ${tokenDebug(n.equal, 'equal')}`, ` ${tokenDebug(n.spacesAfterEqual, 'aE')}`, ` ${tokenDebug(n.startQuote, 'sQ')}`, ` ${tokenDebug(n.value, 'value')}`, ` ${tokenDebug(n.endQuote, 'eQ')}`, ` isDirective: ${!!n.isDirective}`, ` isDynamicValue: ${!!n.isDynamicValue}`);
|
|
31
24
|
if (n.potentialName != null) {
|
|
32
25
|
r.push(` potentialName: ${visibleWhiteSpace(n.potentialName)}`);
|
|
33
26
|
}
|
|
34
|
-
if (n.
|
|
27
|
+
if (n.candidate) {
|
|
35
28
|
r.push(` candidate: ${visibleWhiteSpace(n.candidate)}`);
|
|
36
29
|
}
|
|
37
30
|
return r;
|
|
38
31
|
});
|
|
39
32
|
}
|
|
33
|
+
export function nodeTreeDebugView(nodeTree) {
|
|
34
|
+
return nodeTree
|
|
35
|
+
.map((n, i) => {
|
|
36
|
+
const lines = [];
|
|
37
|
+
if (n.type === 'attr' || n.type === 'spread') {
|
|
38
|
+
return;
|
|
39
|
+
}
|
|
40
|
+
lines.push(`${i.toString().padStart(3, '0')}: [${n.uuid.slice(0, 8)}] ${' '.repeat(Math.max(n.depth, 0))}${n.type === 'endtag' ? '/' : ''}${n.nodeName}(${n.uuid.slice(0, 8)})${n.type === 'starttag' && n.isGhost ? '[👻]' : ''}${n.type === 'starttag'
|
|
41
|
+
? ` => ${n.pairNode ? `/${n.pairNode.nodeName}(${n.pairNode.uuid.slice(0, 8)})` : '💀'}`
|
|
42
|
+
: ''}`);
|
|
43
|
+
if (n.type === 'starttag' || n.type === 'psblock') {
|
|
44
|
+
for (const c of n.childNodes ?? []) {
|
|
45
|
+
lines.push(`${' '.repeat(15)} ${' '.repeat(Math.max(n.depth, 0))}┗━ ${c.type === 'endtag' ? '/' : ''}${c.nodeName}(${c.uuid.slice(0, 8)})`);
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
return lines;
|
|
49
|
+
})
|
|
50
|
+
.filter(Boolean)
|
|
51
|
+
.flat();
|
|
52
|
+
}
|
|
40
53
|
function tokenDebug(n, type = '') {
|
|
54
|
+
if (!n) {
|
|
55
|
+
return 'NULL';
|
|
56
|
+
}
|
|
41
57
|
return `[${n.startLine}:${n.startCol}]>[${n.endLine}:${n.endCol}](${n.startOffset},${n.endOffset})${
|
|
42
58
|
// @ts-ignore
|
|
43
|
-
n.potentialName ?? n.nodeName ?? n.name ?? n.type ?? type}: ${visibleWhiteSpace(n.raw)}`;
|
|
59
|
+
n.potentialName ?? n.nodeName ?? n.name ?? n.type ?? type}${'isGhost' in n && n.isGhost ? '(👻)' : ''}${'isBogus' in n && n.isBogus ? '(👿)' : ''}: ${visibleWhiteSpace(n.raw)}`;
|
|
44
60
|
}
|
|
45
61
|
function visibleWhiteSpace(chars) {
|
|
46
62
|
return chars.replaceAll('\n', '⏎').replaceAll('\t', '→').replaceAll(/\s/g, '␣');
|
package/lib/enums.d.ts
ADDED
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
export declare enum TagState {
|
|
2
|
+
BeforeOpenTag = 0,
|
|
3
|
+
FirstCharOfTagName = 1,
|
|
4
|
+
TagName = 2,
|
|
5
|
+
Attrs = 3,
|
|
6
|
+
AfterAttrs = 4,
|
|
7
|
+
AfterOpenTag = 5
|
|
8
|
+
}
|
|
9
|
+
export declare enum AttrState {
|
|
10
|
+
BeforeName = 0,
|
|
11
|
+
Name = 1,
|
|
12
|
+
Equal = 2,
|
|
13
|
+
BeforeValue = 3,
|
|
14
|
+
Value = 4,
|
|
15
|
+
AfterValue = 5
|
|
16
|
+
}
|
package/lib/enums.js
ADDED
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
export var TagState;
|
|
2
|
+
(function (TagState) {
|
|
3
|
+
TagState[TagState["BeforeOpenTag"] = 0] = "BeforeOpenTag";
|
|
4
|
+
TagState[TagState["FirstCharOfTagName"] = 1] = "FirstCharOfTagName";
|
|
5
|
+
TagState[TagState["TagName"] = 2] = "TagName";
|
|
6
|
+
TagState[TagState["Attrs"] = 3] = "Attrs";
|
|
7
|
+
TagState[TagState["AfterAttrs"] = 4] = "AfterAttrs";
|
|
8
|
+
TagState[TagState["AfterOpenTag"] = 5] = "AfterOpenTag";
|
|
9
|
+
})(TagState || (TagState = {}));
|
|
10
|
+
export var AttrState;
|
|
11
|
+
(function (AttrState) {
|
|
12
|
+
AttrState[AttrState["BeforeName"] = 0] = "BeforeName";
|
|
13
|
+
AttrState[AttrState["Name"] = 1] = "Name";
|
|
14
|
+
AttrState[AttrState["Equal"] = 2] = "Equal";
|
|
15
|
+
AttrState[AttrState["BeforeValue"] = 3] = "BeforeValue";
|
|
16
|
+
AttrState[AttrState["Value"] = 4] = "Value";
|
|
17
|
+
AttrState[AttrState["AfterValue"] = 5] = "AfterValue";
|
|
18
|
+
})(AttrState || (AttrState = {}));
|
package/lib/get-location.d.ts
CHANGED
|
@@ -1,13 +1,4 @@
|
|
|
1
|
-
export declare function getLine(
|
|
2
|
-
export declare function getCol(
|
|
3
|
-
export declare function getEndLine(
|
|
4
|
-
export declare function getEndCol(
|
|
5
|
-
export declare function sliceFragment(rawHtml: string, start: number, end: number): {
|
|
6
|
-
startOffset: number;
|
|
7
|
-
endOffset: number;
|
|
8
|
-
startLine: number;
|
|
9
|
-
endLine: number;
|
|
10
|
-
startCol: number;
|
|
11
|
-
endCol: number;
|
|
12
|
-
raw: string;
|
|
13
|
-
};
|
|
1
|
+
export declare function getLine(rawCodeFragment: string, startOffset: number): number;
|
|
2
|
+
export declare function getCol(rawCodeFragment: string, startOffset: number): number;
|
|
3
|
+
export declare function getEndLine(rawCodeFragment: string, startLine: number): number;
|
|
4
|
+
export declare function getEndCol(rawCodeFragment: string, startCol: number): number;
|
package/lib/get-location.js
CHANGED
|
@@ -1,28 +1,17 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
1
|
+
const LINE_BREAK = '\n';
|
|
2
|
+
export function getLine(rawCodeFragment, startOffset) {
|
|
3
|
+
return rawCodeFragment.slice(0, startOffset).split(LINE_BREAK).length;
|
|
3
4
|
}
|
|
4
|
-
export function getCol(
|
|
5
|
-
const lines =
|
|
5
|
+
export function getCol(rawCodeFragment, startOffset) {
|
|
6
|
+
const lines = rawCodeFragment.slice(0, startOffset).split(LINE_BREAK);
|
|
6
7
|
return (lines.at(-1) ?? '').length + 1;
|
|
7
8
|
}
|
|
8
|
-
export function getEndLine(
|
|
9
|
-
return
|
|
9
|
+
export function getEndLine(rawCodeFragment, startLine) {
|
|
10
|
+
return rawCodeFragment.split(LINE_BREAK).length - 1 + startLine;
|
|
10
11
|
}
|
|
11
|
-
export function getEndCol(
|
|
12
|
-
const lines =
|
|
12
|
+
export function getEndCol(rawCodeFragment, startCol) {
|
|
13
|
+
const lines = rawCodeFragment.split(LINE_BREAK);
|
|
13
14
|
const lineCount = lines.length;
|
|
14
15
|
const lastLine = lines.pop();
|
|
15
|
-
return lineCount > 1 ? lastLine.length + 1 :
|
|
16
|
-
}
|
|
17
|
-
export function sliceFragment(rawHtml, start, end) {
|
|
18
|
-
const raw = rawHtml.slice(start, end);
|
|
19
|
-
return {
|
|
20
|
-
startOffset: start,
|
|
21
|
-
endOffset: end,
|
|
22
|
-
startLine: getLine(rawHtml, start),
|
|
23
|
-
endLine: getLine(rawHtml, end),
|
|
24
|
-
startCol: getCol(rawHtml, start),
|
|
25
|
-
endCol: getCol(rawHtml, end),
|
|
26
|
-
raw,
|
|
27
|
-
};
|
|
16
|
+
return lineCount > 1 ? lastLine.length + 1 : startCol + rawCodeFragment.length;
|
|
28
17
|
}
|
package/lib/ignore-block.d.ts
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
|
+
import type { Parser } from './parser.js';
|
|
1
2
|
import type { IgnoreBlock, IgnoreTag } from './types.js';
|
|
2
|
-
import type {
|
|
3
|
+
import type { MLASTNodeTreeItem } from '@markuplint/ml-ast';
|
|
3
4
|
export declare function ignoreBlock(source: string, tags: readonly IgnoreTag[], maskChar?: string): IgnoreBlock;
|
|
4
|
-
export declare function restoreNode(nodeList:
|
|
5
|
+
export declare function restoreNode(parser: Parser<any, any>, nodeList: readonly MLASTNodeTreeItem[], ignoreBlock: IgnoreBlock, throwErrorWhenTagHasUnresolved?: boolean): MLASTNodeTreeItem[];
|