wikiparser-node 1.39.1 → 1.41.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 (59) hide show
  1. package/README.md +51 -5
  2. package/bundle/bundle-es8.min.js +30 -29
  3. package/bundle/bundle-lsp.min.js +28 -28
  4. package/bundle/bundle.min.js +16 -16
  5. package/config/.schema.json +5 -0
  6. package/config/default.json +11 -2
  7. package/config/enwiki.json +91 -89
  8. package/config/jawiki.json +168 -158
  9. package/config/llwiki.json +2 -1
  10. package/config/minimum.json +3 -81
  11. package/config/moegirl.json +2 -1
  12. package/config/zhwiki.json +128 -126
  13. package/data/signatures.json +1 -1
  14. package/dist/addon/attribute.js +1 -1
  15. package/dist/addon/table.js +1 -1
  16. package/dist/addon/transclude.js +3 -1
  17. package/dist/base.d.mts +11 -9
  18. package/dist/base.d.ts +11 -9
  19. package/dist/base.js +1 -0
  20. package/dist/base.mjs +1 -0
  21. package/dist/bin/config.js +11 -10
  22. package/dist/index.d.ts +5 -5
  23. package/dist/index.js +5 -1
  24. package/dist/lib/lintConfig.js +42 -23
  25. package/dist/lib/lsp.js +6 -12
  26. package/dist/lib/node.js +5 -2
  27. package/dist/lib/text.js +5 -2
  28. package/dist/lib/title.js +8 -4
  29. package/dist/mixin/elementLike.js +2 -2
  30. package/dist/parser/commentAndExt.js +2 -1
  31. package/dist/render/expand.js +3 -3
  32. package/dist/render/extension.js +15 -3
  33. package/dist/render/magicWords.js +13 -10
  34. package/dist/src/attribute.d.ts +4 -1
  35. package/dist/src/attribute.js +5 -4
  36. package/dist/src/attributes.js +29 -7
  37. package/dist/src/heading.js +8 -3
  38. package/dist/src/link/base.d.ts +1 -1
  39. package/dist/src/link/base.js +10 -6
  40. package/dist/src/link/file.js +2 -2
  41. package/dist/src/magicLink.js +20 -16
  42. package/dist/src/multiLine/gallery.d.ts +5 -3
  43. package/dist/src/multiLine/gallery.js +6 -4
  44. package/dist/src/nowiki/base.d.ts +1 -1
  45. package/dist/src/parameter.js +5 -2
  46. package/dist/src/table/tr.js +1 -1
  47. package/dist/src/tagPair/ext.js +12 -18
  48. package/dist/src/tagPair/index.d.ts +1 -1
  49. package/dist/src/transclude.d.ts +6 -1
  50. package/dist/src/transclude.js +27 -19
  51. package/dist/util/constants.js +2 -1
  52. package/dist/util/sharable.js +2 -0
  53. package/dist/util/sharable.mjs +3 -1
  54. package/extensions/dist/base.js +3 -2
  55. package/extensions/dist/env.js +34 -0
  56. package/i18n/en.json +1 -0
  57. package/i18n/zh-hans.json +1 -0
  58. package/i18n/zh-hant.json +1 -0
  59. package/package.json +20 -33
@@ -83,7 +83,7 @@ let LinkBaseToken = (() => {
83
83
  /* NOT FOR BROWSER END */
84
84
  /** full link / 完整链接 */
85
85
  get link() {
86
- LSP: return this.#title;
86
+ LINT: return this.#title;
87
87
  }
88
88
  /* PRINT ONLY */
89
89
  /** 片段标识符 */
@@ -123,9 +123,7 @@ let LinkBaseToken = (() => {
123
123
  super(undefined, config, accum, {
124
124
  AtomToken: 0, Token: 1,
125
125
  });
126
- this.insertAt(new atom_1.AtomToken(link, 'link-target', config, accum, {
127
- 'Stage-2': ':', '!ExtToken': '', '!HeadingToken': '',
128
- }));
126
+ this.insertAt(new atom_1.AtomToken(link, 'link-target', config, accum, { 'Stage-2': ':', '!ExtToken': '', '!HeadingToken': '' }));
129
127
  if (linkText !== undefined) {
130
128
  const inner = new index_2.Token(linkText, { ...config, excludes: [...config.excludes, 'list'] }, accum, { 'Stage-5': ':', QuoteToken: ':', ConverterToken: ':' });
131
129
  inner.type = 'link-text';
@@ -198,12 +196,18 @@ let LinkBaseToken = (() => {
198
196
  /** @private */
199
197
  toString(skip) {
200
198
  const str = super.toString(skip, this.#delimiter);
201
- return this.#bracket ? `[[${str}]]` : str;
199
+ if (this.#bracket) {
200
+ return `[[${str}]]`;
201
+ }
202
+ return str;
202
203
  }
203
204
  /** @private */
204
205
  text() {
205
206
  const str = super.text('|');
206
- return this.#bracket ? `[[${str}]]` : str;
207
+ if (this.#bracket) {
208
+ return `[[${str}]]`;
209
+ }
210
+ return str;
207
211
  }
208
212
  /** @private */
209
213
  getAttribute(key) {
@@ -183,9 +183,9 @@ let FileToken = (() => {
183
183
  /* NOT FOR BROWSER END */
184
184
  const { extension } = this.getTitle(true, true);
185
185
  /-\{|\}-|\|/gu; // eslint-disable-line @typescript-eslint/no-unused-expressions
186
- this.safeAppend(explode(text).map(
186
+ this.safeAppend(explode(text).map((part) =>
187
187
  // @ts-expect-error abstract class
188
- (part) => new imageParameter_1.ImageParameterToken(part, extension, type, config, accum)));
188
+ new imageParameter_1.ImageParameterToken(part, extension, type, config, accum)));
189
189
  }
190
190
  /** @private */
191
191
  lint(start = this.getAbsoluteIndex(), re) {
@@ -191,7 +191,7 @@ let MagicLinkToken = (() => {
191
191
  let rule = 'invalid-url', severity = lintConfig.getSeverity(rule);
192
192
  if (severity && !this.querySelector('magic-word')) {
193
193
  try {
194
- this.getUrl();
194
+ this.#getUrl();
195
195
  }
196
196
  catch {
197
197
  errors.push((0, lint_1.generateForSelf)(this, rect, rule, 'invalid-url', severity));
@@ -219,6 +219,16 @@ let MagicLinkToken = (() => {
219
219
  return errors;
220
220
  }
221
221
  }
222
+ /** 获取自由外链的 URL */
223
+ #getUrl() {
224
+ LINT: {
225
+ let { link } = this;
226
+ if (link.startsWith('//')) {
227
+ link = `https:${link}`;
228
+ }
229
+ return new URL(link);
230
+ }
231
+ }
222
232
  /**
223
233
  * Get the URL
224
234
  *
@@ -227,22 +237,16 @@ let MagicLinkToken = (() => {
227
237
  */
228
238
  getUrl(articlePath) {
229
239
  LSP: {
230
- const { type } = this;
231
- let { link } = this;
232
- if (type === 'magic-link') {
233
- if (link.startsWith('ISBN')) {
234
- return this
235
- .normalizeTitle(`BookSources/${link.slice(5)}`, -1, { temporary: true })
236
- .getUrl(articlePath);
237
- }
238
- link = link.startsWith('RFC')
239
- ? `https://datatracker.ietf.org/doc/html/rfc${link.slice(4)}`
240
- : `https://pubmed.ncbi.nlm.nih.gov/${link.slice(5)}`;
241
- }
242
- else if (link.startsWith('//')) {
243
- link = `https:${link}`;
240
+ if (this.type !== 'magic-link') {
241
+ return this.#getUrl();
244
242
  }
245
- return new URL(link);
243
+ const { link } = this;
244
+ return link.startsWith('ISBN')
245
+ ? this.normalizeTitle(`BookSources/${link.slice(5)}`, -1, { temporary: true })
246
+ .getUrl(articlePath)
247
+ : new URL(link.startsWith('RFC')
248
+ ? `https://datatracker.ietf.org/doc/html/rfc${link.slice(4)}`
249
+ : `https://pubmed.ncbi.nlm.nih.gov/${link.slice(5)}`);
246
250
  }
247
251
  }
248
252
  /* PRINT ONLY */
@@ -3,6 +3,7 @@ import { GalleryImageToken } from '../link/galleryImage';
3
3
  import { CommentLineToken } from '../nowiki/commentLine';
4
4
  import type { Config, LintError, AST } from '../../base';
5
5
  import type { AstText, Token, AstNodes } from '../../internal';
6
+ declare type Child = GalleryImageToken | CommentLineToken | AstText;
6
7
  /**
7
8
  * `<gallery>`
8
9
  * @classdesc `{childNodes: (GalleryImageToken|CommentLineToken|AstText)[]}`
@@ -10,9 +11,9 @@ import type { AstText, Token, AstNodes } from '../../internal';
10
11
  export declare abstract class GalleryToken extends MultiLineToken {
11
12
  #private;
12
13
  readonly name: 'gallery';
13
- readonly childNodes: readonly (GalleryImageToken | CommentLineToken | AstText)[];
14
- abstract get firstChild(): GalleryImageToken | CommentLineToken | AstText | undefined;
15
- abstract get lastChild(): GalleryImageToken | CommentLineToken | AstText | undefined;
14
+ readonly childNodes: readonly Child[];
15
+ abstract get firstChild(): Child | undefined;
16
+ abstract get lastChild(): Child | undefined;
16
17
  abstract get children(): (GalleryImageToken | CommentLineToken)[];
17
18
  abstract get firstElementChild(): GalleryImageToken | CommentLineToken | undefined;
18
19
  abstract get lastElementChild(): GalleryImageToken | CommentLineToken | undefined;
@@ -44,3 +45,4 @@ export declare abstract class GalleryToken extends MultiLineToken {
44
45
  */
45
46
  insertImage(file: string, i?: number): GalleryImageToken;
46
47
  }
48
+ export {};
@@ -48,7 +48,6 @@ const debug_1 = require("../../util/debug");
48
48
  const constants_1 = require("../../util/constants");
49
49
  const html_1 = require("../../util/html");
50
50
  const cached_1 = require("../../mixin/cached");
51
- /* NOT FOR BROWSER END */
52
51
  /**
53
52
  * `<gallery>`
54
53
  * @classdesc `{childNodes: (GalleryImageToken|CommentLineToken|AstText)[]}`
@@ -98,8 +97,10 @@ let GalleryToken = (() => {
98
97
  for (const line of inner?.split('\n') ?? []) {
99
98
  const matches = /^([^|]+)(?:\|(.*))?/u.exec(line);
100
99
  if (!matches) {
101
- // @ts-expect-error abstract class
102
- super.insertAt((line.trim() ? new commentLine_1.CommentLineToken(line, config, accum) : line));
100
+ super.insertAt((line.trim()
101
+ // @ts-expect-error abstract class
102
+ ? new commentLine_1.CommentLineToken(line, config, accum)
103
+ : line));
103
104
  continue;
104
105
  }
105
106
  const [, file, alt] = matches;
@@ -108,8 +109,9 @@ let GalleryToken = (() => {
108
109
  super.insertAt(new galleryImage_1.GalleryImageToken('gallery', file, alt, config, accum));
109
110
  }
110
111
  else {
112
+ super.insertAt(
111
113
  // @ts-expect-error abstract class
112
- super.insertAt(new commentLine_1.CommentLineToken(line, config, accum));
114
+ new commentLine_1.CommentLineToken(line, config, accum));
113
115
  }
114
116
  }
115
117
  }
@@ -1,7 +1,7 @@
1
1
  import { Token } from '../index';
2
2
  import type { Config } from '../../base';
3
3
  import type { AstText } from '../../internal';
4
- declare type NowikiTypes = 'ext-inner' | 'comment' | 'dd' | 'double-underscore' | 'hr' | 'list' | 'noinclude' | 'quote';
4
+ declare type NowikiTypes = 'ext-inner' | 'comment' | 'dd' | 'double-underscore' | 'hr' | 'list' | 'quote' | 'noinclude';
5
5
  /**
6
6
  * text-only token that will not be parsed
7
7
  *
@@ -130,7 +130,9 @@ let ParameterToken = (() => {
130
130
  }
131
131
  /** @private */
132
132
  trimName(name, set = true) {
133
- const trimmed = (typeof name === 'string' ? name : name.toString(true))
133
+ const trimmed = (typeof name === 'string'
134
+ ? name :
135
+ name.toString(true))
134
136
  .replace(/^[ \t\n\0\v]+|([^ \t\n\0\v])[ \t\n\0\v]+$/gu, '$1');
135
137
  if (set) {
136
138
  this.setAttribute('name', trimmed);
@@ -245,7 +247,8 @@ let ParameterToken = (() => {
245
247
  */
246
248
  setValue(value) {
247
249
  const { childNodes } = index_1.default.parseWithRef(value, this);
248
- this.lastChild.safeReplaceChildren(childNodes);
250
+ this.lastChild
251
+ .safeReplaceChildren(childNodes);
249
252
  }
250
253
  /**
251
254
  * Rename the parameter
@@ -61,7 +61,7 @@ class TrToken extends trBase_1.TrBaseToken {
61
61
  * 获取前一行
62
62
  */
63
63
  getPreviousRow() {
64
- return this.#getSiblingRow((childNodes, index) => childNodes.slice(0, index).reverse());
64
+ return this.#getSiblingRow((childNodes, index) => childNodes.slice(0, index).toReversed());
65
65
  }
66
66
  }
67
67
  exports.TrToken = TrToken;
@@ -48,7 +48,6 @@ const attributes_1 = require("../attributes");
48
48
  /* NOT FOR BROWSER */
49
49
  const debug_1 = require("../../util/debug");
50
50
  const constants_1 = require("../../util/constants");
51
- const string_1 = require("../../util/string");
52
51
  const cached_1 = require("../../mixin/cached");
53
52
  /**
54
53
  * extension tag
@@ -116,11 +115,17 @@ let ExtToken = (() => {
116
115
  case 'seo':
117
116
  case 'langconvert':
118
117
  case 'phonos':
119
- if (lcName === 'poem') {
120
- newConfig.excludes.push('heading');
121
- }
122
- else if (lcName === 'tab') {
123
- newConfig.ext = newConfig.ext.filter(e => e !== 'tabs');
118
+ switch (lcName) {
119
+ case 'poem':
120
+ newConfig.excludes.push('heading');
121
+ break;
122
+ case 'langconvert':
123
+ newConfig.excludes.push('list');
124
+ break;
125
+ case 'tab':
126
+ newConfig.ext = newConfig.ext.filter(e => e !== 'tabs');
127
+ break;
128
+ // No default
124
129
  }
125
130
  innerToken = new index_2.Token(inner, newConfig, accum);
126
131
  break;
@@ -242,21 +247,10 @@ let ExtToken = (() => {
242
247
  }
243
248
  /** @private */
244
249
  toHtmlInternal(opt) {
245
- const { name, firstChild, lastChild } = this;
250
+ const { name } = this;
246
251
  if (constants_1.tagHooks.has(name)) {
247
252
  return constants_1.tagHooks.get(name)(this);
248
253
  }
249
- else if (name === 'nowiki') {
250
- const html = lastChild.toHtmlInternal();
251
- return this.closest('ext-inner')?.name === 'poem' ? html : (0, string_1.newline)(html);
252
- }
253
- else if (name === 'pre') {
254
- const html = lastChild.toHtmlInternal({
255
- ...opt,
256
- nowrap: false,
257
- });
258
- return `<pre${firstChild.toHtmlInternal()}>${this.closest('ext-inner')?.name === 'poem' ? html : (0, string_1.newline)(html)}</pre>`;
259
- }
260
254
  const { renderExt } = require('../../render/extension');
261
255
  return renderExt(this, opt);
262
256
  }
@@ -10,7 +10,7 @@ export declare abstract class TagPairToken extends Token {
10
10
  #private;
11
11
  readonly name: string;
12
12
  closed: boolean;
13
- abstract get type(): 'ext' | 'include' | 'translate';
13
+ abstract get type(): 'ext' | 'translate' | 'include';
14
14
  readonly childNodes: readonly [AstNodes, AstNodes];
15
15
  abstract get firstChild(): AstNodes;
16
16
  abstract get lastChild(): AstNodes;
@@ -18,7 +18,12 @@ export declare abstract class TranscludeToken extends Token {
18
18
  #private;
19
19
  readonly modifier: string;
20
20
  readonly name: string;
21
- readonly childNodes: readonly [AtomToken | SyntaxToken, ...ParameterToken[]] | readonly [SyntaxToken, AtomToken, AtomToken, ...ParameterToken[]];
21
+ readonly childNodes: readonly [
22
+ SyntaxToken,
23
+ AtomToken,
24
+ AtomToken,
25
+ ...ParameterToken[]
26
+ ] | readonly [AtomToken | SyntaxToken, ...ParameterToken[]];
22
27
  abstract get firstChild(): AtomToken | SyntaxToken;
23
28
  abstract get lastChild(): AtomToken | SyntaxToken | ParameterToken;
24
29
  abstract get children(): [AtomToken | SyntaxToken, ...ParameterToken[]] | [SyntaxToken, AtomToken, AtomToken, ...ParameterToken[]];
@@ -214,7 +214,9 @@ let TranscludeToken = (() => {
214
214
  let i = 1;
215
215
  for (let j = 0; j < parts.length; j++) {
216
216
  const part = parts[j];
217
- if (!(templateLike || this.name === 'switch' && j > 0 || this.name === 'tag' && j > 1)) {
217
+ if (!(templateLike
218
+ || this.name === 'switch' && j > 0
219
+ || this.name === 'tag' && j > 1)) {
218
220
  part[0] = part.join('=');
219
221
  part.length = 1;
220
222
  }
@@ -257,11 +259,15 @@ let TranscludeToken = (() => {
257
259
  * 是否是模板或模块
258
260
  */
259
261
  isTemplate() {
260
- return this.type === 'template' || this.name === 'invoke';
262
+ return this.type === 'template'
263
+ || this.name === 'invoke';
261
264
  }
262
265
  /** 获取模板或模块名 */
263
266
  #getTitle() {
264
- const isTemplate = this.type === 'template', title = this.normalizeTitle((isTemplate ? '' : 'Module:') + (0, string_1.removeComment)(this.childNodes[isTemplate ? 0 : 1].text()), 10, { temporary: true, ...!isTemplate && { page: '' } });
267
+ const isTemplate = this.type === 'template', title = this.normalizeTitle((isTemplate ? '' : 'Module:')
268
+ + (0, string_1.removeComment)(this.childNodes[isTemplate ?
269
+ 0
270
+ : 1].text()), 10, { temporary: true, ...!isTemplate && { page: '' } });
265
271
  /* NOT FOR BROWSER */
266
272
  title.fragment = undefined;
267
273
  /* NOT FOR BROWSER END */
@@ -319,14 +325,15 @@ let TranscludeToken = (() => {
319
325
  }
320
326
  /** @private */
321
327
  text() {
322
- const { childNodes, length, firstChild, modifier, type, name } = this;
323
- return type === 'magic-word' && name === 'vardefine'
324
- ? ''
325
- : `{{${modifier}${type === 'magic-word'
326
- ? firstChild.text()
327
- + (length === 1 ? '' : this.#colon)
328
- + (0, string_1.text)(childNodes.slice(1), '|')
329
- : super.text('|')}}}`;
328
+ const { childNodes, length, firstChild, modifier, type, name, } = this;
329
+ if (type === 'magic-word' && name === 'vardefine') {
330
+ return '';
331
+ }
332
+ return `{{${modifier}${type === 'magic-word'
333
+ ? firstChild.text()
334
+ + (length === 1 ? '' : this.#colon)
335
+ + (0, string_1.text)(childNodes.slice(1), '|')
336
+ : super.text('|')}}}`;
330
337
  }
331
338
  /** @private */
332
339
  getAttribute(key) {
@@ -407,12 +414,10 @@ let TranscludeToken = (() => {
407
414
  /* NOT FOR BROWSER */
408
415
  const removing = typeof addedToken === 'number';
409
416
  /* NOT FOR BROWSER END */
410
- /* eslint-disable @stylistic/operator-linebreak */
411
417
  this.#anonCount +=
412
418
  removing ?
413
419
  -1 :
414
420
  1;
415
- /* eslint-enable @stylistic/operator-linebreak */
416
421
  /* NOT FOR BROWSER */
417
422
  const maxAnon = String(this.#anonCount + (removing ? 1 : 0));
418
423
  if (!removing) {
@@ -435,11 +440,11 @@ let TranscludeToken = (() => {
435
440
  for (; i < this.#anonCount; i++) {
436
441
  /* NOT FOR BROWSER END */
437
442
  const token =
438
- /* eslint-disable @stylistic/operator-linebreak, unicorn/no-negated-condition */
443
+ /* eslint-disable unicorn/no-negated-condition */
439
444
  !append ?
440
445
  args[i] :
441
446
  addedToken,
442
- /* eslint-enable @stylistic/operator-linebreak, unicorn/no-negated-condition */
447
+ /* eslint-enable unicorn/no-negated-condition */
443
448
  { name } = token, newName = String(i + 1);
444
449
  if (name !== newName || token === addedToken) {
445
450
  token.setAttribute('name', newName);
@@ -670,7 +675,9 @@ let TranscludeToken = (() => {
670
675
  * @param exact whether to match anonymosity / 是否匹配匿名性
671
676
  */
672
677
  getArg(key, exact) {
673
- return [...this.getArgs(key, exact, false)].sort((a, b) => b.compareDocumentPosition(a))[0];
678
+ return [
679
+ ...this.getArgs(key, exact, false),
680
+ ].toSorted((a, b) => b.compareDocumentPosition(a))[0];
674
681
  }
675
682
  /**
676
683
  * Remove parameters with the specified name
@@ -713,9 +720,10 @@ let TranscludeToken = (() => {
713
720
  return [...this.getArgs(key, false, false)].map(token => token.getValue());
714
721
  }
715
722
  getValue(key) {
716
- return key === undefined
717
- ? Object.fromEntries(this.getKeys().map(k => [k, this.getValue(k)]))
718
- : this.getArg(key)?.getValue();
723
+ if (key === undefined) {
724
+ return Object.fromEntries(this.getKeys().map(k => [k, this.getValue(k)]));
725
+ }
726
+ return this.getArg(key)?.getValue();
719
727
  }
720
728
  /**
721
729
  * Insert an anonymous parameter
@@ -10,8 +10,9 @@ var BuildMethod;
10
10
  BuildMethod[BuildMethod["Text"] = 1] = "Text";
11
11
  })(BuildMethod || (exports.BuildMethod = BuildMethod = {}));
12
12
  exports.enMsg = (() => {
13
+ LSP: return require(
13
14
  // eslint-disable-next-line n/no-missing-require
14
- LSP: return require('../../i18n/en.json');
15
+ '../../i18n/en.json');
15
16
  })();
16
17
  exports.galleryParams = new Set(['alt', 'link', 'lang', 'page', 'caption']);
17
18
  exports.extensions = new Set(['tiff', 'tif', 'png', 'gif', 'jpg', 'jpeg', 'webp', 'xcf', 'pdf', 'svg', 'djvu']);
@@ -88,6 +88,8 @@ exports.htmlAttrs = (() => ({
88
88
  categorytree: blockAttrs,
89
89
  combooption: blockAttrs,
90
90
  img: new Set(['alt', 'src', 'width', 'height', 'loading', 'srcset']),
91
+ /* NOT FOR BROWSER ONLY */
92
+ a: new Set(['href', 'rel', 'rev']),
91
93
  }))();
92
94
  exports.extAttrs = (() => ({
93
95
  pre: new Set(['format']),
@@ -85,7 +85,9 @@ const htmlAttrs = /* @__PURE__ */ (() => ({
85
85
  poem: blockAttrs,
86
86
  categorytree: blockAttrs,
87
87
  combooption: blockAttrs,
88
- img: /* @__PURE__ */ new Set(["alt", "src", "width", "height", "loading", "srcset"])
88
+ img: /* @__PURE__ */ new Set(["alt", "src", "width", "height", "loading", "srcset"]),
89
+ /* NOT FOR BROWSER ONLY */
90
+ a: /* @__PURE__ */ new Set(["href", "rel", "rev"])
89
91
  }))();
90
92
  const extAttrs = /* @__PURE__ */ (() => ({
91
93
  pre: /* @__PURE__ */ new Set(["format"]),
@@ -1,6 +1,6 @@
1
1
  (() => {
2
2
  var _a;
3
- const version = '1.39.1', src = (_a = document.currentScript) === null || _a === void 0 ? void 0 : _a.src, file = /\/extensions\/dist\/base\.(?:min\.)?js$/u, CDN = src && file.test(src)
3
+ const version = '1.41.0', src = (_a = document.currentScript) === null || _a === void 0 ? void 0 : _a.src, file = /\/extensions\/dist\/base\.(?:min\.)?js$/u, CDN = src && file.test(src)
4
4
  ? src.replace(file, '')
5
5
  : `https://fastly.jsdelivr.net/npm/wikiparser-node@${version}`;
6
6
  const workerJS = () => {
@@ -82,7 +82,8 @@ const workerJS = () => {
82
82
  stage !== null && stage !== void 0 ? stage : Infinity,
83
83
  String(child),
84
84
  child.type === 'text'
85
- ? String(child).replace(/[&<>]/gu, p => `&${entities[p]};`)
85
+ ? String(child)
86
+ .replaceAll(/[&<>]/gu, p => `&${entities[p]};`)
86
87
  : child.print(),
87
88
  ]),
88
89
  ]);
@@ -0,0 +1,34 @@
1
+ (() => {
2
+ const execute = (obj) => {
3
+ Object.entries(obj.files).find(([k]) => k.endsWith('.data.js'))[1]();
4
+ };
5
+ Object.assign(globalThis, {
6
+ mw: {
7
+ loader: {
8
+ done: false,
9
+ impl(callback) {
10
+ execute(callback()[1]);
11
+ },
12
+ implement(name, callback) {
13
+ if (typeof callback === 'object') {
14
+ execute(callback);
15
+ }
16
+ else if (!this.done) {
17
+ callback();
18
+ }
19
+ if (name.startsWith('ext.CodeMirror.data')) {
20
+ this.done = true;
21
+ }
22
+ },
23
+ state() {
24
+ },
25
+ },
26
+ config: {
27
+ values: {},
28
+ set({ extCodeMirrorConfig }) {
29
+ this.values.extCodeMirrorConfig = extCodeMirrorConfig;
30
+ },
31
+ },
32
+ },
33
+ });
34
+ })();
package/i18n/en.json CHANGED
@@ -67,6 +67,7 @@
67
67
  "redirect-like": "redirect-like syntax in a list item",
68
68
  "ref-in-link": "<ref> in an internal or external link",
69
69
  "remove": null,
70
+ "required-attribute": "required $1 attribute is missing",
70
71
  "template-in-link": "template in an internal link target",
71
72
  "unbalanced-in-section-header": "unbalanced $1 in a section header",
72
73
  "unclosed": "unclosed $1",
package/i18n/zh-hans.json CHANGED
@@ -67,6 +67,7 @@
67
67
  "redirect-like": "列表项中的疑似重定向语法",
68
68
  "ref-in-link": "内部或外部链接中的<ref>",
69
69
  "remove": "移除",
70
+ "required-attribute": "缺少必需的$1属性",
70
71
  "template-in-link": "内部链接目标中的模板",
71
72
  "unbalanced-in-section-header": "章节标题中未成对的$1",
72
73
  "unclosed": "未闭合的$1",
package/i18n/zh-hant.json CHANGED
@@ -67,6 +67,7 @@
67
67
  "redirect-like": "列表項中的疑似重新導向語法",
68
68
  "ref-in-link": "內部或外部連結裡的<ref>",
69
69
  "remove": "移除",
70
+ "required-attribute": "缺少必需的$1屬性",
70
71
  "template-in-link": "內部連結目標中的模板",
71
72
  "unbalanced-in-section-header": "章節標題裡的$1未成對",
72
73
  "unclosed": "有未關閉的$1",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "wikiparser-node",
3
- "version": "1.39.1",
3
+ "version": "1.41.0",
4
4
  "description": "A Node.js parser for MediaWiki markup with AST",
5
5
  "keywords": [
6
6
  "mediawiki",
@@ -8,7 +8,7 @@
8
8
  "parser",
9
9
  "browser"
10
10
  ],
11
- "homepage": "https://github.com/bhsd-harry/wikiparser-node/wiki",
11
+ "homepage": "https://github.com/bhsd-harry/wikiparser-node#readme",
12
12
  "bugs": {
13
13
  "url": "https://github.com/bhsd-harry/wikiparser-node/issues"
14
14
  },
@@ -24,7 +24,7 @@
24
24
  "/errors/README",
25
25
  "/config/",
26
26
  "!/config/mediawikiwiki.json",
27
- "!/config/testwiki.json",
27
+ "!/config/github.json",
28
28
  "/data/",
29
29
  "/i18n/",
30
30
  "/coverage/badge.svg",
@@ -46,13 +46,12 @@
46
46
  },
47
47
  "scripts": {
48
48
  "ls": "npm i --package-lock-only && npm ls --package-lock-only --all --omit=dev",
49
- "toc": "node dist/script/toc.js",
50
49
  "prepublishOnly": "npm run build:core",
51
50
  "build:core": "bash build.sh",
52
51
  "build:define": "bash sed.sh -i \"s/pkg = \\$PKG/pkg = $(npm pkg get name)/; s/version = \\$VERSION/version = $(npm pkg get version)/\" dist/bin/config.js",
53
52
  "build": "npm run build:core && LC_ALL=en.UTF-8 node dist/script/parserTests.js",
54
53
  "diff": "bash diff.sh",
55
- "diff:stat": "f() { git diff --stat --ignore-all-space --color=always $1 $2 -- . | grep '\\.ts'; }; f",
54
+ "diff:stat": "f() { git diff --stat -w --color=always $1 $2 -- . | grep '\\.ts'; }; f",
56
55
  "lint:ts": "tsc --noEmit && eslint --cache .",
57
56
  "lint:json": "v8r -s config/.schema.json config/*.json && v8r -s data/.schema.json data/*.json && mocha dist/test/json.js",
58
57
  "lint:md": "markdownlint-cli2 '**/*.md'",
@@ -83,61 +82,49 @@
83
82
  ]
84
83
  },
85
84
  "dependencies": {
86
- "@bhsd/cm-util": "^1.0.0",
87
- "@bhsd/common": "^2.0.0",
88
- "@bhsd/nodejs": "^1.0.0",
89
- "@bhsd/stylelint-util": "^1.0.2",
85
+ "@bhsd/cm-util": "^2.0.1",
86
+ "@bhsd/common": "^2.2.1",
87
+ "@bhsd/nodejs": "^1.0.1",
88
+ "@bhsd/stylelint-util": "^1.0.3",
90
89
  "binary-search": "^1.3.6",
91
90
  "vscode-languageserver-types": "^3.17.5"
92
91
  },
93
92
  "optionalDependencies": {
94
- "color-name": "^2.0.0",
93
+ "color-name": "~2.0.2",
95
94
  "entities": "^8.0.0",
96
95
  "mathoid-texvcjs": "^0.6.0",
97
- "prism-wiki": "^2.1.0",
96
+ "prism-wiki": "^2.1.1",
98
97
  "prismjs": "^1.30.0",
99
- "stylelint": "^17.9.0",
98
+ "stylelint": "^17.12.0",
100
99
  "vscode-css-languageservice": "^6.3.10",
101
100
  "vscode-html-languageservice": "^5.6.2",
102
101
  "vscode-json-languageservice": "^5.7.2"
103
102
  },
104
103
  "devDependencies": {
105
- "@bhsd/code-standard": "^2.2.0",
106
- "@bhsd/test-util": "^1.1.0",
107
- "@codemirror/lint": "^6.9.5",
104
+ "@bhsd/code-standard": "^2.5.1",
105
+ "@bhsd/test-util": "^1.3.1",
106
+ "@codemirror/lint": "^6.9.6",
108
107
  "@eslint/markdown": "^8.0.1",
109
- "@eslint-community/eslint-plugin-eslint-comments": "^4.7.1",
110
- "@stylistic/eslint-plugin": "^5.10.0",
111
108
  "@types/color-name": "^2.0.0",
112
109
  "@types/color-rgba": "^2.1.3",
113
110
  "@types/mocha": "^10.0.10",
114
- "@types/node": "^24.11.0",
111
+ "@types/node": "^25.9.0",
115
112
  "@types/prismjs": "^1.26.6",
116
- "@typescript-eslint/eslint-plugin": "^8.59.0",
117
- "@typescript-eslint/parser": "^8.59.0",
113
+ "@typescript-eslint/parser": "^8.59.4",
118
114
  "c8": "^11.0.0",
119
- "codejar-async": "^4.3.0",
115
+ "codejar-async": "^4.3.1",
120
116
  "color-rgba": "^3.0.0",
121
117
  "diff2html-cli": "^5.2.15",
122
118
  "esbuild": "^0.28.0",
123
- "eslint": "^10.2.1",
124
- "eslint-plugin-jsdoc": "^62.9.0",
125
- "eslint-plugin-jsonc": "^3.1.2",
126
- "eslint-plugin-n": "^17.24.0",
127
- "eslint-plugin-promise": "^7.2.1",
128
- "eslint-plugin-regexp": "^3.1.0",
129
- "eslint-plugin-unicorn": "^64.0.0",
119
+ "eslint": "^10.4.0",
130
120
  "markdownlint-cli2": "^0.22.1",
131
121
  "mocha": "^11.7.5",
132
122
  "monaco-editor": "~0.53.0",
133
- "tsx": "^4.21.0",
123
+ "tsx": "^4.22.2",
134
124
  "typescript": "^6.0.3",
135
- "v8r": "^6.0.0",
125
+ "v8r": "^6.1.0",
136
126
  "vscode-languageserver-textdocument": "^1.0.12"
137
127
  },
138
- "overrides": {
139
- "eslint": "^10.2.1"
140
- },
141
128
  "engines": {
142
129
  "node": "^20.19.0 || ^22.13.0 || >=24.11.0"
143
130
  }