wikiparser-node 1.21.2 → 1.22.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.
Files changed (97) hide show
  1. package/README.md +9 -5
  2. package/bundle/bundle-es8.min.js +25 -25
  3. package/bundle/bundle-lsp.min.js +26 -26
  4. package/bundle/bundle.min.js +25 -25
  5. package/config/default.json +15 -11
  6. package/config/enwiki.json +1 -1
  7. package/config/jawiki.json +1 -1
  8. package/config/minimum.json +2 -3
  9. package/config/moegirl.json +152 -15
  10. package/config/zhwiki.json +1 -1
  11. package/dist/addon/token.js +3 -0
  12. package/dist/base.d.mts +16 -9
  13. package/dist/base.d.ts +16 -9
  14. package/dist/bin/config.js +23 -11
  15. package/dist/index.d.ts +33 -4
  16. package/dist/index.js +37 -2
  17. package/dist/lib/element.d.ts +4 -4
  18. package/dist/lib/element.js +6 -5
  19. package/dist/lib/lintConfig.d.ts +13 -0
  20. package/dist/lib/lintConfig.js +278 -0
  21. package/dist/lib/lsp.d.ts +7 -7
  22. package/dist/lib/lsp.js +18 -20
  23. package/dist/lib/node.d.ts +1 -1
  24. package/dist/lib/node.js +646 -606
  25. package/dist/lib/range.d.ts +2 -2
  26. package/dist/lib/range.js +2 -2
  27. package/dist/lib/text.js +76 -62
  28. package/dist/lib/title.d.ts +11 -4
  29. package/dist/lib/title.js +16 -6
  30. package/dist/mixin/attributesParent.d.ts +6 -6
  31. package/dist/mixin/attributesParent.js +4 -4
  32. package/dist/mixin/cached.d.ts +5 -0
  33. package/dist/mixin/cached.js +22 -0
  34. package/dist/mixin/clone.d.ts +5 -0
  35. package/dist/mixin/clone.js +23 -0
  36. package/dist/mixin/hidden.js +68 -18
  37. package/dist/mixin/sol.js +1 -1
  38. package/dist/parser/commentAndExt.js +6 -4
  39. package/dist/parser/converter.js +1 -1
  40. package/dist/parser/html.js +3 -3
  41. package/dist/parser/table.js +2 -2
  42. package/dist/src/arg.js +24 -17
  43. package/dist/src/atom.js +76 -31
  44. package/dist/src/attribute.js +79 -39
  45. package/dist/src/attributes.d.ts +7 -7
  46. package/dist/src/attributes.js +417 -366
  47. package/dist/src/commented.js +81 -35
  48. package/dist/src/converter.js +13 -7
  49. package/dist/src/converterFlags.js +33 -22
  50. package/dist/src/converterRule.js +263 -216
  51. package/dist/src/extLink.js +21 -16
  52. package/dist/src/gallery.js +44 -27
  53. package/dist/src/heading.js +48 -43
  54. package/dist/src/hidden.js +14 -9
  55. package/dist/src/html.js +92 -60
  56. package/dist/src/imageParameter.js +13 -6
  57. package/dist/src/imagemap.js +32 -25
  58. package/dist/src/index.d.ts +2 -2
  59. package/dist/src/index.js +61 -50
  60. package/dist/src/link/base.d.ts +1 -1
  61. package/dist/src/link/base.js +35 -23
  62. package/dist/src/link/file.js +409 -354
  63. package/dist/src/link/galleryImage.js +9 -5
  64. package/dist/src/link/index.d.ts +1 -1
  65. package/dist/src/link/index.js +8 -4
  66. package/dist/src/link/redirectTarget.js +7 -3
  67. package/dist/src/magicLink.js +39 -26
  68. package/dist/src/nested.js +122 -74
  69. package/dist/src/nowiki/base.js +5 -2
  70. package/dist/src/nowiki/comment.js +5 -1
  71. package/dist/src/nowiki/index.js +4 -4
  72. package/dist/src/nowiki/quote.js +32 -46
  73. package/dist/src/onlyinclude.js +17 -9
  74. package/dist/src/paramTag/index.js +21 -14
  75. package/dist/src/parameter.js +26 -20
  76. package/dist/src/pre.js +91 -45
  77. package/dist/src/syntax.js +14 -10
  78. package/dist/src/table/index.js +554 -501
  79. package/dist/src/table/td.d.ts +1 -1
  80. package/dist/src/table/td.js +91 -82
  81. package/dist/src/table/trBase.js +183 -130
  82. package/dist/src/tagPair/ext.js +38 -23
  83. package/dist/src/tagPair/include.js +5 -5
  84. package/dist/src/tagPair/index.js +2 -3
  85. package/dist/src/tagPair/translate.js +150 -103
  86. package/dist/src/transclude.d.ts +15 -1
  87. package/dist/src/transclude.js +56 -21
  88. package/dist/util/html.js +46 -41
  89. package/dist/util/lint.js +7 -9
  90. package/dist/util/sharable.js +1 -1
  91. package/dist/util/sharable.mjs +2 -2
  92. package/dist/util/string.js +13 -7
  93. package/extensions/dist/base.js +9 -2
  94. package/extensions/typings.d.ts +2 -1
  95. package/i18n/zh-hans.json +1 -1
  96. package/i18n/zh-hant.json +1 -1
  97. package/package.json +20 -15
@@ -1,4 +1,11 @@
1
1
  "use strict";
2
+ var __runInitializers = (this && this.__runInitializers) || function (thisArg, initializers, value) {
3
+ var useValue = arguments.length > 2;
4
+ for (var i = 0; i < initializers.length; i++) {
5
+ value = useValue ? initializers[i].call(thisArg, value) : initializers[i].call(thisArg);
6
+ }
7
+ return useValue ? value : void 0;
8
+ };
2
9
  var __esDecorate = (this && this.__esDecorate) || function (ctor, descriptorIn, decorators, contextIn, initializers, extraInitializers) {
3
10
  function accept(f) { if (f !== void 0 && typeof f !== "function") throw new TypeError("Function expected"); return f; }
4
11
  var kind = contextIn.kind, key = kind === "getter" ? "get" : kind === "setter" ? "set" : "value";
@@ -26,13 +33,6 @@ var __esDecorate = (this && this.__esDecorate) || function (ctor, descriptorIn,
26
33
  if (target) Object.defineProperty(target, contextIn.name, descriptor);
27
34
  done = true;
28
35
  };
29
- var __runInitializers = (this && this.__runInitializers) || function (thisArg, initializers, value) {
30
- var useValue = arguments.length > 2;
31
- for (var i = 0; i < initializers.length; i++) {
32
- value = useValue ? initializers[i].call(thisArg, value) : initializers[i].call(thisArg);
33
- }
34
- return useValue ? value : void 0;
35
- };
36
36
  var __importDefault = (this && this.__importDefault) || function (mod) {
37
37
  return (mod && mod.__esModule) ? mod : { "default": mod };
38
38
  };
@@ -49,6 +49,7 @@ const attributes_1 = require("../attributes");
49
49
  const debug_1 = require("../../util/debug");
50
50
  const constants_1 = require("../../util/constants");
51
51
  const string_1 = require("../../util/string");
52
+ const cached_1 = require("../../mixin/cached");
52
53
  /**
53
54
  * extension tag
54
55
  *
@@ -61,10 +62,14 @@ let ExtToken = (() => {
61
62
  let _classExtraInitializers = [];
62
63
  let _classThis;
63
64
  let _classSuper = index_3.TagPairToken;
65
+ let _instanceExtraInitializers = [];
66
+ let _toHtmlInternal_decorators;
64
67
  var ExtToken = class extends _classSuper {
65
68
  static { _classThis = this; }
66
69
  static {
67
70
  const _metadata = typeof Symbol === "function" && Symbol.metadata ? Object.create(_classSuper[Symbol.metadata] ?? null) : void 0;
71
+ _toHtmlInternal_decorators = [(0, cached_1.cached)()];
72
+ __esDecorate(this, null, _toHtmlInternal_decorators, { kind: "method", name: "toHtmlInternal", static: false, private: false, access: { has: obj => "toHtmlInternal" in obj, get: obj => obj.toHtmlInternal }, metadata: _metadata }, null, _instanceExtraInitializers);
68
73
  __esDecorate(null, _classDescriptor = { value: _classThis }, _classDecorators, { kind: "class", name: _classThis.name, metadata: _metadata }, null, _classExtraInitializers);
69
74
  ExtToken = _classThis = _classDescriptor.value;
70
75
  if (_metadata) Object.defineProperty(_classThis, Symbol.metadata, { enumerable: true, configurable: true, writable: true, value: _metadata });
@@ -186,6 +191,7 @@ let ExtToken = (() => {
186
191
  innerToken.type = 'ext-inner';
187
192
  }
188
193
  super(name, attrToken, innerToken, closed, config, accum);
194
+ __runInitializers(this, _instanceExtraInitializers);
189
195
  /* PRINT ONLY */
190
196
  this.seal('closed', true);
191
197
  }
@@ -193,13 +199,14 @@ let ExtToken = (() => {
193
199
  lint(start = this.getAbsoluteIndex(), re) {
194
200
  const errors = super.lint(start, re), rect = new rect_1.BoundingRect(this, start);
195
201
  if (this.name !== 'nowiki') {
196
- const s = this.inHtmlAttrs();
197
- if (s) {
198
- errors.push((0, lint_1.generateForSelf)(this, rect, 'parsing-order', 'extension tag in HTML tag attributes', s));
202
+ const s = this.inHtmlAttrs(), rule = 'parsing-order', severity = s && index_1.default.lintConfig.getSeverity(rule, s === 2 ? 'ext' : 'templateInTable');
203
+ if (severity) {
204
+ errors.push((0, lint_1.generateForSelf)(this, rect, rule, 'extension tag in HTML tag attributes', severity));
199
205
  }
200
206
  }
201
- if (this.name === 'ref' && this.closest('heading-title')) {
202
- errors.push((0, lint_1.generateForSelf)(this, rect, 'var-anchor', 'variable anchor in a section header'));
207
+ const rule = 'var-anchor', s = index_1.default.lintConfig.getSeverity(rule, 'ref');
208
+ if (s && this.name === 'ref' && this.closest('heading-title')) {
209
+ errors.push((0, lint_1.generateForSelf)(this, rect, rule, 'variable anchor in a section header', s));
203
210
  }
204
211
  return errors;
205
212
  }
@@ -216,21 +223,29 @@ let ExtToken = (() => {
216
223
  /** @private */
217
224
  toHtmlInternal(opt) {
218
225
  const { name, firstChild, lastChild } = this;
226
+ if (index_1.default.tagHooks.has(name)) {
227
+ return index_1.default.tagHooks.get(name)(this);
228
+ }
219
229
  switch (name) {
220
- case 'nowiki':
221
- return (0, string_1.newline)(lastChild.toHtmlInternal());
222
- case 'pre':
223
- return `<pre${firstChild.toHtmlInternal()}>${(0, string_1.newline)(lastChild.toHtmlInternal({
230
+ case 'nowiki': {
231
+ const html = lastChild.toHtmlInternal();
232
+ return this.closest('ext#poem') ? html : (0, string_1.newline)(html);
233
+ }
234
+ case 'pre': {
235
+ const html = lastChild.toHtmlInternal({
224
236
  ...opt,
225
237
  nowrap: false,
226
- }))}</pre>`;
227
- case 'poem':
238
+ });
239
+ return `<pre${firstChild.toHtmlInternal()}>${this.closest('ext#poem') ? html : (0, string_1.newline)(html)}</pre>`;
240
+ }
241
+ case 'poem': {
242
+ const padding = firstChild.hasAttr('compact') ? '' : '\n';
228
243
  firstChild.classList.add('poem');
229
- return `<div${firstChild.toHtmlInternal()}>${lastChild.toHtmlInternal({
230
- ...opt,
231
- nowrap: false,
232
- }).replace(/(?<!^|<hr>)\n(?!$)/gu, '<br>\n')
233
- .replace(/^ +/gmu, p => '&nbsp;'.repeat(p.length))}</div>`;
244
+ return `<div${firstChild.toHtmlInternal()}>${padding}${lastChild.toHtmlInternal({ ...opt, nowrap: false })
245
+ .replace(/(?<!^|<hr>)\n(?!$)/gu, '<br>\n')
246
+ .replace(/^ +/gmu, p => '&nbsp;'.repeat(p.length))
247
+ .trim()}${padding}</div>`;
248
+ }
234
249
  case 'gallery': {
235
250
  const caption = firstChild.getAttrToken('caption'), perrow = parseInt(String(firstChild.getAttr('perrow'))), mode = firstChild.getAttr('mode'), nolines = typeof mode === 'string' && mode.toLowerCase() === 'nolines', padding = nolines ? 9 : 43;
236
251
  firstChild.classList.add('gallery');
@@ -101,14 +101,14 @@ let IncludeToken = (() => {
101
101
  }
102
102
  /** @private */
103
103
  lint(start = this.getAbsoluteIndex()) {
104
- const errors = [], { firstChild, closed, name } = this, rect = new rect_1.BoundingRect(this, start);
105
- if (firstChild.data.trim()) {
106
- const e = (0, lint_1.generateForChild)(firstChild, rect, 'no-ignored', 'useless attribute', 'warning');
104
+ const errors = [], { firstChild, closed, name } = this, rect = new rect_1.BoundingRect(this, start), rules = ['no-ignored', 'unclosed-comment'], s = rules.map(rule => index_1.default.lintConfig.getSeverity(rule, 'include'));
105
+ if (s[0] && firstChild.data.trim()) {
106
+ const e = (0, lint_1.generateForChild)(firstChild, rect, rules[0], 'useless attribute', s[0]);
107
107
  e.suggestions = [{ desc: 'remove', range: [e.startIndex, e.endIndex], text: '' }];
108
108
  errors.push(e);
109
109
  }
110
- if (!closed) {
111
- const e = (0, lint_1.generateForSelf)(this, rect, 'unclosed-comment', index_1.default.msg('unclosed $1', `<${name}>`));
110
+ if (s[1] && !closed) {
111
+ const e = (0, lint_1.generateForSelf)(this, rect, rules[1], index_1.default.msg('unclosed $1', `<${name}>`), s[1]);
112
112
  e.suggestions = [{ desc: 'close', range: [e.endIndex, e.endIndex], text: `</${name}>` }];
113
113
  errors.push(e);
114
114
  }
@@ -69,7 +69,6 @@ let TagPairToken = (() => {
69
69
  #tags;
70
70
  closed;
71
71
  selfClosing;
72
- /* NOT FOR BROWSER END */
73
72
  /** inner wikitext / 内部wikitext */
74
73
  get innerText() {
75
74
  return this.selfClosing ? undefined : this.lastChild.text();
@@ -94,9 +93,9 @@ let TagPairToken = (() => {
94
93
  toString(skip) {
95
94
  const { selfClosing, firstChild, lastChild,
96
95
  /* NOT FOR BROWSER */
97
- nextSibling, name, closed, } = this, [opening, closing] = this.#tags;
96
+ nextSibling, name, closed, type, } = this, [opening, closing] = this.#tags;
98
97
  /* NOT FOR BROWSER */
99
- if (!closed && nextSibling) {
98
+ if (!closed && nextSibling && type === 'include') {
100
99
  index_2.default.error(`Auto-closing <${name}>`, lastChild);
101
100
  this.closed = true;
102
101
  }
@@ -1,4 +1,38 @@
1
1
  "use strict";
2
+ var __runInitializers = (this && this.__runInitializers) || function (thisArg, initializers, value) {
3
+ var useValue = arguments.length > 2;
4
+ for (var i = 0; i < initializers.length; i++) {
5
+ value = useValue ? initializers[i].call(thisArg, value) : initializers[i].call(thisArg);
6
+ }
7
+ return useValue ? value : void 0;
8
+ };
9
+ var __esDecorate = (this && this.__esDecorate) || function (ctor, descriptorIn, decorators, contextIn, initializers, extraInitializers) {
10
+ function accept(f) { if (f !== void 0 && typeof f !== "function") throw new TypeError("Function expected"); return f; }
11
+ var kind = contextIn.kind, key = kind === "getter" ? "get" : kind === "setter" ? "set" : "value";
12
+ var target = !descriptorIn && ctor ? contextIn["static"] ? ctor : ctor.prototype : null;
13
+ var descriptor = descriptorIn || (target ? Object.getOwnPropertyDescriptor(target, contextIn.name) : {});
14
+ var _, done = false;
15
+ for (var i = decorators.length - 1; i >= 0; i--) {
16
+ var context = {};
17
+ for (var p in contextIn) context[p] = p === "access" ? {} : contextIn[p];
18
+ for (var p in contextIn.access) context.access[p] = contextIn.access[p];
19
+ context.addInitializer = function (f) { if (done) throw new TypeError("Cannot add initializers after decoration has completed"); extraInitializers.push(accept(f || null)); };
20
+ var result = (0, decorators[i])(kind === "accessor" ? { get: descriptor.get, set: descriptor.set } : descriptor[key], context);
21
+ if (kind === "accessor") {
22
+ if (result === void 0) continue;
23
+ if (result === null || typeof result !== "object") throw new TypeError("Object expected");
24
+ if (_ = accept(result.get)) descriptor.get = _;
25
+ if (_ = accept(result.set)) descriptor.set = _;
26
+ if (_ = accept(result.init)) initializers.unshift(_);
27
+ }
28
+ else if (_ = accept(result)) {
29
+ if (kind === "field") initializers.unshift(_);
30
+ else descriptor[key] = _;
31
+ }
32
+ }
33
+ if (target) Object.defineProperty(target, contextIn.name, descriptor);
34
+ done = true;
35
+ };
2
36
  Object.defineProperty(exports, "__esModule", { value: true });
3
37
  exports.TranslateToken = void 0;
4
38
  const index_1 = require("../index");
@@ -9,121 +43,134 @@ const noinclude_1 = require("../nowiki/noinclude");
9
43
  const debug_1 = require("../../util/debug");
10
44
  const constants_1 = require("../../util/constants");
11
45
  const string_1 = require("../../util/string");
46
+ const cached_1 = require("../../mixin/cached");
12
47
  /* NOT FOR BROWSER END */
13
48
  /**
14
49
  * `<translate>`
15
50
  * @classdesc `{childNodes: [SyntaxToken, Token]}`
16
51
  */
17
- class TranslateToken extends index_2.TagPairToken {
18
- /* NOT FOR BROWSER END */
19
- get type() {
20
- return 'translate';
21
- }
22
- /**
23
- * @param attr 标签属性
24
- * @param inner 内部wikitext
25
- */
26
- constructor(attr, inner, config, accum = []) {
27
- const attrToken = new syntax_1.SyntaxToken(attr, /^(?: nowrap)?$/u, 'translate-attr', config, accum, { AstText: ':' });
28
- inner = inner?.replace(/(<tvar\|[^>]+>)([\s\S]*?)(<\/>)/gu, (_, p1, p2, p3) => {
29
- // @ts-expect-error abstract class
30
- new noinclude_1.NoincludeToken(p1, config, accum);
31
- // @ts-expect-error abstract class
32
- new noinclude_1.NoincludeToken(p3, config, accum);
33
- return `\0${accum.length - 1}n\x7F${p2}\0${accum.length}n\x7F`;
34
- }).replace(/(<tvar\s+name\s*=(?:\s*(?:(["'])[\s\S]*?\2|[^"'\s>]+))?\s*>)([\s\S]*?)(<\/tvar\s*>)/giu, (_, p1, __, p3, p4) => {
35
- // @ts-expect-error abstract class
36
- new noinclude_1.NoincludeToken(p1, config, accum);
37
- // @ts-expect-error abstract class
38
- new noinclude_1.NoincludeToken(p4, config, accum);
39
- return `\0${accum.length - 1}n\x7F${p3}\0${accum.length}n\x7F`;
40
- });
41
- const innerToken = new index_1.Token(inner, config, accum);
42
- innerToken.type = 'translate-inner';
43
- super('translate', attrToken, innerToken, 'translate', config, accum);
52
+ let TranslateToken = (() => {
53
+ let _classSuper = index_2.TagPairToken;
54
+ let _instanceExtraInitializers = [];
55
+ let _toHtmlInternal_decorators;
56
+ return class TranslateToken extends _classSuper {
57
+ static {
58
+ const _metadata = typeof Symbol === "function" && Symbol.metadata ? Object.create(_classSuper[Symbol.metadata] ?? null) : void 0;
59
+ _toHtmlInternal_decorators = [(0, cached_1.cached)()];
60
+ __esDecorate(this, null, _toHtmlInternal_decorators, { kind: "method", name: "toHtmlInternal", static: false, private: false, access: { has: obj => "toHtmlInternal" in obj, get: obj => obj.toHtmlInternal }, metadata: _metadata }, null, _instanceExtraInitializers);
61
+ if (_metadata) Object.defineProperty(this, Symbol.metadata, { enumerable: true, configurable: true, writable: true, value: _metadata });
62
+ }
63
+ /* NOT FOR BROWSER END */
64
+ get type() {
65
+ return 'translate';
66
+ }
67
+ /**
68
+ * @param attr 标签属性
69
+ * @param inner 内部wikitext
70
+ */
71
+ constructor(attr, inner, config, accum = []) {
72
+ const attrToken = new syntax_1.SyntaxToken(attr, /^(?: nowrap)?$/u, 'translate-attr', config, accum, { AstText: ':' });
73
+ inner = inner?.replace(/(<tvar\|[^>]+>)([\s\S]*?)(<\/>)/gu, (_, p1, p2, p3) => {
74
+ // @ts-expect-error abstract class
75
+ new noinclude_1.NoincludeToken(p1, config, accum);
76
+ // @ts-expect-error abstract class
77
+ new noinclude_1.NoincludeToken(p3, config, accum);
78
+ return `\0${accum.length - 1}n\x7F${p2}\0${accum.length}n\x7F`;
79
+ }).replace(/(<tvar\s+name\s*=(?:\s*(?:(["'])[\s\S]*?\2|[^"'\s>]+))?\s*>)([\s\S]*?)(<\/tvar\s*>)/giu, (_, p1, __, p3, p4) => {
80
+ // @ts-expect-error abstract class
81
+ new noinclude_1.NoincludeToken(p1, config, accum);
82
+ // @ts-expect-error abstract class
83
+ new noinclude_1.NoincludeToken(p4, config, accum);
84
+ return `\0${accum.length - 1}n\x7F${p3}\0${accum.length}n\x7F`;
85
+ });
86
+ const innerToken = new index_1.Token(inner, config, accum);
87
+ innerToken.type = 'translate-inner';
88
+ super('translate', attrToken, innerToken, 'translate', config, accum);
89
+ __runInitializers(this, _instanceExtraInitializers);
90
+ /* PRINT ONLY */
91
+ this.seal('closed', true);
92
+ this.seal('selfClosing', true);
93
+ }
94
+ /** @private */
95
+ toString(skip) {
96
+ return skip ? this.lastChild.toString(true) : super.toString();
97
+ }
98
+ /** @private */
99
+ text() {
100
+ return this.lastChild.text();
101
+ }
44
102
  /* PRINT ONLY */
45
- this.seal('closed', true);
46
- this.seal('selfClosing', true);
47
- }
48
- /** @private */
49
- toString(skip) {
50
- return skip ? this.lastChild.toString(true) : super.toString();
51
- }
52
- /** @private */
53
- text() {
54
- return this.lastChild.text();
55
- }
56
- /* PRINT ONLY */
57
- /** 是否有nowrap属性 */
58
- #isNowrap() {
59
- return this.firstChild.toString() === ' nowrap';
60
- }
61
- /** @private */
62
- print() {
63
- return `<span class="wpb-ext">&lt;translate${this.#isNowrap()
64
- ? '<span class="wpb-ext-attrs"> <span class="wpb-ext-attr">'
65
- + '<span class="wpb-attr-key">nowrap</span>'
66
- + '</span></span>'
67
- : ''}&gt;${this.lastChild.print({ class: 'ext-inner' })}&lt;/translate&gt;</span>`;
68
- }
69
- /* PRINT ONLY END */
70
- /* NOT FOR BROWSER */
71
- /**
72
- * 设置nowrap属性
73
- * @param nowrap 是否nowrap
74
- */
75
- #setNowrap(nowrap) {
76
- this.firstChild.setText(nowrap ? ' nowrap' : '');
77
- }
78
- /** @implements */
79
- getAttr(key) {
80
- return (0, string_1.trimLc)(key) === 'nowrap' && this.#isNowrap() || undefined;
81
- }
82
- /** @implements */
83
- hasAttr(key) {
84
- return (0, string_1.trimLc)(key) === 'nowrap' && this.#isNowrap();
85
- }
86
- /** @implements */
87
- setAttr(keyOrProp, value) {
88
- if (typeof keyOrProp === 'object') {
89
- for (const [key, val] of Object.entries(keyOrProp)) {
90
- this.setAttr(key, val);
103
+ /** 是否有nowrap属性 */
104
+ #isNowrap() {
105
+ return this.firstChild.toString() === ' nowrap';
106
+ }
107
+ /** @private */
108
+ print() {
109
+ return `<span class="wpb-ext">&lt;translate${this.#isNowrap()
110
+ ? '<span class="wpb-ext-attrs"> <span class="wpb-ext-attr">'
111
+ + '<span class="wpb-attr-key">nowrap</span>'
112
+ + '</span></span>'
113
+ : ''}&gt;${this.lastChild.print({ class: 'ext-inner' })}&lt;/translate&gt;</span>`;
114
+ }
115
+ /* PRINT ONLY END */
116
+ /* NOT FOR BROWSER */
117
+ /**
118
+ * 设置nowrap属性
119
+ * @param nowrap 是否nowrap
120
+ */
121
+ #setNowrap(nowrap) {
122
+ this.firstChild.setText(nowrap ? ' nowrap' : '');
123
+ }
124
+ /** @implements */
125
+ getAttr(key) {
126
+ return (0, string_1.trimLc)(key) === 'nowrap' && this.#isNowrap() || undefined;
127
+ }
128
+ /** @implements */
129
+ hasAttr(key) {
130
+ return (0, string_1.trimLc)(key) === 'nowrap' && this.#isNowrap();
131
+ }
132
+ /** @implements */
133
+ setAttr(keyOrProp, value) {
134
+ if (typeof keyOrProp === 'object') {
135
+ for (const [key, val] of Object.entries(keyOrProp)) {
136
+ this.setAttr(key, val);
137
+ }
138
+ }
139
+ else if ((0, string_1.trimLc)(keyOrProp) === 'nowrap') {
140
+ this.#setNowrap(value);
91
141
  }
92
142
  }
93
- else if ((0, string_1.trimLc)(keyOrProp) === 'nowrap') {
94
- this.#setNowrap(value);
143
+ /** @implements */
144
+ removeAttr(key) {
145
+ if ((0, string_1.trimLc)(key) === 'nowrap') {
146
+ this.firstChild.replaceChildren();
147
+ }
95
148
  }
96
- }
97
- /** @implements */
98
- removeAttr(key) {
99
- if ((0, string_1.trimLc)(key) === 'nowrap') {
100
- this.firstChild.replaceChildren();
149
+ /** @implements */
150
+ toggleAttr(key, force) {
151
+ if ((0, string_1.trimLc)(key) === 'nowrap') {
152
+ this.#setNowrap(force ?? !this.#isNowrap());
153
+ }
101
154
  }
102
- }
103
- /** @implements */
104
- toggleAttr(key, force) {
105
- if ((0, string_1.trimLc)(key) === 'nowrap') {
106
- this.#setNowrap(force ?? !this.#isNowrap());
155
+ cloneNode() {
156
+ const inner = this.lastChild.cloneNode(), config = this.getAttribute('config'), attr = this.firstChild.toString() || undefined;
157
+ return debug_1.Shadow.run(() => {
158
+ // @ts-expect-error abstract class
159
+ const token = new TranslateToken(attr, undefined, config);
160
+ token.lastChild.safeReplaceWith(inner);
161
+ return token;
162
+ });
107
163
  }
108
- }
109
- cloneNode() {
110
- const inner = this.lastChild.cloneNode(), config = this.getAttribute('config'), attr = this.firstChild.toString() || undefined;
111
- return debug_1.Shadow.run(() => {
112
- // @ts-expect-error abstract class
113
- const token = new TranslateToken(attr, undefined, config);
114
- token.lastChild.safeReplaceWith(inner);
115
- return token;
116
- });
117
- }
118
- /** @private */
119
- toHtmlInternal(opt) {
120
- for (const { innerText, nextSibling } of this.querySelectorAll('comment')) {
121
- if (nextSibling?.type === 'text' && /^T:[^_/\n<>~]+$/u.test(innerText) && /^[\n ]/u.test(nextSibling.data)) {
122
- nextSibling.deleteData(0, 1);
164
+ /** @private */
165
+ toHtmlInternal(opt) {
166
+ for (const { innerText, nextSibling } of this.querySelectorAll('comment')) {
167
+ if (nextSibling?.type === 'text' && /^T:[^_/\n<>~]+$/u.test(innerText) && /^[\n ]/u.test(nextSibling.data)) {
168
+ nextSibling.deleteData(0, 1);
169
+ }
123
170
  }
171
+ return this.lastChild.toHtmlInternal(opt);
124
172
  }
125
- return this.lastChild.toHtmlInternal(opt);
126
- }
127
- }
173
+ };
174
+ })();
128
175
  exports.TranslateToken = TranslateToken;
129
176
  constants_1.classes['TranslateToken'] = __filename;
@@ -3,6 +3,11 @@ import { ParameterToken } from './parameter';
3
3
  import { AtomToken } from './atom';
4
4
  import { SyntaxToken } from './syntax';
5
5
  import type { Config, LintError } from '../base';
6
+ declare interface Frame {
7
+ args: Record<string, string>;
8
+ parent?: Frame | undefined;
9
+ title: string;
10
+ }
6
11
  declare type Child = AtomToken | SyntaxToken;
7
12
  /**
8
13
  * template or magic word
@@ -236,7 +241,7 @@ export declare abstract class TranscludeToken extends Token {
236
241
  * 转义模板内的表格
237
242
  * @throws `Error` 转义失败
238
243
  */
239
- escapeTables(): TranscludeToken;
244
+ escapeTables(): this;
240
245
  /**
241
246
  * Get the module name and module function name
242
247
  *
@@ -245,5 +250,14 @@ export declare abstract class TranscludeToken extends Token {
245
250
  * @since v1.16.4
246
251
  */
247
252
  getModule(): [string, string | undefined];
253
+ /**
254
+ * Get the [frame object](https://www.mediawiki.org/wiki/Extension:Scribunto/Lua_reference_manual#frame-object)
255
+ *
256
+ * 获取 [frame 对象](https://www.mediawiki.org/wiki/Extension:Scribunto/Lua_reference_manual#frame-object)
257
+ * @param context template calling this module / 调用该模块的模板
258
+ * @throws `Error` 仅用于模块
259
+ * @since v1.22.0
260
+ */
261
+ getFrame(context?: this): Frame;
248
262
  }
249
263
  export {};
@@ -1,4 +1,11 @@
1
1
  "use strict";
2
+ var __runInitializers = (this && this.__runInitializers) || function (thisArg, initializers, value) {
3
+ var useValue = arguments.length > 2;
4
+ for (var i = 0; i < initializers.length; i++) {
5
+ value = useValue ? initializers[i].call(thisArg, value) : initializers[i].call(thisArg);
6
+ }
7
+ return useValue ? value : void 0;
8
+ };
2
9
  var __esDecorate = (this && this.__esDecorate) || function (ctor, descriptorIn, decorators, contextIn, initializers, extraInitializers) {
3
10
  function accept(f) { if (f !== void 0 && typeof f !== "function") throw new TypeError("Function expected"); return f; }
4
11
  var kind = contextIn.kind, key = kind === "getter" ? "get" : kind === "setter" ? "set" : "value";
@@ -26,13 +33,6 @@ var __esDecorate = (this && this.__esDecorate) || function (ctor, descriptorIn,
26
33
  if (target) Object.defineProperty(target, contextIn.name, descriptor);
27
34
  done = true;
28
35
  };
29
- var __runInitializers = (this && this.__runInitializers) || function (thisArg, initializers, value) {
30
- var useValue = arguments.length > 2;
31
- for (var i = 0; i < initializers.length; i++) {
32
- value = useValue ? initializers[i].call(thisArg, value) : initializers[i].call(thisArg);
33
- }
34
- return useValue ? value : void 0;
35
- };
36
36
  var __importDefault = (this && this.__importDefault) || function (mod) {
37
37
  return (mod && mod.__esModule) ? mod : { "default": mod };
38
38
  };
@@ -44,13 +44,14 @@ const debug_1 = require("../util/debug");
44
44
  const constants_1 = require("../util/constants");
45
45
  const rect_1 = require("../lib/rect");
46
46
  const gapped_1 = require("../mixin/gapped");
47
- const index_1 = require("./index");
47
+ const index_1 = __importDefault(require("../index"));
48
+ const index_2 = require("./index");
48
49
  const parameter_1 = require("./parameter");
49
50
  const atom_1 = require("./atom");
50
51
  const syntax_1 = require("./syntax");
51
52
  /* NOT FOR BROWSER */
52
53
  const noEscape_1 = require("../mixin/noEscape");
53
- const index_2 = __importDefault(require("../index"));
54
+ const cached_1 = require("../mixin/cached");
54
55
  const basicMagicWords = new Map([['=', '='], ['!', '|']]);
55
56
  /**
56
57
  * template or magic word
@@ -63,17 +64,21 @@ let TranscludeToken = (() => {
63
64
  let _classDescriptor;
64
65
  let _classExtraInitializers = [];
65
66
  let _classThis;
66
- let _classSuper = index_1.Token;
67
+ let _classSuper = index_2.Token;
68
+ let _instanceExtraInitializers = [];
69
+ let _toHtmlInternal_decorators;
67
70
  var TranscludeToken = class extends _classSuper {
68
71
  static { _classThis = this; }
69
72
  static {
70
73
  const _metadata = typeof Symbol === "function" && Symbol.metadata ? Object.create(_classSuper[Symbol.metadata] ?? null) : void 0;
74
+ _toHtmlInternal_decorators = [(0, cached_1.cached)()];
75
+ __esDecorate(this, null, _toHtmlInternal_decorators, { kind: "method", name: "toHtmlInternal", static: false, private: false, access: { has: obj => "toHtmlInternal" in obj, get: obj => obj.toHtmlInternal }, metadata: _metadata }, null, _instanceExtraInitializers);
71
76
  __esDecorate(null, _classDescriptor = { value: _classThis }, _classDecorators, { kind: "class", name: _classThis.name, metadata: _metadata }, null, _classExtraInitializers);
72
77
  TranscludeToken = _classThis = _classDescriptor.value;
73
78
  if (_metadata) Object.defineProperty(_classThis, Symbol.metadata, { enumerable: true, configurable: true, writable: true, value: _metadata });
74
79
  __runInitializers(_classThis, _classExtraInitializers);
75
80
  }
76
- modifier = '';
81
+ modifier = (__runInitializers(this, _instanceExtraInitializers), '');
77
82
  #type = 'template';
78
83
  #colon = ':';
79
84
  #raw = false;
@@ -187,7 +192,7 @@ let TranscludeToken = (() => {
187
192
  if (!this.normalizeTitle(name, 10, { halfParsed: true, temporary: true }).valid) {
188
193
  accum.pop();
189
194
  /* NOT FOR BROWSER */
190
- index_2.default.debug(`Invalid template name: ${(0, string_1.noWrap)(name)}`);
195
+ index_1.default.debug(`Invalid template name: ${(0, string_1.noWrap)(name)}`);
191
196
  /* NOT FOR BROWSER END */
192
197
  throw new SyntaxError('Invalid template name');
193
198
  }
@@ -253,7 +258,9 @@ let TranscludeToken = (() => {
253
258
  /** 获取模板或模块名 */
254
259
  #getTitle() {
255
260
  const isTemplate = this.type === 'template', title = this.normalizeTitle(this.childNodes[isTemplate ? 0 : 1].text(), isTemplate ? 10 : 828, { temporary: true });
261
+ /* NOT FOR BROWSER */
256
262
  title.fragment = undefined;
263
+ /* NOT FOR BROWSER END */
257
264
  return title;
258
265
  }
259
266
  /** @private */
@@ -345,14 +352,19 @@ let TranscludeToken = (() => {
345
352
  return errors;
346
353
  }
347
354
  const { type, childNodes, length } = this, rect = new rect_1.BoundingRect(this, start), invoke = type === 'magic-word';
355
+ let rule = 'no-ignored', s = index_1.default.lintConfig.getSeverity(rule, 'fragment');
348
356
  if (invoke && !this.#getTitle().valid) {
349
- errors.push((0, lint_1.generateForChild)(childNodes[1], rect, 'invalid-invoke', 'illegal module name'));
357
+ rule = 'invalid-invoke';
358
+ s = index_1.default.lintConfig.getSeverity(rule, 'name');
359
+ if (s) {
360
+ errors.push((0, lint_1.generateForChild)(childNodes[1], rect, rule, 'illegal module name', s));
361
+ }
350
362
  }
351
- else {
363
+ else if (s) {
352
364
  const child = childNodes[invoke ? 1 : 0], i = child.childNodes
353
365
  .findIndex(c => c.type === 'text' && (0, string_1.decodeHtml)(c.data).includes('#')), textNode = child.childNodes[i];
354
366
  if (textNode) {
355
- const e = (0, lint_1.generateForChild)(child, rect, 'no-ignored', 'useless fragment', 'warning');
367
+ const e = (0, lint_1.generateForChild)(child, rect, rule, 'useless fragment', s);
356
368
  e.fix = {
357
369
  desc: 'remove',
358
370
  range: [
@@ -364,16 +376,20 @@ let TranscludeToken = (() => {
364
376
  errors.push(e);
365
377
  }
366
378
  }
367
- if (invoke && length === 2) {
368
- errors.push((0, lint_1.generateForSelf)(this, rect, 'invalid-invoke', 'missing module function'));
379
+ rule = 'invalid-invoke';
380
+ s = index_1.default.lintConfig.getSeverity(rule, 'function');
381
+ if (s && invoke && length === 2) {
382
+ errors.push((0, lint_1.generateForSelf)(this, rect, rule, 'missing module function', s));
369
383
  return errors;
370
384
  }
371
- const duplicatedArgs = this.getDuplicatedArgs()
372
- .filter(([, parameter]) => !parameter[0].querySelector('ext'));
373
- if (duplicatedArgs.length > 0) {
385
+ rule = 'no-duplicate';
386
+ s = index_1.default.lintConfig.getSeverity(rule, 'parameter');
387
+ if (s) {
388
+ const duplicatedArgs = this.getDuplicatedArgs()
389
+ .filter(([, parameter]) => !parameter[0].querySelector('ext')), msg = 'duplicated parameter';
374
390
  for (const [, args] of duplicatedArgs) {
375
391
  errors.push(...args.map(arg => {
376
- const e = (0, lint_1.generateForChild)(arg, rect, 'no-duplicate', 'duplicated parameter');
392
+ const e = (0, lint_1.generateForChild)(arg, rect, rule, msg, s);
377
393
  e.suggestions = [{ desc: 'remove', range: [e.startIndex - 1, e.endIndex], text: '' }];
378
394
  return e;
379
395
  }));
@@ -787,6 +803,25 @@ let TranscludeToken = (() => {
787
803
  }
788
804
  return [this.module, this.function];
789
805
  }
806
+ /**
807
+ * Get the [frame object](https://www.mediawiki.org/wiki/Extension:Scribunto/Lua_reference_manual#frame-object)
808
+ *
809
+ * 获取 [frame 对象](https://www.mediawiki.org/wiki/Extension:Scribunto/Lua_reference_manual#frame-object)
810
+ * @param context template calling this module / 调用该模块的模板
811
+ * @throws `Error` 仅用于模块
812
+ * @since v1.22.0
813
+ */
814
+ getFrame(context) {
815
+ /* istanbul ignore if */
816
+ if (this.type === 'magic-word' && this.name !== 'invoke' || this.type === 'template' && context) {
817
+ throw new Error('TranscludeToken.getFrame method is only for modules!');
818
+ }
819
+ return {
820
+ args: this.getValue(),
821
+ parent: context?.getFrame(),
822
+ title: this.#getTitle().toString(true),
823
+ };
824
+ }
790
825
  /** @private */
791
826
  toHtmlInternal(opt) {
792
827
  const { type, name } = this;