@markuplint/parser-utils 3.5.0 → 3.6.0
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/lib/const.d.ts +1 -1
- package/lib/create-token.d.ts +6 -1
- package/lib/create-token.js +2 -2
- package/lib/debugger.js +2 -1
- package/lib/detect-element-type.d.ts +5 -1
- package/lib/detect-element-type.js +2 -2
- package/lib/flatten-nodes.js +35 -29
- package/lib/get-location.d.ts +12 -8
- package/lib/get-space-before.d.ts +1 -0
- package/lib/get-space-before.js +13 -0
- package/lib/idl-attributes.d.ts +2 -2
- package/lib/idl-attributes.js +5 -4
- package/lib/ignore-block.js +10 -10
- package/lib/index.d.ts +2 -0
- package/lib/index.js +2 -0
- package/lib/parse-attr.d.ts +27 -0
- package/lib/parse-attr.js +150 -0
- package/lib/parser-error.d.ts +19 -11
- package/lib/remove-deprecated-node.js +1 -1
- package/lib/siblings-correction.js +3 -2
- package/lib/tag-splitter.d.ts +4 -4
- package/lib/types.d.ts +12 -12
- package/lib/walker.js +1 -1
- package/package.json +3 -3
package/lib/const.d.ts
CHANGED
package/lib/create-token.d.ts
CHANGED
|
@@ -1,4 +1,9 @@
|
|
|
1
1
|
import type { MLToken } from '@markuplint/ml-ast';
|
|
2
|
-
export declare function tokenizer(
|
|
2
|
+
export declare function tokenizer(
|
|
3
|
+
raw: string | null,
|
|
4
|
+
startLine: number,
|
|
5
|
+
startCol: number,
|
|
6
|
+
startOffset: number,
|
|
7
|
+
): MLToken;
|
|
3
8
|
export declare function createTokenFromRawCode(raw: string | null, startOffset: number, rawCode: string): MLToken;
|
|
4
9
|
export declare function uuid(): string;
|
package/lib/create-token.js
CHANGED
|
@@ -4,7 +4,7 @@ exports.uuid = exports.createTokenFromRawCode = exports.tokenizer = void 0;
|
|
|
4
4
|
const uuid_1 = require("uuid");
|
|
5
5
|
const get_location_1 = require("./get-location");
|
|
6
6
|
function tokenizer(raw, startLine, startCol, startOffset) {
|
|
7
|
-
raw = raw
|
|
7
|
+
raw = raw !== null && raw !== void 0 ? raw : '';
|
|
8
8
|
const endLine = (0, get_location_1.getEndLine)(raw, startLine);
|
|
9
9
|
const endCol = (0, get_location_1.getEndCol)(raw, startCol);
|
|
10
10
|
const endOffset = startOffset + raw.length;
|
|
@@ -21,7 +21,7 @@ function tokenizer(raw, startLine, startCol, startOffset) {
|
|
|
21
21
|
}
|
|
22
22
|
exports.tokenizer = tokenizer;
|
|
23
23
|
function createTokenFromRawCode(raw, startOffset, rawCode) {
|
|
24
|
-
raw = raw
|
|
24
|
+
raw = raw !== null && raw !== void 0 ? raw : '';
|
|
25
25
|
const loc = (0, get_location_1.sliceFragment)(rawCode, startOffset, startOffset + raw.length);
|
|
26
26
|
return {
|
|
27
27
|
uuid: uuid(),
|
package/lib/debugger.js
CHANGED
|
@@ -54,9 +54,10 @@ attributes) {
|
|
|
54
54
|
}
|
|
55
55
|
exports.attributesToDebugMaps = attributesToDebugMaps;
|
|
56
56
|
function tokenDebug(n, type = '') {
|
|
57
|
+
var _a, _b, _c, _d;
|
|
57
58
|
return `[${n.startLine}:${n.startCol}]>[${n.endLine}:${n.endCol}](${n.startOffset},${n.endOffset})${
|
|
58
59
|
// @ts-ignore
|
|
59
|
-
n.potentialName
|
|
60
|
+
(_d = (_c = (_b = (_a = n.potentialName) !== null && _a !== void 0 ? _a : n.nodeName) !== null && _b !== void 0 ? _b : n.name) !== null && _c !== void 0 ? _c : n.type) !== null && _d !== void 0 ? _d : type}: ${visibleWhiteSpace(n.raw)}`;
|
|
60
61
|
}
|
|
61
62
|
function visibleWhiteSpace(chars) {
|
|
62
63
|
return chars.replace(/\n/g, '⏎').replace(/\t/g, '→').replace(/\s/g, '␣');
|
|
@@ -1,2 +1,6 @@
|
|
|
1
1
|
import type { ElementType, ParserAuthoredElementNameDistinguishing } from '@markuplint/ml-ast';
|
|
2
|
-
export declare function detectElementType(
|
|
2
|
+
export declare function detectElementType(
|
|
3
|
+
name: string,
|
|
4
|
+
option?: ParserAuthoredElementNameDistinguishing,
|
|
5
|
+
defaultPattern?: ParserAuthoredElementNameDistinguishing,
|
|
6
|
+
): ElementType;
|
|
@@ -10,10 +10,10 @@ function detectElementType(name, option, defaultPattern) {
|
|
|
10
10
|
}
|
|
11
11
|
exports.detectElementType = detectElementType;
|
|
12
12
|
function distinguishAuthoredName(name, pattern, defaultPattern) {
|
|
13
|
-
if (pattern) {
|
|
13
|
+
if (pattern != null) {
|
|
14
14
|
return _distinguishAuthoredName(name, pattern);
|
|
15
15
|
}
|
|
16
|
-
if (defaultPattern) {
|
|
16
|
+
if (defaultPattern != null) {
|
|
17
17
|
return _distinguishAuthoredName(name, defaultPattern);
|
|
18
18
|
}
|
|
19
19
|
return false;
|
package/lib/flatten-nodes.js
CHANGED
|
@@ -8,6 +8,7 @@ const parser_utils_1 = require("@markuplint/parser-utils");
|
|
|
8
8
|
function flattenNodes(
|
|
9
9
|
// eslint-disable-next-line @typescript-eslint/prefer-readonly-parameter-types
|
|
10
10
|
nodeTree, rawHtml, createLastText = true) {
|
|
11
|
+
var _a, _b, _c, _d;
|
|
11
12
|
const nodeOrders = arrayize(nodeTree, rawHtml);
|
|
12
13
|
{
|
|
13
14
|
/**
|
|
@@ -26,21 +27,19 @@ nodeTree, rawHtml, createLastText = true) {
|
|
|
26
27
|
const endTag = node;
|
|
27
28
|
if (endTag.nodeName.toLowerCase() === 'body' && prevToken.type === 'text') {
|
|
28
29
|
const prevWreckagesText = prevToken;
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
prevWreckagesText.endCol = (0, parser_utils_1.getEndCol)(raw, startCol);
|
|
43
|
-
}
|
|
30
|
+
const wreckages = (0, tag_splitter_1.default)(prevWreckagesText.raw, prevWreckagesText.startLine, prevWreckagesText.startCol);
|
|
31
|
+
if (wreckages.length > 0 && wreckages[0]) {
|
|
32
|
+
// console.log('wreckages\n', wreckages);
|
|
33
|
+
const lastText = wreckages[0];
|
|
34
|
+
const raw = lastText.raw;
|
|
35
|
+
const startLine = lastText.line;
|
|
36
|
+
const startCol = lastText.col;
|
|
37
|
+
prevWreckagesText.raw = raw;
|
|
38
|
+
prevWreckagesText.endOffset = prevWreckagesText.startOffset + raw.length;
|
|
39
|
+
prevWreckagesText.startLine = startLine;
|
|
40
|
+
prevWreckagesText.endLine = (0, parser_utils_1.getEndLine)(raw, startLine);
|
|
41
|
+
prevWreckagesText.startCol = startCol;
|
|
42
|
+
prevWreckagesText.endCol = (0, parser_utils_1.getEndCol)(raw, startCol);
|
|
44
43
|
}
|
|
45
44
|
}
|
|
46
45
|
}
|
|
@@ -61,7 +60,7 @@ nodeTree, rawHtml, createLastText = true) {
|
|
|
61
60
|
if (lastNode.type === 'text') {
|
|
62
61
|
// Correction for Parse5 AST
|
|
63
62
|
// prev node: ? -> html
|
|
64
|
-
lastNode.prevNode = lastNode.parentNode && lastNode.parentNode
|
|
63
|
+
lastNode.prevNode = (_b = (_a = lastNode.parentNode) === null || _a === void 0 ? void 0 : _a.parentNode) !== null && _b !== void 0 ? _b : lastNode.parentNode;
|
|
65
64
|
if (lastNode.prevNode) {
|
|
66
65
|
lastNode.prevNode.nextNode = lastNode;
|
|
67
66
|
}
|
|
@@ -82,8 +81,8 @@ nodeTree, rawHtml, createLastText = true) {
|
|
|
82
81
|
const lastTextContent = rawHtml.slice(lastOffset);
|
|
83
82
|
// console.log(`"${lastTextContent}"`);
|
|
84
83
|
if (lastTextContent) {
|
|
85
|
-
const line = lastNode ? lastNode.endLine : 0;
|
|
86
|
-
const col = lastNode ? lastNode.endCol : 0;
|
|
84
|
+
const line = (_c = lastNode === null || lastNode === void 0 ? void 0 : lastNode.endLine) !== null && _c !== void 0 ? _c : 0;
|
|
85
|
+
const col = (_d = lastNode === null || lastNode === void 0 ? void 0 : lastNode.endCol) !== null && _d !== void 0 ? _d : 0;
|
|
87
86
|
const lastTextNode = {
|
|
88
87
|
uuid: (0, parser_utils_1.uuid)(),
|
|
89
88
|
raw: lastTextContent,
|
|
@@ -101,11 +100,9 @@ nodeTree, rawHtml, createLastText = true) {
|
|
|
101
100
|
isFragment: false,
|
|
102
101
|
isGhost: false,
|
|
103
102
|
};
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
lastNode.pearNode.nextNode = lastTextNode;
|
|
108
|
-
}
|
|
103
|
+
lastNode.nextNode = lastTextNode;
|
|
104
|
+
if ((lastNode.type === 'starttag' || lastNode.type === 'endtag') && lastNode.pearNode) {
|
|
105
|
+
lastNode.pearNode.nextNode = lastTextNode;
|
|
109
106
|
}
|
|
110
107
|
nodeOrders.push(lastTextNode);
|
|
111
108
|
}
|
|
@@ -117,15 +114,24 @@ nodeTree, rawHtml, createLastText = true) {
|
|
|
117
114
|
*/
|
|
118
115
|
const result = [];
|
|
119
116
|
nodeOrders.forEach(node => {
|
|
120
|
-
|
|
121
|
-
|
|
117
|
+
var _a, _b;
|
|
118
|
+
const prevNode = (_a = result[result.length - 1]) !== null && _a !== void 0 ? _a : null;
|
|
119
|
+
if (node.type === 'text' && (prevNode === null || prevNode === void 0 ? void 0 : prevNode.type) === 'text') {
|
|
122
120
|
prevNode.raw = prevNode.raw + node.raw;
|
|
123
121
|
prevNode.endOffset = node.endOffset;
|
|
124
122
|
prevNode.endLine = node.endLine;
|
|
125
123
|
prevNode.endCol = node.endCol;
|
|
126
124
|
prevNode.nextNode = node.nextNode;
|
|
127
|
-
if (prevNode.parentNode
|
|
128
|
-
|
|
125
|
+
if (prevNode.parentNode) {
|
|
126
|
+
if (prevNode.parentNode.childNodes) {
|
|
127
|
+
if (prevNode.parentNode.childNodes.findIndex(currentChild => currentChild.uuid === prevNode.uuid) === -1) {
|
|
128
|
+
prevNode.parentNode.childNodes.unshift(prevNode);
|
|
129
|
+
}
|
|
130
|
+
else {
|
|
131
|
+
prevNode.parentNode.childNodes = [prevNode];
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
prevNode.parentNode.childNodes = (_b = prevNode.parentNode.childNodes) === null || _b === void 0 ? void 0 : _b.filter(n => n.uuid !== node.uuid);
|
|
129
135
|
}
|
|
130
136
|
if (node.nextNode) {
|
|
131
137
|
node.nextNode.prevNode = prevNode;
|
|
@@ -190,6 +196,7 @@ nodeTree, rawHtml) {
|
|
|
190
196
|
* pushing list
|
|
191
197
|
*/
|
|
192
198
|
(0, parser_utils_1.walk)(nodeTree, node => {
|
|
199
|
+
var _a;
|
|
193
200
|
const diff = node.startOffset - currentEndOffset;
|
|
194
201
|
if (diff > 0) {
|
|
195
202
|
const html = rawHtml.slice(currentEndOffset, node.startOffset);
|
|
@@ -237,8 +244,7 @@ nodeTree, rawHtml) {
|
|
|
237
244
|
prevLine = node.endLine;
|
|
238
245
|
prevCol = node.endCol;
|
|
239
246
|
// for ghost nodes
|
|
240
|
-
node.
|
|
241
|
-
node.endOffset = node.endOffset || currentEndOffset;
|
|
247
|
+
node.endOffset = (_a = node.endOffset) !== null && _a !== void 0 ? _a : currentEndOffset;
|
|
242
248
|
nodeOrders.push(node);
|
|
243
249
|
});
|
|
244
250
|
return nodeOrders.slice();
|
package/lib/get-location.d.ts
CHANGED
|
@@ -2,12 +2,16 @@ export declare function getLine(html: string, startOffset: number): number;
|
|
|
2
2
|
export declare function getCol(html: string, startOffset: number): number;
|
|
3
3
|
export declare function getEndLine(html: string, line: number): number;
|
|
4
4
|
export declare function getEndCol(html: string, col: number): number;
|
|
5
|
-
export declare function sliceFragment(
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
5
|
+
export declare function sliceFragment(
|
|
6
|
+
rawHtml: string,
|
|
7
|
+
start: number,
|
|
8
|
+
end: number,
|
|
9
|
+
): {
|
|
10
|
+
startOffset: number;
|
|
11
|
+
endOffset: number;
|
|
12
|
+
startLine: number;
|
|
13
|
+
endLine: number;
|
|
14
|
+
startCol: number;
|
|
15
|
+
endCol: number;
|
|
16
|
+
raw: string;
|
|
13
17
|
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare function getSpaceBefore(offset: number, rawCode: string): import('@markuplint/ml-ast').MLToken;
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.getSpaceBefore = void 0;
|
|
4
|
+
const create_token_1 = require("./create-token");
|
|
5
|
+
function getSpaceBefore(offset, rawCode) {
|
|
6
|
+
var _a;
|
|
7
|
+
const aboveCode = rawCode.slice(0, offset);
|
|
8
|
+
const aboveAttrMatched = aboveCode.match(/\s+$/m);
|
|
9
|
+
const aboveAttrChar = (_a = aboveAttrMatched === null || aboveAttrMatched === void 0 ? void 0 : aboveAttrMatched[0]) !== null && _a !== void 0 ? _a : '';
|
|
10
|
+
const spacesBefore = (0, create_token_1.createTokenFromRawCode)(aboveAttrChar, offset - aboveAttrChar.length, rawCode);
|
|
11
|
+
return spacesBefore;
|
|
12
|
+
}
|
|
13
|
+
exports.getSpaceBefore = getSpaceBefore;
|
package/lib/idl-attributes.d.ts
CHANGED
package/lib/idl-attributes.js
CHANGED
|
@@ -419,12 +419,13 @@ const idlContentMap = {
|
|
|
419
419
|
};
|
|
420
420
|
const list = Object.entries(idlContentMap);
|
|
421
421
|
function searchIDLAttribute(name) {
|
|
422
|
+
var _a;
|
|
422
423
|
const camelizedName = camelize(name);
|
|
423
|
-
const [idlPropName, contentAttrName] =
|
|
424
|
-
|
|
424
|
+
const [idlPropName, contentAttrName] = /^on[a-z]/.test(name)
|
|
425
|
+
? [name.toLowerCase(), name.toLowerCase()]
|
|
426
|
+
: (_a = list.find(([idlPropName, contentAttrName]) => idlPropName.toLowerCase() === camelizedName.toLowerCase() ||
|
|
425
427
|
contentAttrName.toLowerCase() === name.toLowerCase() ||
|
|
426
|
-
hyphenize(idlPropName) === name.toLowerCase())
|
|
427
|
-
[];
|
|
428
|
+
hyphenize(idlPropName) === name.toLowerCase())) !== null && _a !== void 0 ? _a : [];
|
|
428
429
|
return {
|
|
429
430
|
idlPropName,
|
|
430
431
|
contentAttrName,
|
package/lib/ignore-block.js
CHANGED
|
@@ -13,7 +13,7 @@ function ignoreBlock(source, tags, maskChar = const_1.MASK_CHAR) {
|
|
|
13
13
|
const attr = maskText(prepend(tag.start, '(?<=(?:"|\'))'), append(tag.end, '(?=(?:"|\'))'), replaced, (startTag, taggedCode, endTag) => {
|
|
14
14
|
const mask = maskChar.repeat(startTag.length) +
|
|
15
15
|
taggedCode.replace(/[^\n]/g, maskChar) +
|
|
16
|
-
maskChar.repeat((endTag
|
|
16
|
+
maskChar.repeat((endTag !== null && endTag !== void 0 ? endTag : '').length);
|
|
17
17
|
return mask;
|
|
18
18
|
});
|
|
19
19
|
replaced = attr.replaced;
|
|
@@ -22,7 +22,7 @@ function ignoreBlock(source, tags, maskChar = const_1.MASK_CHAR) {
|
|
|
22
22
|
const text = maskText(tag.start, tag.end, replaced, (startTag, taggedCode, endTag) => {
|
|
23
23
|
const mask = maskChar.repeat(startTag.length) +
|
|
24
24
|
taggedCode.replace(/[^\n]/g, maskChar) +
|
|
25
|
-
maskChar.repeat((endTag
|
|
25
|
+
maskChar.repeat((endTag !== null && endTag !== void 0 ? endTag : '').length);
|
|
26
26
|
const taggedMask = `<!${mask.slice(2).slice(0, -1)}>`;
|
|
27
27
|
return taggedMask;
|
|
28
28
|
});
|
|
@@ -52,12 +52,12 @@ function maskText(start, end, replaced, masking) {
|
|
|
52
52
|
index,
|
|
53
53
|
startTag,
|
|
54
54
|
taggedCode,
|
|
55
|
-
endTag: endTag
|
|
55
|
+
endTag: endTag !== null && endTag !== void 0 ? endTag : null,
|
|
56
56
|
});
|
|
57
57
|
/**
|
|
58
58
|
* It will not replace line breaks because detects line number.
|
|
59
59
|
*/
|
|
60
|
-
replaced = above + masking(startTag, taggedCode, endTag) + (below
|
|
60
|
+
replaced = above + masking(startTag, taggedCode, endTag) + (below !== null && below !== void 0 ? below : '');
|
|
61
61
|
}
|
|
62
62
|
return {
|
|
63
63
|
replaced,
|
|
@@ -67,7 +67,7 @@ function maskText(start, end, replaced, masking) {
|
|
|
67
67
|
function restoreNode(
|
|
68
68
|
// eslint-disable-next-line @typescript-eslint/prefer-readonly-parameter-types
|
|
69
69
|
nodeList, ignoreBlock) {
|
|
70
|
-
var _a, _b, _c, _d;
|
|
70
|
+
var _a, _b, _c, _d, _e;
|
|
71
71
|
nodeList = nodeList.slice();
|
|
72
72
|
const { source, stack, maskChar } = ignoreBlock;
|
|
73
73
|
for (const node of nodeList) {
|
|
@@ -83,7 +83,7 @@ nodeList, ignoreBlock) {
|
|
|
83
83
|
for (const tag of stack) {
|
|
84
84
|
if (node.startOffset <= tag.index && tag.index < node.endOffset) {
|
|
85
85
|
const start = tag.index - node.startOffset;
|
|
86
|
-
const body = tag.startTag + tag.taggedCode + (tag.endTag
|
|
86
|
+
const body = tag.startTag + tag.taggedCode + ((_a = tag.endTag) !== null && _a !== void 0 ? _a : '');
|
|
87
87
|
const above = node.raw.slice(pointer, start);
|
|
88
88
|
const below = text.slice(above.length + body.length);
|
|
89
89
|
if (above) {
|
|
@@ -101,10 +101,10 @@ nodeList, ignoreBlock) {
|
|
|
101
101
|
startCol,
|
|
102
102
|
endCol,
|
|
103
103
|
};
|
|
104
|
-
if ((
|
|
104
|
+
if ((_b = node.prevNode) === null || _b === void 0 ? void 0 : _b.nextNode) {
|
|
105
105
|
node.prevNode.nextNode = textNode;
|
|
106
106
|
}
|
|
107
|
-
if ((
|
|
107
|
+
if ((_c = node.nextNode) === null || _c === void 0 ? void 0 : _c.prevNode) {
|
|
108
108
|
node.nextNode.prevNode = textNode;
|
|
109
109
|
}
|
|
110
110
|
insertList.push(textNode);
|
|
@@ -129,10 +129,10 @@ nodeList, ignoreBlock) {
|
|
|
129
129
|
startCol,
|
|
130
130
|
endCol,
|
|
131
131
|
};
|
|
132
|
-
if ((
|
|
132
|
+
if ((_d = node.prevNode) === null || _d === void 0 ? void 0 : _d.nextNode) {
|
|
133
133
|
node.prevNode.nextNode = bodyNode;
|
|
134
134
|
}
|
|
135
|
-
if ((
|
|
135
|
+
if ((_e = node.nextNode) === null || _e === void 0 ? void 0 : _e.prevNode) {
|
|
136
136
|
node.nextNode.prevNode = bodyNode;
|
|
137
137
|
}
|
|
138
138
|
insertList.push(bodyNode);
|
package/lib/index.d.ts
CHANGED
|
@@ -5,9 +5,11 @@ export * from './decision';
|
|
|
5
5
|
export * from './detect-element-type';
|
|
6
6
|
export * from './flatten-nodes';
|
|
7
7
|
export * from './get-location';
|
|
8
|
+
export * from './get-space-before';
|
|
8
9
|
export * from './idl-attributes';
|
|
9
10
|
export * from './ignore-block';
|
|
10
11
|
export * from './ignore-front-matter';
|
|
12
|
+
export * from './parse-attr';
|
|
11
13
|
export * from './parser-error';
|
|
12
14
|
export * from './remove-deprecated-node';
|
|
13
15
|
export * from './tag-splitter';
|
package/lib/index.js
CHANGED
|
@@ -8,9 +8,11 @@ tslib_1.__exportStar(require("./decision"), exports);
|
|
|
8
8
|
tslib_1.__exportStar(require("./detect-element-type"), exports);
|
|
9
9
|
tslib_1.__exportStar(require("./flatten-nodes"), exports);
|
|
10
10
|
tslib_1.__exportStar(require("./get-location"), exports);
|
|
11
|
+
tslib_1.__exportStar(require("./get-space-before"), exports);
|
|
11
12
|
tslib_1.__exportStar(require("./idl-attributes"), exports);
|
|
12
13
|
tslib_1.__exportStar(require("./ignore-block"), exports);
|
|
13
14
|
tslib_1.__exportStar(require("./ignore-front-matter"), exports);
|
|
15
|
+
tslib_1.__exportStar(require("./parse-attr"), exports);
|
|
14
16
|
tslib_1.__exportStar(require("./parser-error"), exports);
|
|
15
17
|
tslib_1.__exportStar(require("./remove-deprecated-node"), exports);
|
|
16
18
|
tslib_1.__exportStar(require("./tag-splitter"), exports);
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import type { MLASTHTMLAttr } from '@markuplint/ml-ast';
|
|
2
|
+
type ParseAttrOptions = {
|
|
3
|
+
readonly booleanish?: boolean;
|
|
4
|
+
readonly valueDelimiters?: readonly ValueDelimiter[];
|
|
5
|
+
readonly equal?: string;
|
|
6
|
+
};
|
|
7
|
+
type ValueDelimiter = {
|
|
8
|
+
readonly start: string;
|
|
9
|
+
readonly end: string;
|
|
10
|
+
};
|
|
11
|
+
export declare const defaultValueDelimiters: readonly ValueDelimiter[];
|
|
12
|
+
export declare function parseAttr(raw: string, offset: number, html: string, options?: ParseAttrOptions): MLASTHTMLAttr;
|
|
13
|
+
export declare function tokenize(
|
|
14
|
+
raw: string,
|
|
15
|
+
options?: ParseAttrOptions,
|
|
16
|
+
): {
|
|
17
|
+
beforeName: string;
|
|
18
|
+
name: string;
|
|
19
|
+
afterName: string;
|
|
20
|
+
equal: string;
|
|
21
|
+
beforeValue: string;
|
|
22
|
+
startQuote: string;
|
|
23
|
+
value: string;
|
|
24
|
+
endQuote: string;
|
|
25
|
+
afterAttr: string;
|
|
26
|
+
};
|
|
27
|
+
export {};
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.tokenize = exports.parseAttr = exports.defaultValueDelimiters = void 0;
|
|
4
|
+
const create_token_1 = require("./create-token");
|
|
5
|
+
exports.defaultValueDelimiters = [
|
|
6
|
+
{
|
|
7
|
+
start: "'",
|
|
8
|
+
end: "'",
|
|
9
|
+
},
|
|
10
|
+
{
|
|
11
|
+
start: '"',
|
|
12
|
+
end: '"',
|
|
13
|
+
},
|
|
14
|
+
];
|
|
15
|
+
const defaultEqual = '=';
|
|
16
|
+
const spaceRegex = /^\s$/;
|
|
17
|
+
function parseAttr(raw, offset, html, options) {
|
|
18
|
+
const tokens = tokenize(raw, options);
|
|
19
|
+
tokens.beforeName;
|
|
20
|
+
const attrToken = (0, create_token_1.createTokenFromRawCode)(raw, offset, html);
|
|
21
|
+
const spacesBeforeName = (0, create_token_1.tokenizer)(tokens.beforeName, attrToken.startLine, attrToken.startCol, attrToken.startOffset);
|
|
22
|
+
const name = (0, create_token_1.tokenizer)(tokens.name, spacesBeforeName.endLine, spacesBeforeName.endCol, spacesBeforeName.endOffset);
|
|
23
|
+
const spacesBeforeEqual = (0, create_token_1.tokenizer)(tokens.afterName, name.endLine, name.endCol, name.endOffset);
|
|
24
|
+
const equal = (0, create_token_1.tokenizer)(tokens.equal, spacesBeforeEqual.endLine, spacesBeforeEqual.endCol, spacesBeforeEqual.endOffset);
|
|
25
|
+
const spacesAfterEqual = (0, create_token_1.tokenizer)(tokens.beforeValue, equal.endLine, equal.endCol, equal.endOffset);
|
|
26
|
+
const startQuote = (0, create_token_1.tokenizer)(tokens.startQuote, spacesAfterEqual.endLine, spacesAfterEqual.endCol, spacesAfterEqual.endOffset);
|
|
27
|
+
const value = (0, create_token_1.tokenizer)(tokens.value, startQuote.endLine, startQuote.endCol, startQuote.endOffset);
|
|
28
|
+
const endQuote = (0, create_token_1.tokenizer)(tokens.endQuote, value.endLine, value.endCol, value.endOffset);
|
|
29
|
+
const attr = {
|
|
30
|
+
type: 'html-attr',
|
|
31
|
+
uuid: (0, create_token_1.uuid)(),
|
|
32
|
+
raw: attrToken.raw,
|
|
33
|
+
startOffset: attrToken.startOffset,
|
|
34
|
+
endOffset: attrToken.endOffset,
|
|
35
|
+
startLine: attrToken.startLine,
|
|
36
|
+
endLine: attrToken.endLine,
|
|
37
|
+
startCol: attrToken.startCol,
|
|
38
|
+
endCol: attrToken.endCol,
|
|
39
|
+
spacesBeforeName,
|
|
40
|
+
name,
|
|
41
|
+
spacesBeforeEqual,
|
|
42
|
+
equal,
|
|
43
|
+
spacesAfterEqual,
|
|
44
|
+
startQuote,
|
|
45
|
+
value,
|
|
46
|
+
endQuote,
|
|
47
|
+
isDuplicatable: false,
|
|
48
|
+
nodeName: name.raw,
|
|
49
|
+
parentNode: null,
|
|
50
|
+
nextNode: null,
|
|
51
|
+
prevNode: null,
|
|
52
|
+
isFragment: false,
|
|
53
|
+
isGhost: false,
|
|
54
|
+
};
|
|
55
|
+
return attr;
|
|
56
|
+
}
|
|
57
|
+
exports.parseAttr = parseAttr;
|
|
58
|
+
function tokenize(raw, options) {
|
|
59
|
+
var _a, _b, _c;
|
|
60
|
+
const valueDelimiters = (_a = options === null || options === void 0 ? void 0 : options.valueDelimiters) !== null && _a !== void 0 ? _a : exports.defaultValueDelimiters;
|
|
61
|
+
const equalDelimiter = (_b = options === null || options === void 0 ? void 0 : options.equal) !== null && _b !== void 0 ? _b : defaultEqual;
|
|
62
|
+
let state = 'b-name';
|
|
63
|
+
const charactors = raw.split('');
|
|
64
|
+
let beforeName = '';
|
|
65
|
+
let name = '';
|
|
66
|
+
let afterName = '';
|
|
67
|
+
let equal = '';
|
|
68
|
+
let valueDelimiter = null;
|
|
69
|
+
let beforeValue = '';
|
|
70
|
+
let startQuote = '';
|
|
71
|
+
let value = '';
|
|
72
|
+
let endQuote = '';
|
|
73
|
+
let afterAttr = '';
|
|
74
|
+
while (charactors.length > 0) {
|
|
75
|
+
const charactor = charactors.shift();
|
|
76
|
+
if (state === 'b-name') {
|
|
77
|
+
if (spaceRegex.test(charactor)) {
|
|
78
|
+
beforeName += charactor;
|
|
79
|
+
continue;
|
|
80
|
+
}
|
|
81
|
+
name += charactor;
|
|
82
|
+
state = 'name';
|
|
83
|
+
continue;
|
|
84
|
+
}
|
|
85
|
+
if (state === 'name') {
|
|
86
|
+
if (equalDelimiter === charactor) {
|
|
87
|
+
equal = equalDelimiter;
|
|
88
|
+
state = 'value-start';
|
|
89
|
+
continue;
|
|
90
|
+
}
|
|
91
|
+
if (spaceRegex.test(charactor)) {
|
|
92
|
+
afterName += charactor;
|
|
93
|
+
state = 'a-name';
|
|
94
|
+
continue;
|
|
95
|
+
}
|
|
96
|
+
name += charactor;
|
|
97
|
+
continue;
|
|
98
|
+
}
|
|
99
|
+
if (state === 'a-name') {
|
|
100
|
+
if (equalDelimiter === charactor) {
|
|
101
|
+
equal = equalDelimiter;
|
|
102
|
+
state = 'value-start';
|
|
103
|
+
continue;
|
|
104
|
+
}
|
|
105
|
+
if (spaceRegex.test(charactor)) {
|
|
106
|
+
afterName += charactor;
|
|
107
|
+
continue;
|
|
108
|
+
}
|
|
109
|
+
break;
|
|
110
|
+
}
|
|
111
|
+
if (state === 'value-start') {
|
|
112
|
+
if (spaceRegex.test(charactor)) {
|
|
113
|
+
beforeValue += charactor;
|
|
114
|
+
continue;
|
|
115
|
+
}
|
|
116
|
+
valueDelimiter = (_c = valueDelimiters.find(d => d.start === charactor)) !== null && _c !== void 0 ? _c : null;
|
|
117
|
+
if (valueDelimiter) {
|
|
118
|
+
startQuote += valueDelimiter.start;
|
|
119
|
+
}
|
|
120
|
+
else {
|
|
121
|
+
value += beforeValue + charactor;
|
|
122
|
+
beforeValue = '';
|
|
123
|
+
}
|
|
124
|
+
state = 'value';
|
|
125
|
+
continue;
|
|
126
|
+
}
|
|
127
|
+
if (state !== 'value') {
|
|
128
|
+
throw new Error('ParseError: unknown parse state in the attribute');
|
|
129
|
+
}
|
|
130
|
+
value += charactor;
|
|
131
|
+
}
|
|
132
|
+
if (valueDelimiter) {
|
|
133
|
+
const endQuoteIndex = value.lastIndexOf(valueDelimiter.end);
|
|
134
|
+
endQuote = value.slice(endQuoteIndex, endQuoteIndex + 1);
|
|
135
|
+
afterAttr = value.slice(endQuoteIndex + 1);
|
|
136
|
+
value = value.slice(0, endQuoteIndex);
|
|
137
|
+
}
|
|
138
|
+
return {
|
|
139
|
+
beforeName,
|
|
140
|
+
name,
|
|
141
|
+
afterName,
|
|
142
|
+
equal,
|
|
143
|
+
beforeValue,
|
|
144
|
+
startQuote,
|
|
145
|
+
value,
|
|
146
|
+
endQuote,
|
|
147
|
+
afterAttr,
|
|
148
|
+
};
|
|
149
|
+
}
|
|
150
|
+
exports.tokenize = tokenize;
|
package/lib/parser-error.d.ts
CHANGED
|
@@ -1,13 +1,21 @@
|
|
|
1
1
|
export declare class ParserError extends Error {
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
2
|
+
readonly col: number;
|
|
3
|
+
readonly line: number;
|
|
4
|
+
name: string;
|
|
5
|
+
readonly nodeName: string | null;
|
|
6
|
+
readonly raw: string;
|
|
7
|
+
constructor(
|
|
8
|
+
message: string,
|
|
9
|
+
{
|
|
10
|
+
line,
|
|
11
|
+
col,
|
|
12
|
+
raw,
|
|
13
|
+
nodeName,
|
|
14
|
+
}: {
|
|
15
|
+
readonly line?: number;
|
|
16
|
+
readonly col?: number;
|
|
17
|
+
readonly raw?: string;
|
|
18
|
+
readonly nodeName?: string | null;
|
|
19
|
+
},
|
|
20
|
+
);
|
|
13
21
|
}
|
|
@@ -11,13 +11,14 @@ exports.siblingsCorrection = void 0;
|
|
|
11
11
|
function siblingsCorrection(
|
|
12
12
|
// eslint-disable-next-line @typescript-eslint/prefer-readonly-parameter-types
|
|
13
13
|
nodeList) {
|
|
14
|
+
var _a, _b;
|
|
14
15
|
for (let i = 0; i < nodeList.length; i++) {
|
|
15
|
-
const prevNode = nodeList[i - 1]
|
|
16
|
+
const prevNode = (_a = nodeList[i - 1]) !== null && _a !== void 0 ? _a : null;
|
|
16
17
|
const node = nodeList[i];
|
|
17
18
|
if (!node) {
|
|
18
19
|
continue;
|
|
19
20
|
}
|
|
20
|
-
const nextNode = nodeList[i + 1]
|
|
21
|
+
const nextNode = (_b = nodeList[i + 1]) !== null && _b !== void 0 ? _b : null;
|
|
21
22
|
node.prevNode = prevNode;
|
|
22
23
|
node.nextNode = nextNode;
|
|
23
24
|
}
|
package/lib/tag-splitter.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
export interface N {
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
2
|
+
type: 'text' | 'starttag' | 'endtag' | 'comment' | 'boguscomment';
|
|
3
|
+
raw: string;
|
|
4
|
+
line: number;
|
|
5
|
+
col: number;
|
|
6
6
|
}
|
|
7
7
|
export default function tagSplitter(raw: string, line: number, col: number): N[];
|
package/lib/types.d.ts
CHANGED
|
@@ -1,18 +1,18 @@
|
|
|
1
1
|
export type Code = {
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
2
|
+
readonly type: string;
|
|
3
|
+
readonly index: number;
|
|
4
|
+
readonly startTag: string;
|
|
5
|
+
readonly taggedCode: string;
|
|
6
|
+
readonly endTag: string | null;
|
|
7
7
|
};
|
|
8
8
|
export type IgnoreTag = {
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
9
|
+
readonly type: string;
|
|
10
|
+
readonly start: Readonly<RegExp>;
|
|
11
|
+
readonly end: Readonly<RegExp>;
|
|
12
12
|
};
|
|
13
13
|
export type IgnoreBlock = {
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
14
|
+
readonly source: string;
|
|
15
|
+
readonly replaced: string;
|
|
16
|
+
readonly stack: readonly Code[];
|
|
17
|
+
readonly maskChar: string;
|
|
18
18
|
};
|
package/lib/walker.js
CHANGED
|
@@ -10,7 +10,7 @@ nodeList, walker, depth = 0) {
|
|
|
10
10
|
if (node.type === 'endtag') {
|
|
11
11
|
continue;
|
|
12
12
|
}
|
|
13
|
-
if (node.childNodes && node.childNodes.length) {
|
|
13
|
+
if (node.childNodes && node.childNodes.length > 0) {
|
|
14
14
|
walk(node.childNodes, walker, depth + 1);
|
|
15
15
|
}
|
|
16
16
|
if ('pearNode' in node && node.pearNode) {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@markuplint/parser-utils",
|
|
3
|
-
"version": "3.
|
|
3
|
+
"version": "3.6.0",
|
|
4
4
|
"description": "Utility module for markuplint parser plugin",
|
|
5
5
|
"repository": "git@github.com:markuplint/markuplint.git",
|
|
6
6
|
"author": "Yusuke Hirao <yusukehirao@me.com>",
|
|
@@ -24,12 +24,12 @@
|
|
|
24
24
|
},
|
|
25
25
|
"dependencies": {
|
|
26
26
|
"@markuplint/ml-ast": "3.1.0",
|
|
27
|
-
"@markuplint/types": "3.
|
|
27
|
+
"@markuplint/types": "3.5.0",
|
|
28
28
|
"tslib": "^2.4.1",
|
|
29
29
|
"uuid": "^9.0.0"
|
|
30
30
|
},
|
|
31
31
|
"peerDependencies": {
|
|
32
32
|
"@markuplint/ml-core": "3.x"
|
|
33
33
|
},
|
|
34
|
-
"gitHead": "
|
|
34
|
+
"gitHead": "715dd53d3b1064a9bcf616c1533921cad9e3b187"
|
|
35
35
|
}
|