wikilint 2.44.0 → 2.46.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/config/default.json +1 -2
- package/config/enwiki.json +1 -1
- package/config/jawiki.json +1 -1
- package/config/minimum.json +1 -1
- package/config/zhwiki.json +1 -1
- package/data/ext/templatedata.json +13 -5
- package/data/signatures.json +38 -32
- package/dist/base.d.mts +10 -2
- package/dist/base.d.ts +10 -2
- package/dist/bin/config.js +1 -1
- package/dist/index.js +1 -1
- package/dist/internal.d.ts +6 -1
- package/dist/lib/element.js +5 -5
- package/dist/lib/lintConfig.js +7 -0
- package/dist/lib/lsp.d.ts +11 -3
- package/dist/lib/lsp.js +91 -59
- package/dist/lib/node.js +2 -2
- package/dist/lib/text.js +2 -2
- package/dist/map.d.ts +4 -1
- package/dist/mixin/elementLike.js +29 -31
- package/dist/mixin/hidden.js +0 -1
- package/dist/mixin/paramLineParent.d.ts +29 -0
- package/dist/mixin/paramLineParent.js +51 -0
- package/dist/src/arg.js +17 -35
- package/dist/src/atom.d.ts +1 -1
- package/dist/src/atom.js +2 -0
- package/dist/src/attribute.js +10 -5
- package/dist/src/attributes.js +18 -15
- package/dist/src/commented.d.ts +1 -0
- package/dist/src/commented.js +1 -3
- package/dist/src/converterFlags.js +18 -21
- package/dist/src/converterRule.js +2 -2
- package/dist/src/funcTag.d.ts +23 -0
- package/dist/src/funcTag.js +85 -0
- package/dist/src/heading.js +8 -3
- package/dist/src/hidden.d.ts +3 -2
- package/dist/src/hidden.js +29 -5
- package/dist/src/imageParameter.js +16 -4
- package/dist/src/index.js +2 -2
- package/dist/src/link/base.js +14 -2
- package/dist/src/link/categorytree.d.ts +2 -0
- package/dist/src/link/categorytree.js +8 -5
- package/dist/src/link/file.js +21 -14
- package/dist/src/multiLine/charinsert.d.ts +16 -0
- package/dist/src/multiLine/charinsert.js +84 -0
- package/dist/src/multiLine/gallery.js +4 -4
- package/dist/src/multiLine/imagemap.d.ts +1 -1
- package/dist/src/multiLine/imagemap.js +13 -12
- package/dist/src/multiLine/index.d.ts +3 -0
- package/dist/src/multiLine/index.js +79 -18
- package/dist/src/multiLine/inputbox.d.ts +1 -0
- package/dist/src/multiLine/paramTag.d.ts +3 -0
- package/dist/src/multiLine/paramTag.js +60 -13
- package/dist/src/nested.js +23 -25
- package/dist/src/nowiki/quote.js +6 -5
- package/dist/src/paramLine.d.ts +23 -3
- package/dist/src/paramLine.js +129 -31
- package/dist/src/parameter.d.ts +6 -0
- package/dist/src/parameter.js +15 -1
- package/dist/src/singleLine/charinsertLine.d.ts +21 -0
- package/dist/src/singleLine/charinsertLine.js +69 -0
- package/dist/src/{imagemapLink.d.ts → singleLine/imagemapLink.d.ts} +8 -7
- package/dist/src/singleLine/imagemapLink.js +95 -0
- package/dist/src/singleLine/index.d.ts +10 -0
- package/dist/src/singleLine/index.js +16 -0
- package/dist/src/table/td.js +5 -4
- package/dist/src/tag/html.js +26 -8
- package/dist/src/tag/index.js +30 -17
- package/dist/src/tagPair/ext.js +23 -2
- package/dist/src/tagPair/index.js +1 -10
- package/dist/src/transclude.js +15 -15
- package/dist/util/sharable.js +22 -0
- package/dist/util/sharable.mjs +22 -0
- package/dist/util/string.js +27 -2
- package/i18n/en.json +4 -0
- package/i18n/zh-hans.json +4 -0
- package/i18n/zh-hant.json +4 -0
- package/package.json +17 -25
- package/dist/src/imagemapLink.js +0 -34
- /package/dist/{util → vendor}/search.js +0 -0
package/dist/lib/lsp.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import Parser from '../index';
|
|
2
2
|
import { Token } from '../src/index';
|
|
3
|
-
import type { Range, Position, ColorInformation, ColorPresentation, FoldingRange, DocumentLink, Location, WorkspaceEdit, Diagnostic as DiagnosticBase, TextEdit, Hover, SignatureHelp, InlayHint, CodeAction, DocumentSymbol } from 'vscode-languageserver-types';
|
|
3
|
+
import type { Range, Position, ColorInformation, ColorPresentation, FoldingRange, DocumentLink, Location, DocumentHighlight, WorkspaceEdit, Diagnostic as DiagnosticBase, TextEdit, Hover, SignatureHelp, InlayHint, CodeAction, DocumentSymbol } from 'vscode-languageserver-types';
|
|
4
4
|
import type { Config, LanguageService as LanguageServiceBase, CompletionItem, SignatureData } from '../base';
|
|
5
5
|
import type { AttributeToken } from '../internal';
|
|
6
6
|
import type { TokenTypeMap, SelectedTokenTypes } from '../map';
|
|
@@ -24,9 +24,8 @@ export declare class LanguageService implements LanguageServiceBase {
|
|
|
24
24
|
* 提供颜色指示
|
|
25
25
|
* @param rgba color parser / 颜色解析函数
|
|
26
26
|
* @param text source Wikitext / 源代码
|
|
27
|
-
* @param hsl whether HSL colors are treated / 是否允许HSL颜色
|
|
28
27
|
*/
|
|
29
|
-
provideDocumentColors(rgba: (s: string) => [number, number, number, number] | [], text: string
|
|
28
|
+
provideDocumentColors(rgba: (s: string) => [number, number, number, number] | [], text: string): Promise<ColorInformation[]>;
|
|
30
29
|
/**
|
|
31
30
|
* Provide color pickers
|
|
32
31
|
*
|
|
@@ -72,6 +71,15 @@ export declare class LanguageService implements LanguageServiceBase {
|
|
|
72
71
|
* @param text source Wikitext / 源代码
|
|
73
72
|
*/
|
|
74
73
|
provideLinks(text: string): Promise<DocumentLink[]>;
|
|
74
|
+
/**
|
|
75
|
+
* Provide document highlights
|
|
76
|
+
*
|
|
77
|
+
* 提供文档高亮
|
|
78
|
+
* @param text source Wikitext / 源代码
|
|
79
|
+
* @param position position / 位置
|
|
80
|
+
* @since v1.46.0
|
|
81
|
+
*/
|
|
82
|
+
provideDocumentHighlights(text: string, position: Position): Promise<DocumentHighlight[] | undefined>;
|
|
75
83
|
/**
|
|
76
84
|
* Provide references
|
|
77
85
|
*
|
package/dist/lib/lsp.js
CHANGED
|
@@ -21,7 +21,8 @@ const util_1 = __importDefault(require("util"));
|
|
|
21
21
|
const child_process_1 = require("child_process");
|
|
22
22
|
const crypto_1 = require("crypto");
|
|
23
23
|
const stylelint_util_1 = require("@bhsd/stylelint-util");
|
|
24
|
-
const
|
|
24
|
+
const color_1 = require("@bhsd/common/color");
|
|
25
|
+
const search_1 = __importDefault(require("../vendor/search"));
|
|
25
26
|
const constants_2 = require("../util/constants");
|
|
26
27
|
const document_1 = require("./document");
|
|
27
28
|
exports.tasks = new WeakMap();
|
|
@@ -30,15 +31,17 @@ const refTags = new Set(['ref']), referencesTags = new Set(['ref', 'references']
|
|
|
30
31
|
'template-name',
|
|
31
32
|
'link-target',
|
|
32
33
|
'parameter-key',
|
|
33
|
-
]),
|
|
34
|
+
]), highlightTypes = new Set([
|
|
34
35
|
'ext',
|
|
35
36
|
'html',
|
|
36
37
|
'attr-key',
|
|
38
|
+
'magic-word-name',
|
|
39
|
+
...renameTypes,
|
|
40
|
+
]), referenceTypes = new Set([
|
|
37
41
|
'image-parameter',
|
|
38
42
|
'heading-title',
|
|
39
43
|
'heading',
|
|
40
|
-
|
|
41
|
-
...renameTypes,
|
|
44
|
+
...highlightTypes,
|
|
42
45
|
]), plainTypes = new Set(['text', 'comment', 'noinclude', 'include']), rawLilyPondCommands = new Set(['paper', 'book', 'bookpart', 'score', 'markuplist'].map(c => `\\${c}`)), cssSelector = ['ext', 'html', 'table'].map(s => `${s}-attr#style`).join();
|
|
43
46
|
const getLinkRegex = (0, common_1.getRegex)(protocol => new RegExp(`^(?:${protocol}|//)`, 'iu'));
|
|
44
47
|
/**
|
|
@@ -105,7 +108,7 @@ const createNodeRange = (token) => {
|
|
|
105
108
|
* @param extra extra text
|
|
106
109
|
* @param getDoc documentation method
|
|
107
110
|
*/
|
|
108
|
-
const getCompletion = (words, kind, mt, { line, character }, extra, getDoc) => [...new Set(words)].map((w) => {
|
|
111
|
+
const getCompletion = (words, kind, mt, { line, character }, extra = '', getDoc) => [...new Set(words)].map((w) => {
|
|
109
112
|
const doc = getDoc?.(w)?.description;
|
|
110
113
|
return {
|
|
111
114
|
label: w,
|
|
@@ -115,7 +118,7 @@ const getCompletion = (words, kind, mt, { line, character }, extra, getDoc) => [
|
|
|
115
118
|
start: { line, character: character - mt.length },
|
|
116
119
|
end: { line, character },
|
|
117
120
|
},
|
|
118
|
-
newText: w +
|
|
121
|
+
newText: w + extra,
|
|
119
122
|
},
|
|
120
123
|
...doc && {
|
|
121
124
|
documentation: {
|
|
@@ -168,8 +171,10 @@ const getName = (token) => {
|
|
|
168
171
|
return token.level;
|
|
169
172
|
case 'heading-title':
|
|
170
173
|
return parentNode.level;
|
|
171
|
-
case 'parameter-key':
|
|
172
|
-
|
|
174
|
+
case 'parameter-key': {
|
|
175
|
+
const { type: t, name: n } = parentNode.parentNode;
|
|
176
|
+
return n + (t === 'template' ? '|' : '#') + parentNode.name;
|
|
177
|
+
}
|
|
173
178
|
case 'ext':
|
|
174
179
|
case 'html':
|
|
175
180
|
case 'image-parameter':
|
|
@@ -178,6 +183,22 @@ const getName = (token) => {
|
|
|
178
183
|
return parentNode.name;
|
|
179
184
|
}
|
|
180
185
|
};
|
|
186
|
+
/**
|
|
187
|
+
* Get the tokens that match the given token.
|
|
188
|
+
* @param root
|
|
189
|
+
* @param node the token to match
|
|
190
|
+
* @param types accepted token types
|
|
191
|
+
*/
|
|
192
|
+
const getMatchingTokens = (root, node, types) => {
|
|
193
|
+
const { type } = node, refName = getRefName(node), refGroup = getRefGroup(node);
|
|
194
|
+
if (!refName && !refGroup && !types.has(type)) {
|
|
195
|
+
return undefined;
|
|
196
|
+
}
|
|
197
|
+
const name = getName(node), refs = root.querySelectorAll(type === 'heading-title' ? 'heading' : type).filter(token => type === 'attr-value'
|
|
198
|
+
? getRefName(token) === refName || getRefGroup(token) === refGroup
|
|
199
|
+
: getName(token) === name);
|
|
200
|
+
return refs.length === 0 ? undefined : refs.reverse();
|
|
201
|
+
};
|
|
181
202
|
/**
|
|
182
203
|
* Get the quick fix data.
|
|
183
204
|
* @param root root token
|
|
@@ -272,8 +293,7 @@ const partialParse = async (wikitext, watch, include, config = index_1.default.g
|
|
|
272
293
|
};
|
|
273
294
|
/* NOT FOR BROWSER ONLY */
|
|
274
295
|
/** @see https://www.npmjs.com/package/stylelint-config-recommended */
|
|
275
|
-
const cssRules = { 'block-no-empty': null }, sources = { 'invalid-css': 'css', 'invalid-math': 'texvc' }, jsonSelector = constants_2.jsonTags.map(s => `ext#${s}`).join(), scores = new Map();
|
|
276
|
-
let colors;
|
|
296
|
+
const cssRules = { 'block-no-empty': null }, colors = Object.keys(color_1.colorsNamed), sources = { 'invalid-css': 'css', 'invalid-math': 'texvc' }, jsonSelector = constants_2.jsonTags.map(s => `ext#${s}`).join(), scores = new Map();
|
|
277
297
|
/**
|
|
278
298
|
* Correct the position of an error.
|
|
279
299
|
* @param height
|
|
@@ -479,22 +499,9 @@ class LanguageService {
|
|
|
479
499
|
* 提供颜色指示
|
|
480
500
|
* @param rgba color parser / 颜色解析函数
|
|
481
501
|
* @param text source Wikitext / 源代码
|
|
482
|
-
* @param hsl whether HSL colors are treated / 是否允许HSL颜色
|
|
483
502
|
*/
|
|
484
|
-
async provideDocumentColors(rgba, text
|
|
503
|
+
async provideDocumentColors(rgba, text) {
|
|
485
504
|
const root = await this.#queue(text);
|
|
486
|
-
/* NOT FOR BROWSER ONLY */
|
|
487
|
-
if (colors === undefined) {
|
|
488
|
-
try {
|
|
489
|
-
const { default: colorName } = require('color-name');
|
|
490
|
-
colors = new RegExp(String.raw `\b${Object.keys(colorName).join('|')}\b`, 'giu');
|
|
491
|
-
}
|
|
492
|
-
catch {
|
|
493
|
-
/* c8 ignore next */
|
|
494
|
-
colors = false;
|
|
495
|
-
}
|
|
496
|
-
}
|
|
497
|
-
/* NOT FOR BROWSER ONLY END */
|
|
498
505
|
return root.querySelectorAll('attr-value,parameter-value,arg-default').reverse().flatMap(token => {
|
|
499
506
|
const { type, childNodes,
|
|
500
507
|
/* NOT FOR BROWSER ONLY */
|
|
@@ -509,15 +516,10 @@ class LanguageService {
|
|
|
509
516
|
/* NOT FOR BROWSER ONLY END */
|
|
510
517
|
}
|
|
511
518
|
/* NOT FOR BROWSER ONLY */
|
|
512
|
-
const isStyle =
|
|
519
|
+
const isStyle = type === 'attr-value' && parentNode.name === 'style';
|
|
513
520
|
/* NOT FOR BROWSER ONLY END */
|
|
514
521
|
return childNodes.filter((child) => child.type === 'text').reverse().flatMap(child => {
|
|
515
|
-
const { data } = child, parts = (0, common_1.splitColors)(data,
|
|
516
|
-
/* NOT FOR BROWSER ONLY */
|
|
517
|
-
if (isStyle) {
|
|
518
|
-
parts.push(...[...data.matchAll(colors)].map(({ index, 0: s }) => [s, index, index + s.length, true]));
|
|
519
|
-
}
|
|
520
|
-
/* NOT FOR BROWSER ONLY END */
|
|
522
|
+
const { data } = child, parts = (0, common_1.splitColors)(data, isStyle && colors).filter(([, , , isColor]) => isColor);
|
|
521
523
|
if (parts.length === 0) {
|
|
522
524
|
return [];
|
|
523
525
|
}
|
|
@@ -688,13 +690,8 @@ class LanguageService {
|
|
|
688
690
|
if (mt?.[7] !== undefined || type === 'image-parameter') { // image parameter
|
|
689
691
|
const index = root.indexFromPos(line, character), match = mt?.[7]?.trimStart()
|
|
690
692
|
?? this.#text.slice(cur.getAbsoluteIndex(), index).trimStart(), equal = this.#text[index] === '=';
|
|
691
|
-
return
|
|
692
|
-
|
|
693
|
-
.filter(({ label }) => !equal || !/[= ]$/u.test(label)),
|
|
694
|
-
...getCompletion(root.querySelectorAll('image-parameter#width')
|
|
695
|
-
.filter(token => token !== cur)
|
|
696
|
-
.map(width => width.text()), 'Unit', match, position),
|
|
697
|
-
];
|
|
693
|
+
return getCompletion(params, 'Property', match, position)
|
|
694
|
+
.filter(({ label }) => !equal || !/[= ]$/u.test(label));
|
|
698
695
|
}
|
|
699
696
|
else if (mt?.[8] !== undefined || type === 'attr-key') { // attribute key
|
|
700
697
|
const tag = mt?.[8]?.toLowerCase() ?? parentNode.tag, key = mt?.[10]
|
|
@@ -739,11 +736,11 @@ class LanguageService {
|
|
|
739
736
|
}).map(({ name }) => name), 'Variable', key, position, type === 'parameter-value' ? '=' : '')
|
|
740
737
|
: undefined;
|
|
741
738
|
}
|
|
742
|
-
else if (type === 'param-line') {
|
|
743
|
-
// parameter line of `<dynamicpagelist>` or `<
|
|
739
|
+
else if (type === 'param-line-key') {
|
|
740
|
+
// parameter line of `<dynamicpagelist>`, `<inputbox>` or `<seo>`
|
|
744
741
|
const key = this.#text.slice(cur.getAbsoluteIndex(), root.indexFromPos(line, character)).trimStart();
|
|
745
742
|
return /^[a-z]+$/iu.test(key)
|
|
746
|
-
? getCompletion(sharable_1.extParams[
|
|
743
|
+
? getCompletion(sharable_1.extParams[parentNode.name], 'Property', key, position)
|
|
747
744
|
: undefined;
|
|
748
745
|
/* NOT FOR BROWSER ONLY */
|
|
749
746
|
}
|
|
@@ -935,7 +932,8 @@ class LanguageService {
|
|
|
935
932
|
catch (e) {
|
|
936
933
|
const { stderr } = e;
|
|
937
934
|
if (stderr) {
|
|
938
|
-
const re = new RegExp(String.raw `^${file}:(\d+):(\d+): error: (.+)$`, 'gmu'), lilypondErrors = [...stderr.matchAll(re)]
|
|
935
|
+
const re = new RegExp(String.raw `^${file}:(\d+):(\d+): error: (.+)$`, 'gmu'), lilypondErrors = [...stderr.matchAll(re)]
|
|
936
|
+
.map(([, line, col, msg]) => {
|
|
939
937
|
const { offsetHeight, offsetWidth } = token.lastChild, pos = adjustPos(offsetHeight, offsetWidth, Number(line) - 1, Number(col) - 1);
|
|
940
938
|
return {
|
|
941
939
|
line: pos[0],
|
|
@@ -989,8 +987,8 @@ class LanguageService {
|
|
|
989
987
|
*/
|
|
990
988
|
async provideFoldingRanges(text) {
|
|
991
989
|
const root = await this.#queue(text), { length } = root.getLines(), ranges = [], levels = Array.from({ length: 6 }), tokens = root.querySelectorAll('heading-title,table,template,magic-word');
|
|
992
|
-
for (
|
|
993
|
-
|
|
990
|
+
for (let i = tokens.length - 1; i >= 0; i--) { // 提高 getBoundingClientRect 的性能
|
|
991
|
+
tokens[i].getRelativeIndex();
|
|
994
992
|
}
|
|
995
993
|
for (const token of tokens) {
|
|
996
994
|
const { offsetHeight } = token;
|
|
@@ -1146,6 +1144,37 @@ class LanguageService {
|
|
|
1146
1144
|
})
|
|
1147
1145
|
.filter(link => link !== false);
|
|
1148
1146
|
}
|
|
1147
|
+
/**
|
|
1148
|
+
* Provide document highlights
|
|
1149
|
+
*
|
|
1150
|
+
* 提供文档高亮
|
|
1151
|
+
* @param text source Wikitext / 源代码
|
|
1152
|
+
* @param position position / 位置
|
|
1153
|
+
* @since v1.46.0
|
|
1154
|
+
*/
|
|
1155
|
+
async provideDocumentHighlights(text, position) {
|
|
1156
|
+
const root = await this.#queue(text), index = root.indexFromPos(position.line, position.character), node = root.elementFromIndex(index), type = node?.type;
|
|
1157
|
+
if (!node || (type === 'ext' || type === 'html') && !/\w/u.test(text.charAt(index))) {
|
|
1158
|
+
return undefined;
|
|
1159
|
+
}
|
|
1160
|
+
return getMatchingTokens(root, node, highlightTypes)?.map((token) => {
|
|
1161
|
+
const range = createNodeRange(token);
|
|
1162
|
+
if (type === 'ext' || type === 'html') {
|
|
1163
|
+
const { start } = range;
|
|
1164
|
+
start.character += token.closing ? 2 : 1;
|
|
1165
|
+
return {
|
|
1166
|
+
range: {
|
|
1167
|
+
start,
|
|
1168
|
+
end: {
|
|
1169
|
+
line: start.line,
|
|
1170
|
+
character: start.character + token.name.length,
|
|
1171
|
+
},
|
|
1172
|
+
},
|
|
1173
|
+
};
|
|
1174
|
+
}
|
|
1175
|
+
return { range };
|
|
1176
|
+
});
|
|
1177
|
+
}
|
|
1149
1178
|
/**
|
|
1150
1179
|
* Provide references
|
|
1151
1180
|
*
|
|
@@ -1156,16 +1185,19 @@ class LanguageService {
|
|
|
1156
1185
|
async provideReferences(text, position) {
|
|
1157
1186
|
const root = await this.#queue(text), { offsetNode, offset } = caretPositionFromWord(root, this.#text, position), element = offsetNode.type === 'text' ? offsetNode.parentNode : offsetNode, node = offset === 0 && (element.is('ext-attr-dirty') || element.is('html-attr-dirty'))
|
|
1158
1187
|
? element.parentNode.parentNode
|
|
1159
|
-
: element
|
|
1160
|
-
|
|
1161
|
-
return undefined;
|
|
1162
|
-
}
|
|
1163
|
-
const name = getName(node), refs = root.querySelectorAll(type === 'heading-title' ? 'heading' : type).filter(token => type === 'attr-value'
|
|
1164
|
-
? getRefName(token) === refName || getRefGroup(token) === refGroup
|
|
1165
|
-
: getName(token) === name).reverse().map((token) => ({
|
|
1188
|
+
: element;
|
|
1189
|
+
return getMatchingTokens(root, node, referenceTypes)?.map((token) => ({
|
|
1166
1190
|
range: createNodeRange(token.type === 'parameter-key' ? token.parentNode : token),
|
|
1167
1191
|
}));
|
|
1168
|
-
|
|
1192
|
+
}
|
|
1193
|
+
/**
|
|
1194
|
+
* 获取根节点和当前节点
|
|
1195
|
+
* @param text 源代码
|
|
1196
|
+
* @param position 位置
|
|
1197
|
+
*/
|
|
1198
|
+
async #getRootAndNode(text, position) {
|
|
1199
|
+
const root = await this.#queue(text), node = root.elementFromPoint(position.character, position.line);
|
|
1200
|
+
return [root, node];
|
|
1169
1201
|
}
|
|
1170
1202
|
/**
|
|
1171
1203
|
* Provide definitions
|
|
@@ -1175,7 +1207,7 @@ class LanguageService {
|
|
|
1175
1207
|
* @param position position / 位置
|
|
1176
1208
|
*/
|
|
1177
1209
|
async provideDefinition(text, position) {
|
|
1178
|
-
const root = await this.#
|
|
1210
|
+
const [root, node] = await this.#getRootAndNode(text, position);
|
|
1179
1211
|
if (!node) {
|
|
1180
1212
|
return undefined;
|
|
1181
1213
|
}
|
|
@@ -1200,7 +1232,7 @@ class LanguageService {
|
|
|
1200
1232
|
* @param position position / 位置
|
|
1201
1233
|
*/
|
|
1202
1234
|
async resolveRenameLocation(text, position) {
|
|
1203
|
-
const
|
|
1235
|
+
const [, node] = await this.#getRootAndNode(text, position);
|
|
1204
1236
|
if (!node) {
|
|
1205
1237
|
return undefined;
|
|
1206
1238
|
}
|
|
@@ -1220,12 +1252,12 @@ class LanguageService {
|
|
|
1220
1252
|
* @param newName new name / 新名称
|
|
1221
1253
|
*/
|
|
1222
1254
|
async provideRenameEdits(text, position, newName) {
|
|
1223
|
-
const root = await this.#
|
|
1255
|
+
const [root, node] = await this.#getRootAndNode(text, position);
|
|
1224
1256
|
if (!node) {
|
|
1225
1257
|
return undefined;
|
|
1226
1258
|
}
|
|
1227
1259
|
const { type } = node, refName = getRefName(node), refNameGroup = refName && node.parentNode.parentNode.getAttr('group'), refGroup = getRefGroup(node), name = getName(node), refs = root.querySelectorAll(type).filter(token => {
|
|
1228
|
-
const
|
|
1260
|
+
const t = token.parentNode.type;
|
|
1229
1261
|
if (type === 'link-target' && t !== 'link' && t !== 'redirect-target') {
|
|
1230
1262
|
return false;
|
|
1231
1263
|
}
|
|
@@ -1415,10 +1447,10 @@ class LanguageService {
|
|
|
1415
1447
|
* @since v1.16.3
|
|
1416
1448
|
*/
|
|
1417
1449
|
async provideInlayHints(text) {
|
|
1418
|
-
const root = await this.#queue(text);
|
|
1450
|
+
const root = await this.#queue(text), templates = root.querySelectorAll('template,magic-word#invoke');
|
|
1419
1451
|
let hints = [];
|
|
1420
|
-
for (
|
|
1421
|
-
const { type, childNodes } =
|
|
1452
|
+
for (let i = templates.length - 1; i >= 0; i--) {
|
|
1453
|
+
const { type, childNodes } = templates[i];
|
|
1422
1454
|
hints = [
|
|
1423
1455
|
...hints,
|
|
1424
1456
|
...childNodes.slice(type === 'template' ? 1 : 3).filter(({ anon }) => anon)
|
package/dist/lib/node.js
CHANGED
|
@@ -40,7 +40,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
40
40
|
exports.AstNode = void 0;
|
|
41
41
|
/* eslint-disable @typescript-eslint/no-base-to-string */
|
|
42
42
|
const common_1 = require("@bhsd/common");
|
|
43
|
-
const search_1 = __importDefault(require("../
|
|
43
|
+
const search_1 = __importDefault(require("../vendor/search"));
|
|
44
44
|
const lint_1 = require("../util/lint");
|
|
45
45
|
const debug_1 = require("../util/debug");
|
|
46
46
|
const cached_1 = require("../mixin/cached");
|
|
@@ -145,7 +145,7 @@ let AstNode = (() => {
|
|
|
145
145
|
* @param left column number / 列号
|
|
146
146
|
*/
|
|
147
147
|
indexFromPos(top, left) {
|
|
148
|
-
|
|
148
|
+
LSP: {
|
|
149
149
|
if (top < 0 || left < 0) {
|
|
150
150
|
return undefined;
|
|
151
151
|
}
|
package/dist/lib/text.js
CHANGED
|
@@ -16,7 +16,7 @@ const errorSyntaxUrl = /* #__PURE__ */ new RegExp(source, 'giu'), noLinkTypes =
|
|
|
16
16
|
'{': /[{}]/u,
|
|
17
17
|
']': /[[\]](?=[^[\]]*$)/u,
|
|
18
18
|
'}': /[{}](?=[^{}]*$)/u,
|
|
19
|
-
}, disallowedTags = new Set([
|
|
19
|
+
}, magic = new Set(['rfc', 'pmid', 'isbn']), disallowedTags = new Set([
|
|
20
20
|
'html',
|
|
21
21
|
'head',
|
|
22
22
|
'style',
|
|
@@ -136,7 +136,7 @@ class AstText extends node_1.AstNode {
|
|
|
136
136
|
error = error.slice(1);
|
|
137
137
|
}
|
|
138
138
|
error = error.toLowerCase();
|
|
139
|
-
const [char] = error, magicLink = error
|
|
139
|
+
const [char] = error, magicLink = magic.has(error), lbrace = char === '{', rbrace = char === '}', lbrack = char === '[', rbrack = char === ']';
|
|
140
140
|
let { length } = error;
|
|
141
141
|
if (rbrack && (index || length > 1)) {
|
|
142
142
|
errorRegex.lastIndex--;
|
package/dist/map.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { RedirectToken, RedirectTargetToken, OnlyincludeToken, IncludeToken, CommentToken, ExtToken, AttributesToken, AttributeToken, AtomToken, ArgToken, TranscludeToken, SyntaxToken, ParameterToken, HeadingToken, HtmlToken, TableToken, TrToken, TdToken, DoubleUnderscoreToken, HrToken, LinkToken, CategoryToken, FileToken, ImageParameterToken, QuoteToken, ExtLinkToken, MagicLinkToken, ListToken, DdToken, ConverterToken, ConverterFlagsToken, ConverterRuleToken, TranslateToken, TvarToken, HiddenToken, GalleryImageToken, ParamLineToken, ImagemapLinkToken } from './internal';
|
|
1
|
+
import type { RedirectToken, RedirectTargetToken, OnlyincludeToken, IncludeToken, CommentToken, ExtToken, AttributesToken, AttributeToken, AtomToken, ArgToken, TranscludeToken, SyntaxToken, ParameterToken, HeadingToken, HtmlToken, TableToken, TrToken, TdToken, DoubleUnderscoreToken, HrToken, LinkToken, CategoryToken, FileToken, ImageParameterToken, QuoteToken, ExtLinkToken, MagicLinkToken, ListToken, DdToken, ConverterToken, ConverterFlagsToken, ConverterRuleToken, TranslateToken, TvarToken, HiddenToken, GalleryImageToken, ParamLineToken, ImagemapLinkToken, CharinsertLineToken } from './internal';
|
|
2
2
|
export interface TokenTypeMap {
|
|
3
3
|
redirect: RedirectToken;
|
|
4
4
|
'redirect-syntax': SyntaxToken;
|
|
@@ -60,6 +60,9 @@ export interface TokenTypeMap {
|
|
|
60
60
|
'converter-rule': ConverterRuleToken;
|
|
61
61
|
'converter-rule-variant': AtomToken;
|
|
62
62
|
'param-line': ParamLineToken;
|
|
63
|
+
'param-line-key': AtomToken;
|
|
64
|
+
'param-line-value': AtomToken;
|
|
63
65
|
'imagemap-link': ImagemapLinkToken;
|
|
66
|
+
'charinsert-line': CharinsertLineToken;
|
|
64
67
|
}
|
|
65
68
|
export type SelectedTokenTypes = keyof TokenTypeMap;
|
|
@@ -5,23 +5,23 @@ const debug_1 = require("../util/debug");
|
|
|
5
5
|
const selector_1 = require("../util/selector");
|
|
6
6
|
/** @ignore */
|
|
7
7
|
const elementLike = (constructor) => {
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
8
|
+
LINT: {
|
|
9
|
+
class ElementLike extends constructor {
|
|
10
|
+
#getCondition(selector) {
|
|
11
|
+
return (0, selector_1.getCondition)(selector, this);
|
|
12
|
+
}
|
|
13
|
+
closest(selector) {
|
|
14
|
+
const condition = this.#getCondition(selector);
|
|
15
|
+
let { parentNode } = this;
|
|
16
|
+
while (parentNode) {
|
|
17
|
+
if (condition(parentNode)) {
|
|
18
|
+
return parentNode;
|
|
19
|
+
}
|
|
20
|
+
({ parentNode } = parentNode);
|
|
18
21
|
}
|
|
19
|
-
|
|
22
|
+
return undefined;
|
|
20
23
|
}
|
|
21
|
-
|
|
22
|
-
}
|
|
23
|
-
getElementBy(condition) {
|
|
24
|
-
LINT: {
|
|
24
|
+
getElementBy(condition) {
|
|
25
25
|
const stack = [...this.childNodes].reverse();
|
|
26
26
|
while (stack.length > 0) {
|
|
27
27
|
const child = stack.pop(), { type, childNodes } = child;
|
|
@@ -37,12 +37,10 @@ const elementLike = (constructor) => {
|
|
|
37
37
|
}
|
|
38
38
|
return undefined;
|
|
39
39
|
}
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
getElementsBy(condition) {
|
|
45
|
-
LINT: {
|
|
40
|
+
querySelector(selector) {
|
|
41
|
+
return this.getElementBy(this.#getCondition(selector));
|
|
42
|
+
}
|
|
43
|
+
getElementsBy(condition) {
|
|
46
44
|
const stack = [...this.childNodes].reverse(), descendants = [];
|
|
47
45
|
while (stack.length > 0) {
|
|
48
46
|
const child = stack.pop(), { type, childNodes } = child;
|
|
@@ -58,19 +56,19 @@ const elementLike = (constructor) => {
|
|
|
58
56
|
}
|
|
59
57
|
return descendants;
|
|
60
58
|
}
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
59
|
+
querySelectorAll(selector) {
|
|
60
|
+
return this.getElementsBy(this.#getCondition(selector));
|
|
61
|
+
}
|
|
62
|
+
escape() {
|
|
63
|
+
LSP: {
|
|
64
|
+
for (const child of this.childNodes) {
|
|
65
|
+
child.escape();
|
|
66
|
+
}
|
|
69
67
|
}
|
|
70
68
|
}
|
|
71
69
|
}
|
|
70
|
+
(0, debug_1.mixin)(ElementLike, constructor);
|
|
71
|
+
return ElementLike;
|
|
72
72
|
}
|
|
73
|
-
(0, debug_1.mixin)(ElementLike, constructor);
|
|
74
|
-
return ElementLike;
|
|
75
73
|
};
|
|
76
74
|
exports.elementLike = elementLike;
|
package/dist/mixin/hidden.js
CHANGED
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import { ParamLineToken } from '../src/paramLine';
|
|
2
|
+
export interface ParamLineParentBase {
|
|
3
|
+
/**
|
|
4
|
+
* Get all parameter keys
|
|
5
|
+
*
|
|
6
|
+
* 获取所有参数键
|
|
7
|
+
* @since v1.45.0
|
|
8
|
+
*/
|
|
9
|
+
getKeys(): Set<string>;
|
|
10
|
+
/**
|
|
11
|
+
* Get parameters with the specified key
|
|
12
|
+
*
|
|
13
|
+
* 获取指定参数
|
|
14
|
+
* @param key parameter key / 参数键
|
|
15
|
+
* @since v1.45.0
|
|
16
|
+
*/
|
|
17
|
+
getParams(key: string): ParamLineToken[];
|
|
18
|
+
/**
|
|
19
|
+
* Get duplicated parameters
|
|
20
|
+
*
|
|
21
|
+
* 获取重复参数
|
|
22
|
+
* @since v1.45.0
|
|
23
|
+
*/
|
|
24
|
+
getDuplicatedParams(): [string, ParamLineToken[]][];
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* 子节点为ParamLineToken的类
|
|
28
|
+
* @ignore
|
|
29
|
+
*/
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.paramLineParent = void 0;
|
|
7
|
+
const debug_1 = require("../util/debug");
|
|
8
|
+
const lint_1 = require("../util/lint");
|
|
9
|
+
const rect_1 = require("../lib/rect");
|
|
10
|
+
const index_1 = __importDefault(require("../index"));
|
|
11
|
+
/**
|
|
12
|
+
* 子节点为ParamLineToken的类
|
|
13
|
+
* @ignore
|
|
14
|
+
*/
|
|
15
|
+
const paramLineParent = (constructor) => {
|
|
16
|
+
LINT: {
|
|
17
|
+
class ParamLineParent extends constructor {
|
|
18
|
+
getKeys() {
|
|
19
|
+
return new Set(this.childNodes.map(({ key }) => key).filter((key) => key !== undefined));
|
|
20
|
+
}
|
|
21
|
+
getParams(key) {
|
|
22
|
+
return this.childNodes.filter(({ key: k }) => k === key);
|
|
23
|
+
}
|
|
24
|
+
getDuplicatedParams() {
|
|
25
|
+
return [...this.getKeys()].map((key) => [key, this.getParams(key)])
|
|
26
|
+
.filter(([, { length }]) => length > 1);
|
|
27
|
+
}
|
|
28
|
+
lint(start = this.getAbsoluteIndex()) {
|
|
29
|
+
const errors = super.lint(start), { name, firstChild } = this, rule = 'no-duplicate', { lintConfig } = index_1.default, s = lintConfig.getSeverity(rule, name);
|
|
30
|
+
if (s) {
|
|
31
|
+
const msg = index_1.default.msg('duplicate-ext-parameter', name), rect = new rect_1.BoundingRect(this, start), { computeEditInfo } = lintConfig;
|
|
32
|
+
for (const [, params] of this.getDuplicatedParams()) {
|
|
33
|
+
const { length } = params, duplication = Array.from({ length });
|
|
34
|
+
for (let i = length - 1; i >= 0; i--) {
|
|
35
|
+
const param = params[i], e = (0, lint_1.generateForChild)(param, rect, rule, msg, s);
|
|
36
|
+
if (computeEditInfo) {
|
|
37
|
+
e.suggestions = [(0, lint_1.fixByRemove)(e, param === firstChild ? 0 : -1)];
|
|
38
|
+
}
|
|
39
|
+
duplication[i] = e;
|
|
40
|
+
}
|
|
41
|
+
Array.prototype.push.apply(errors, duplication);
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
return errors;
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
(0, debug_1.mixin)(ParamLineParent, constructor);
|
|
48
|
+
return ParamLineParent;
|
|
49
|
+
}
|
|
50
|
+
};
|
|
51
|
+
exports.paramLineParent = paramLineParent;
|
package/dist/src/arg.js
CHANGED
|
@@ -38,7 +38,6 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
38
38
|
};
|
|
39
39
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
40
40
|
exports.ArgToken = void 0;
|
|
41
|
-
const string_1 = require("../util/string");
|
|
42
41
|
const lint_1 = require("../util/lint");
|
|
43
42
|
const rect_1 = require("../lib/rect");
|
|
44
43
|
const padded_1 = require("../mixin/padded");
|
|
@@ -99,11 +98,17 @@ let ArgToken = (() => {
|
|
|
99
98
|
}
|
|
100
99
|
/** @private */
|
|
101
100
|
text() {
|
|
102
|
-
|
|
101
|
+
// eslint-disable-next-line @typescript-eslint/no-useless-default-assignment
|
|
102
|
+
const { length, childNodes, name = this.#getName() } = this;
|
|
103
|
+
return length === 1 ? `{{{${name}}}}` : `{{{${name}|${childNodes[1].text()}}}}`;
|
|
104
|
+
}
|
|
105
|
+
/** 获取name */
|
|
106
|
+
#getName() {
|
|
107
|
+
return this.firstChild.text().trim();
|
|
103
108
|
}
|
|
104
109
|
/** 更新name */
|
|
105
110
|
#setName() {
|
|
106
|
-
LSP: this.setAttribute('name', this
|
|
111
|
+
LSP: this.setAttribute('name', this.#getName());
|
|
107
112
|
}
|
|
108
113
|
/** @private */
|
|
109
114
|
afterBuild() {
|
|
@@ -113,44 +118,21 @@ let ArgToken = (() => {
|
|
|
113
118
|
/** @private */
|
|
114
119
|
lint(start = this.getAbsoluteIndex(), re) {
|
|
115
120
|
LINT: {
|
|
116
|
-
const
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
argDefault.setAttribute('aIndex', index);
|
|
122
|
-
const childErrors = argDefault.lint(index, re);
|
|
123
|
-
if (childErrors.length > 0) {
|
|
124
|
-
Array.prototype.push.apply(errors, childErrors);
|
|
125
|
-
}
|
|
126
|
-
}
|
|
127
|
-
const rules = ['no-ignored', 'no-arg'], { lintConfig } = index_1.default, { computeEditInfo } = lintConfig, rect = new rect_1.BoundingRect(this, start), s = rules.map(rule => lintConfig.getSeverity(rule, 'arg'));
|
|
128
|
-
if (s[0] && rest.length > 0) {
|
|
129
|
-
Array.prototype.push.apply(errors, rest.map(child => {
|
|
130
|
-
const e = (0, lint_1.generateForChild)(child, rect, rules[0], 'invisible-triple-braces', s[0]);
|
|
131
|
-
e.startIndex--;
|
|
132
|
-
e.startCol--;
|
|
133
|
-
if (computeEditInfo) {
|
|
134
|
-
e.suggestions = [
|
|
135
|
-
(0, lint_1.fixByRemove)(e),
|
|
136
|
-
(0, lint_1.fixByEscape)(e.startIndex, '{{!}}'),
|
|
137
|
-
];
|
|
138
|
-
}
|
|
139
|
-
return e;
|
|
140
|
-
}));
|
|
141
|
-
}
|
|
142
|
-
if (s[1] && !this.getAttribute('include')) {
|
|
143
|
-
const e = (0, lint_1.generateForSelf)(this, rect, rules[1], 'unexpected-argument', s[1]);
|
|
144
|
-
if (computeEditInfo && argDefault) {
|
|
121
|
+
const errors = super.lint(start, re), { lintConfig } = index_1.default, rect = new rect_1.BoundingRect(this, start);
|
|
122
|
+
let rule = 'no-arg', s = lintConfig.getSeverity(rule);
|
|
123
|
+
if (s && !this.getAttribute('include')) {
|
|
124
|
+
const e = (0, lint_1.generateForSelf)(this, rect, rule, 'unexpected-argument', s), [, argDefault] = this.childNodes;
|
|
125
|
+
if (lintConfig.computeEditInfo && argDefault) {
|
|
145
126
|
e.suggestions = [(0, lint_1.fixBy)(e, 'expand', argDefault.text())];
|
|
146
127
|
}
|
|
147
128
|
errors.push(e);
|
|
148
129
|
}
|
|
149
130
|
const ext = this.closest('ext');
|
|
150
131
|
if (ext) {
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
132
|
+
rule = 'arg-in-ext';
|
|
133
|
+
s = lintConfig.getSeverity(rule, ext.name);
|
|
134
|
+
if (s) {
|
|
135
|
+
errors.push((0, lint_1.generateForSelf)(this, rect, rule, 'argument-in-ext', s));
|
|
154
136
|
}
|
|
155
137
|
}
|
|
156
138
|
return errors;
|
package/dist/src/atom.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { Token } from './index';
|
|
2
2
|
import type { Config } from '../base';
|
|
3
|
-
declare const atomTypes: readonly ["arg-name", "attr-key", "attr-value", "ext-attr-dirty", "html-attr-dirty", "table-attr-dirty", "converter-flag", "converter-rule-variant", "invoke-function", "invoke-module", "template-name", "link-target"];
|
|
3
|
+
declare const atomTypes: readonly ["arg-name", "attr-key", "attr-value", "ext-attr-dirty", "html-attr-dirty", "table-attr-dirty", "converter-flag", "converter-rule-variant", "invoke-function", "invoke-module", "template-name", "link-target", "param-line-key", "param-line-value"];
|
|
4
4
|
declare type AtomTypes = typeof atomTypes[number];
|
|
5
5
|
/**
|
|
6
6
|
* plain Token that will not be parsed further
|