wikiparser-node 0.1.0 → 0.2.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/README.md +211 -2
- package/config/default.json +12 -1
- package/config/llwiki.json +12 -1
- package/config/moegirl.json +9 -1
- package/errors/2022-07-04T22:30:41.785Z +1 -0
- package/errors/2022-07-04T22:30:41.785Z.err +11 -0
- package/errors/2022-07-04T22:30:41.785Z.json +5 -0
- package/index.js +42 -0
- package/lib/element.js +2 -1
- package/mixin/sol.js +8 -4
- package/package.json +1 -1
- package/parser/converter.js +44 -0
- package/src/arg.js +6 -6
- package/src/attribute.js +6 -6
- package/src/converter.js +135 -0
- package/src/converterFlags.js +214 -0
- package/src/converterRule.js +209 -0
- package/src/extLink.js +11 -11
- package/src/imageParameter.js +1 -1
- package/src/index.js +14 -10
- package/src/link/file.js +2 -2
- package/src/link/index.js +7 -7
- package/src/parameter.js +2 -2
- package/src/syntax.js +3 -1
- package/src/table/td.js +1 -0
- package/src/table/tr.js +1 -1
- package/src/transclude.js +14 -14
- package/typings/index.d.ts +2 -0
- package/typings/node.d.ts +2 -2
- package/typings/token.d.ts +1 -0
- package/util/string.js +13 -1
package/README.md
CHANGED
|
@@ -181,12 +181,35 @@
|
|
|
181
181
|
2. [setTarget](#magiclinktoken.settarget)
|
|
182
182
|
2. [原型属性](#magiclinktoken.prototype.properties)
|
|
183
183
|
1. [protocol](#magiclinktoken.protocol)
|
|
184
|
-
21. [
|
|
184
|
+
21. [ConverterToken](#convertertoken)
|
|
185
|
+
1. [原型方法](#convertertoken.prototype.methods)
|
|
186
|
+
1. [getAllFlags](#convertertoken.getallflags)
|
|
187
|
+
2. [getEffectiveFlags](#convertertoken.geteffectiveflags)
|
|
188
|
+
3. [hasFlag](#convertertoken.hasflag)
|
|
189
|
+
4. [hasEffectiveFlag](#convertertoken.haseffectiveflag)
|
|
190
|
+
5. [removeFlag](#convertertoken.removeflag)
|
|
191
|
+
6. [setFlag](#convertertoken.setflag)
|
|
192
|
+
7. [toggleFlag](#convertertoken.toggleflag)
|
|
193
|
+
2. [原型属性](#convertertoken.prototype.properties)
|
|
194
|
+
1. [noConvert](#convertertoken.noconvert)
|
|
195
|
+
22. [ConverterRuleToken](#converterruletoken)
|
|
196
|
+
1. [原型方法](#converterruletoken.prototype.methods)
|
|
197
|
+
1. [noConvert](#converterruletoken.noconvert)
|
|
198
|
+
2. [setTo](#converterruletoken.setto)
|
|
199
|
+
3. [setVariant](#converterruletoken.setvariant)
|
|
200
|
+
4. [setFrom](#converterruletoken.setfrom)
|
|
201
|
+
5. [makeUnidirectional](#converterruletoken.makeunidirectional)
|
|
202
|
+
6. [makeBidirectional](#converterruletoken.makebidirectional)
|
|
203
|
+
2. [实例属性](#converterruletoken.instance.properties)
|
|
204
|
+
1. [variant](#converterruletoken.variant)
|
|
205
|
+
2. [unidirectional](#converterruletoken.unidirectional)
|
|
206
|
+
3. [bidirectional](#converterruletoken.bidirectional)
|
|
207
|
+
23. [选择器](#选择器)
|
|
185
208
|
1. [type](#selector.type)
|
|
186
209
|
2. [name](#selector.name)
|
|
187
210
|
3. [属性](#selector.attribute)
|
|
188
211
|
4. [伪选择器](#selector.pseudo)
|
|
189
|
-
|
|
212
|
+
24. [$ (TokenCollection)](#-tokencollection)
|
|
190
213
|
</details>
|
|
191
214
|
|
|
192
215
|
# Parser
|
|
@@ -1807,6 +1830,192 @@ assert(root.toString() === 'https://example.org');
|
|
|
1807
1830
|
|
|
1808
1831
|
[返回目录](#目录)
|
|
1809
1832
|
|
|
1833
|
+
# ConverterToken
|
|
1834
|
+
转换。
|
|
1835
|
+
|
|
1836
|
+
## 原型方法<a id="convertertoken.prototype.methods"></a>
|
|
1837
|
+
<details>
|
|
1838
|
+
<summary>展开</summary>
|
|
1839
|
+
|
|
1840
|
+
**getAllFlags**(): Set\<string><a id="convertertoken.getallflags"></a>
|
|
1841
|
+
- 获取所有转换 flag,包括无效的。
|
|
1842
|
+
|
|
1843
|
+
```js
|
|
1844
|
+
var root = Parser.parse('-{zh-hans;zh-hant|}-'),
|
|
1845
|
+
converter = root.firstChild;
|
|
1846
|
+
assert.deepStrictEqual(converter.getAllFlags(), new Set(['zh-hans', 'zh-hant']));
|
|
1847
|
+
```
|
|
1848
|
+
|
|
1849
|
+
**getEffectiveFlags**(): Set\<string><a id="convertertoken.geteffectiveflags"></a>
|
|
1850
|
+
- 解析有效的转换 flag。
|
|
1851
|
+
|
|
1852
|
+
```js
|
|
1853
|
+
var root = Parser.parse('-{}-'),
|
|
1854
|
+
converter = root.firstChild;
|
|
1855
|
+
assert.deepStrictEqual(converter.getEffectiveFlags(), new Set(['S']));
|
|
1856
|
+
```
|
|
1857
|
+
|
|
1858
|
+
**hasFlag**(flag: string): boolean<a id="convertertoken.hasflag"></a>
|
|
1859
|
+
- 是否包含 flag,即使可能是无效 flag。
|
|
1860
|
+
|
|
1861
|
+
```js
|
|
1862
|
+
var root = Parser.parse('-{R|}-'),
|
|
1863
|
+
converter = root.firstChild;
|
|
1864
|
+
assert(converter.hasFlag('R') === true);
|
|
1865
|
+
```
|
|
1866
|
+
|
|
1867
|
+
**hasEffectiveFlag**(flag: string): boolean<a id="convertertoken.haseffectiveflag"></a>
|
|
1868
|
+
- 是否包含某有效 flag。
|
|
1869
|
+
|
|
1870
|
+
```js
|
|
1871
|
+
var root = Parser.parse('-{}-'),
|
|
1872
|
+
converter = root.firstChild;
|
|
1873
|
+
assert(converter.hasEffectiveFlag('S') === true);
|
|
1874
|
+
```
|
|
1875
|
+
|
|
1876
|
+
**removeFlag**(flag: string): void<a id="convertertoken.removeflag"></a>
|
|
1877
|
+
- 移除 flag,可能原本就是无效的 flag。
|
|
1878
|
+
|
|
1879
|
+
```js
|
|
1880
|
+
var root = Parser.parse('-{R|}-'),
|
|
1881
|
+
converter = root.firstChild;
|
|
1882
|
+
converter.removeFlag('R');
|
|
1883
|
+
assert(root.toString() === '-{}-');
|
|
1884
|
+
```
|
|
1885
|
+
|
|
1886
|
+
**setFlag**(flag: string): void<a id="convertertoken.setflag"></a>
|
|
1887
|
+
- 添加指定 flag,可能是无效 flag。
|
|
1888
|
+
|
|
1889
|
+
```js
|
|
1890
|
+
var root = Parser.parse('-{}-'),
|
|
1891
|
+
converter = root.firstChild;
|
|
1892
|
+
converter.setFlag('R');
|
|
1893
|
+
assert(root.toString() === '-{R|}-');
|
|
1894
|
+
```
|
|
1895
|
+
|
|
1896
|
+
**toggleFlag**(flag: string): void<a id="convertertoken.toggleflag"></a>
|
|
1897
|
+
- 改变某 flag 的有无,可能是无效 flag。
|
|
1898
|
+
|
|
1899
|
+
```js
|
|
1900
|
+
var root = Parser.parse('-{R|}-'),
|
|
1901
|
+
converter = root.firstChild;
|
|
1902
|
+
converter.toggleFlag('R');
|
|
1903
|
+
converter.toggleFlag('D');
|
|
1904
|
+
assert(root.toString() === '-{D|}-');
|
|
1905
|
+
```
|
|
1906
|
+
</details>
|
|
1907
|
+
|
|
1908
|
+
## 原型属性<a id="convertertoken.prototype.properties"></a>
|
|
1909
|
+
<details>
|
|
1910
|
+
<summary>展开</summary>
|
|
1911
|
+
|
|
1912
|
+
**noConvert**: boolean<a id="convertertoken.noconvert"></a>
|
|
1913
|
+
- 是否不会转换。
|
|
1914
|
+
|
|
1915
|
+
```js
|
|
1916
|
+
var root = Parser.parse('-{简体}-'),
|
|
1917
|
+
converter = root.firstChild;
|
|
1918
|
+
assert(converter.noConvert === true);
|
|
1919
|
+
```
|
|
1920
|
+
</details>
|
|
1921
|
+
|
|
1922
|
+
[返回目录](#目录)
|
|
1923
|
+
|
|
1924
|
+
# ConverterRuleToken
|
|
1925
|
+
单条转换规则。
|
|
1926
|
+
|
|
1927
|
+
## 原型方法<a id="converterruletoken.prototype.methods"></a>
|
|
1928
|
+
<details>
|
|
1929
|
+
<summary>展开</summary>
|
|
1930
|
+
|
|
1931
|
+
**noConvert**(): void<a id="converterruletoken.noconvert"></a>
|
|
1932
|
+
- 更改规则使得内容不会转换。
|
|
1933
|
+
|
|
1934
|
+
```js
|
|
1935
|
+
var root = Parser.parse('-{繁體=>zh-hans:繁體}-'),
|
|
1936
|
+
converterRule = root.querySelector('converter-rule');
|
|
1937
|
+
converterRule.noConvert();
|
|
1938
|
+
assert(root.toString() === '-{繁體}-');
|
|
1939
|
+
```
|
|
1940
|
+
|
|
1941
|
+
**setTo**(to: string): void<a id="converterruletoken.setto"></a>
|
|
1942
|
+
- 修改转换结果。
|
|
1943
|
+
|
|
1944
|
+
```js
|
|
1945
|
+
var root = Parser.parse('-{繁體=>zh-hans:繁體}-'),
|
|
1946
|
+
converterRule = root.querySelector('converter-rule');
|
|
1947
|
+
converterRule.setTo('繁体');
|
|
1948
|
+
assert(root.toString() === '-{繁體=>zh-hans:繁体}-');
|
|
1949
|
+
```
|
|
1950
|
+
|
|
1951
|
+
**setVariant**(variant: string): void<a id="converterruletoken.setvariant"></a>
|
|
1952
|
+
- 修改转换规则对应的语言变体。
|
|
1953
|
+
|
|
1954
|
+
```js
|
|
1955
|
+
var root = Parser.parse('-{繁體=>zh-hans:繁體}-'),
|
|
1956
|
+
converterRule = root.querySelector('converter-rule');
|
|
1957
|
+
converterRule.setVariant('zh-cn');
|
|
1958
|
+
assert(root.toString() === '-{繁體=>zh-cn:繁體}-');
|
|
1959
|
+
```
|
|
1960
|
+
|
|
1961
|
+
**setFrom**(from: string): void<a id="converterruletoken.setfrom"></a>
|
|
1962
|
+
- 对单项转换规则,修改待转换的内容。
|
|
1963
|
+
|
|
1964
|
+
```js
|
|
1965
|
+
var root = Parser.parse('-{繁體=>zh-hans:繁体}-'),
|
|
1966
|
+
converterRule = root.querySelector('converter-rule');
|
|
1967
|
+
converterRule.setFrom('正體');
|
|
1968
|
+
assert(root.toString() === '-{正體=>zh-hans:繁体}-');
|
|
1969
|
+
```
|
|
1970
|
+
|
|
1971
|
+
**makeUnidirectional**(from: string): void<a id="converterruletoken.makeunidirectional"></a>
|
|
1972
|
+
- [ConverterRuleToken.setFrom](#converterruletoken.setfrom) 方法的別名。
|
|
1973
|
+
|
|
1974
|
+
**makeBidirectional**(): void<a id="converterruletoken.makebidirectional"></a>
|
|
1975
|
+
- 将规则改为双向转换。
|
|
1976
|
+
|
|
1977
|
+
```js
|
|
1978
|
+
var root = Parser.parse('-{繁體=>zh-hans:繁体}-'),
|
|
1979
|
+
converterRule = root.querySelector('converter-rule');
|
|
1980
|
+
converterRule.makeBidirectional();
|
|
1981
|
+
assert(root.toString() === '-{zh-hans:繁体}-');
|
|
1982
|
+
```
|
|
1983
|
+
</details>
|
|
1984
|
+
|
|
1985
|
+
## 原型属性<a id="convertertoken.prototype.properties"></a>
|
|
1986
|
+
<details>
|
|
1987
|
+
<summary>展开</summary>
|
|
1988
|
+
|
|
1989
|
+
**variant**: string<a id="converterruletoken.variant"></a>
|
|
1990
|
+
- 规则对应的语言变体。
|
|
1991
|
+
|
|
1992
|
+
```js
|
|
1993
|
+
var root = Parser.parse('-{繁體=>zh-hans:繁体}-'),
|
|
1994
|
+
converterRule = root.querySelector('converter-rule');
|
|
1995
|
+
assert(converterRule.variant === 'zh-hans');
|
|
1996
|
+
```
|
|
1997
|
+
|
|
1998
|
+
**unidirectional**: boolean<a id="converterruletoken.unidirectional"></a>
|
|
1999
|
+
- 是否是单向转换。
|
|
2000
|
+
|
|
2001
|
+
```js
|
|
2002
|
+
var root = Parser.parse('-{繁體=>zh-hans:繁体}-'),
|
|
2003
|
+
converterRule = root.querySelector('converter-rule');
|
|
2004
|
+
assert(converterRule.unidirectional === true);
|
|
2005
|
+
```
|
|
2006
|
+
|
|
2007
|
+
**bidirectional**: boolean<a id="converterruletoken.bidirectional"></a>
|
|
2008
|
+
- 是否是双向转换。
|
|
2009
|
+
|
|
2010
|
+
```js
|
|
2011
|
+
var root = Parser.parse('-{zh-hans:繁体}-'),
|
|
2012
|
+
converterRule = root.querySelector('converter-rule');
|
|
2013
|
+
assert(converterRule.bidirectional === true);
|
|
2014
|
+
```
|
|
2015
|
+
</details>
|
|
2016
|
+
|
|
2017
|
+
[返回目录](#目录)
|
|
2018
|
+
|
|
1810
2019
|
# 选择器
|
|
1811
2020
|
Token 选择器的设计仿照了 CSS 和 jQuery 的选择器。
|
|
1812
2021
|
<details>
|
package/config/default.json
CHANGED
|
@@ -763,5 +763,16 @@
|
|
|
763
763
|
"底部": "bottom",
|
|
764
764
|
"text-bottom": "text-bottom",
|
|
765
765
|
"文字底部": "text-bottom"
|
|
766
|
-
}
|
|
766
|
+
},
|
|
767
|
+
"variants": [
|
|
768
|
+
"zh",
|
|
769
|
+
"zh-hans",
|
|
770
|
+
"zh-hant",
|
|
771
|
+
"zh-cn",
|
|
772
|
+
"zh-tw",
|
|
773
|
+
"zh-hk",
|
|
774
|
+
"zh-sg",
|
|
775
|
+
"zh-my",
|
|
776
|
+
"zh-mo"
|
|
777
|
+
]
|
|
767
778
|
}
|
package/config/llwiki.json
CHANGED
|
@@ -683,5 +683,16 @@
|
|
|
683
683
|
"底部": "bottom",
|
|
684
684
|
"text-bottom": "text-bottom",
|
|
685
685
|
"文字底部": "text-bottom"
|
|
686
|
-
}
|
|
686
|
+
},
|
|
687
|
+
"variants": [
|
|
688
|
+
"zh",
|
|
689
|
+
"zh-hans",
|
|
690
|
+
"zh-hant",
|
|
691
|
+
"zh-cn",
|
|
692
|
+
"zh-tw",
|
|
693
|
+
"zh-hk",
|
|
694
|
+
"zh-sg",
|
|
695
|
+
"zh-my",
|
|
696
|
+
"zh-mo"
|
|
697
|
+
]
|
|
687
698
|
}
|
package/config/moegirl.json
CHANGED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{|
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
TypeError: normalizeSpace is not a function
|
|
2
|
+
at AttributeToken.toString (/Users/mengxiwu/Documents/CCM-RP/node/wikiparser-node/src/attribute.js:249:44)
|
|
3
|
+
at #parseAttr (/Users/mengxiwu/Documents/CCM-RP/node/wikiparser-node/src/attribute.js:58:21)
|
|
4
|
+
at new AttributeToken (/Users/mengxiwu/Documents/CCM-RP/node/wikiparser-node/src/attribute.js:87:45)
|
|
5
|
+
at new TrToken (/Users/mengxiwu/Documents/CCM-RP/node/wikiparser-node/src/table/tr.js:28:4)
|
|
6
|
+
at new TableToken (/Users/mengxiwu/Documents/CCM-RP/node/wikiparser-node/src/table/index.js:66:3)
|
|
7
|
+
at parseTable (/Users/mengxiwu/Documents/CCM-RP/node/wikiparser-node/parser/table.js:40:18)
|
|
8
|
+
at #parseTable (/Users/mengxiwu/Documents/CCM-RP/node/wikiparser-node/src/index.js:553:16)
|
|
9
|
+
at Token.parseOnce (/Users/mengxiwu/Documents/CCM-RP/node/wikiparser-node/src/index.js:431:21)
|
|
10
|
+
at Token.parse (/Users/mengxiwu/Documents/CCM-RP/node/wikiparser-node/src/index.js:526:9)
|
|
11
|
+
at /Users/mengxiwu/Documents/CCM-RP/node/wikiparser-node/index.js:134:11
|
package/index.js
CHANGED
|
@@ -77,6 +77,7 @@ const /** @type {Parser} */ Parser = {
|
|
|
77
77
|
['ExtLinkToken'],
|
|
78
78
|
['MagicLinkToken'],
|
|
79
79
|
['ListToken', 'DdToken'],
|
|
80
|
+
['ConverterToken'],
|
|
80
81
|
],
|
|
81
82
|
|
|
82
83
|
config: './config/default',
|
|
@@ -178,6 +179,47 @@ const /** @type {Parser} */ Parser = {
|
|
|
178
179
|
delete require.cache[require.resolve('./tool')];
|
|
179
180
|
return require('./tool');
|
|
180
181
|
},
|
|
182
|
+
|
|
183
|
+
typeAliases: {
|
|
184
|
+
ext: ['extension'],
|
|
185
|
+
'ext-inner': ['extension-inner'],
|
|
186
|
+
arg: ['argument'],
|
|
187
|
+
'arg-name': ['argument-name'],
|
|
188
|
+
'arg-default': ['argument-default'],
|
|
189
|
+
'arg-redundant': ['argument-redundant'],
|
|
190
|
+
template: ['tpl'],
|
|
191
|
+
'template-name': ['tpl-name'],
|
|
192
|
+
'magic-word': ['parser-function', 'parser-func'],
|
|
193
|
+
'invoke-function': ['invoke-func'],
|
|
194
|
+
'invoke-module': ['invoke-mod'],
|
|
195
|
+
parameter: ['param'],
|
|
196
|
+
'parameter-key': ['param-key'],
|
|
197
|
+
'parameter-value': ['parameter-val', 'param-value', 'param-val'],
|
|
198
|
+
heading: ['header'],
|
|
199
|
+
'heading-title': ['header-title'],
|
|
200
|
+
table: ['tbl'],
|
|
201
|
+
'table-inter': ['tbl-inter'],
|
|
202
|
+
tr: ['table-row', 'tbl-row'],
|
|
203
|
+
td: ['table-cell', 'tbl-cell', 'table-data', 'tbl-data'],
|
|
204
|
+
'double-underscore': ['underscore', 'behavior-switch', 'behaviour-switch'],
|
|
205
|
+
hr: ['horizontal'],
|
|
206
|
+
category: ['category-link', 'cat', 'cat-link'],
|
|
207
|
+
file: ['file-link', 'image', 'image-link', 'img', 'img-link'],
|
|
208
|
+
'image-parameter': ['img-parameter', 'image-param', 'img-param'],
|
|
209
|
+
quote: ['quotes', 'quot', 'apostrophe', 'apostrophes', 'apos'],
|
|
210
|
+
'ext-link': ['external-link'],
|
|
211
|
+
'ext-link-text': ['external-link-text'],
|
|
212
|
+
'ext-link-url': ['external-link-url'],
|
|
213
|
+
'free-ext-link': ['free-external-link', 'magic-link'],
|
|
214
|
+
dd: ['indent', 'indentation'],
|
|
215
|
+
converter: ['convert', 'conversion'],
|
|
216
|
+
'converter-flags': ['convert-flags', 'conversion-flags', 'converter-flag', 'convert-flag', 'conversion-flag'],
|
|
217
|
+
'converter-rule': ['convert-rule', 'conversion-rule'],
|
|
218
|
+
'converter-rule-noconvert': ['convert-rule-noconvert', 'conversion-rule-noconvert'],
|
|
219
|
+
'converter-rule-variant': ['convert-rule-variant', 'conversion-rule-variant'],
|
|
220
|
+
'converter-rule-to': ['convert-rule-to', 'conversion-rule-to'],
|
|
221
|
+
'converter-rule-from': ['convert-rule-from', 'conversion-rule-from'],
|
|
222
|
+
},
|
|
181
223
|
};
|
|
182
224
|
|
|
183
225
|
const /** @type {PropertyDescriptorMap} */ def = {};
|
package/lib/element.js
CHANGED
|
@@ -402,7 +402,8 @@ class AstElement extends AstNode {
|
|
|
402
402
|
),
|
|
403
403
|
[type, ...parts] = plainSelector.trim().split('#'),
|
|
404
404
|
name = parts.join('#');
|
|
405
|
-
return (!type || this.type === type
|
|
405
|
+
return (!type || this.type === type || Boolean(Parser.typeAliases[this.type]?.includes(type)))
|
|
406
|
+
&& (!name || this.name === name)
|
|
406
407
|
&& attributes.every(args => this.matchesAttr(...args));
|
|
407
408
|
}
|
|
408
409
|
/*
|
package/mixin/sol.js
CHANGED
|
@@ -11,14 +11,18 @@ const /** @type {Parser} */ Parser = require('..'),
|
|
|
11
11
|
const sol = constructor => class extends constructor {
|
|
12
12
|
/** @this {Token} */
|
|
13
13
|
prependNewLine() {
|
|
14
|
-
const {previousVisibleSibling} = this;
|
|
15
|
-
return previousVisibleSibling && !String(previousVisibleSibling).endsWith('\n')
|
|
14
|
+
const {previousVisibleSibling = '', parentNode} = this;
|
|
15
|
+
return (previousVisibleSibling || parentNode?.type !== 'root') && !String(previousVisibleSibling).endsWith('\n')
|
|
16
|
+
? '\n'
|
|
17
|
+
: '';
|
|
16
18
|
}
|
|
17
19
|
|
|
18
20
|
/** @this {Token} */
|
|
19
21
|
appendNewLine() {
|
|
20
|
-
const {nextVisibleSibling} = this;
|
|
21
|
-
return nextVisibleSibling && !String(nextVisibleSibling).startsWith('\n')
|
|
22
|
+
const {nextVisibleSibling = '', parentNode} = this;
|
|
23
|
+
return (nextVisibleSibling || parentNode?.type !== 'root') && !String(nextVisibleSibling ?? '').startsWith('\n')
|
|
24
|
+
? '\n'
|
|
25
|
+
: '';
|
|
22
26
|
}
|
|
23
27
|
|
|
24
28
|
toString(ownLine = false) {
|
package/package.json
CHANGED
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
const /** @type {Parser} */ Parser = require('..');
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* @param {string} firstChild
|
|
7
|
+
* @param {accum} accum
|
|
8
|
+
*/
|
|
9
|
+
const parseConverter = (firstChild, config = Parser.getConfig(), accum = []) => {
|
|
10
|
+
const ConverterToken = require('../src/converter'),
|
|
11
|
+
regex1 = /-{/g,
|
|
12
|
+
regex2 = /-{|}-/g,
|
|
13
|
+
/** @type {RegExpExecArray[]} */ stack = [];
|
|
14
|
+
let regex = regex1,
|
|
15
|
+
mt = regex.exec(firstChild);
|
|
16
|
+
while (mt) {
|
|
17
|
+
const {0: syntax, index} = mt;
|
|
18
|
+
if (syntax === '}-') {
|
|
19
|
+
const top = stack.pop(),
|
|
20
|
+
{length} = accum,
|
|
21
|
+
str = firstChild.slice(top.index + 2, index),
|
|
22
|
+
i = str.indexOf('|'),
|
|
23
|
+
[flags, text] = i === -1 ? [[], str] : [str.slice(0, i).split(';'), str.slice(i + 1)],
|
|
24
|
+
temp = text.replace(/(?<=&[#a-z0-9]+);/i, '\x01'),
|
|
25
|
+
variants = `(?:${config.variants.join('|')})`,
|
|
26
|
+
rules = temp.split(new RegExp(`;(?=\\s*(?:${variants}|[^;]*?=>\\s*${variants})\\s*:)`))
|
|
27
|
+
.map(rule => rule.replaceAll('\x01', ';'));
|
|
28
|
+
new ConverterToken(flags, rules, config, accum);
|
|
29
|
+
firstChild = `${firstChild.slice(0, top.index)}\x00${length}v\x7f${firstChild.slice(index + 2)}`;
|
|
30
|
+
if (stack.length === 0) {
|
|
31
|
+
regex = regex1;
|
|
32
|
+
}
|
|
33
|
+
regex.lastIndex = top.index + 3 + String(length).length;
|
|
34
|
+
} else {
|
|
35
|
+
stack.push(mt);
|
|
36
|
+
regex = regex2;
|
|
37
|
+
}
|
|
38
|
+
mt = regex.exec(firstChild);
|
|
39
|
+
}
|
|
40
|
+
return firstChild;
|
|
41
|
+
};
|
|
42
|
+
|
|
43
|
+
Parser.parsers.parseConverter = __filename;
|
|
44
|
+
module.exports = parseConverter;
|
package/src/arg.js
CHANGED
|
@@ -75,13 +75,13 @@ class ArgToken extends Token {
|
|
|
75
75
|
|
|
76
76
|
/** @returns {[number, string][]} */
|
|
77
77
|
plain() {
|
|
78
|
-
return this.
|
|
78
|
+
return this.childNodes.length > 1 ? this.children[1].plain() : [];
|
|
79
79
|
}
|
|
80
80
|
|
|
81
81
|
/** @complexity `n` */
|
|
82
82
|
removeRedundant() {
|
|
83
83
|
Parser.run(() => {
|
|
84
|
-
for (let i = this.
|
|
84
|
+
for (let i = this.childNodes.length - 1; i > 1; i--) {
|
|
85
85
|
super.removeAt(i);
|
|
86
86
|
}
|
|
87
87
|
});
|
|
@@ -100,8 +100,8 @@ class ArgToken extends Token {
|
|
|
100
100
|
}
|
|
101
101
|
|
|
102
102
|
/** @param {Token} token */
|
|
103
|
-
insertAt(token, i = this.
|
|
104
|
-
const j = i < 0 ? i + this.
|
|
103
|
+
insertAt(token, i = this.childNodes.length) {
|
|
104
|
+
const j = i < 0 ? i + this.childNodes.length : i;
|
|
105
105
|
if (j > 1 && !Parser.running) {
|
|
106
106
|
throw new RangeError(`${this.constructor.name} 不可插入 arg-redundant 子节点!`);
|
|
107
107
|
}
|
|
@@ -117,7 +117,7 @@ class ArgToken extends Token {
|
|
|
117
117
|
name = String(name);
|
|
118
118
|
const root = Parser.parse(`{{{${name}}}}`, this.getAttribute('include'), 2, this.getAttribute('config')),
|
|
119
119
|
{childNodes: {length}, firstElementChild} = root;
|
|
120
|
-
if (length !== 1 || firstElementChild?.type !== 'arg' || firstElementChild.
|
|
120
|
+
if (length !== 1 || firstElementChild?.type !== 'arg' || firstElementChild.childNodes.length !== 1) {
|
|
121
121
|
throw new SyntaxError(`非法的参数名称:${noWrap(name)}`);
|
|
122
122
|
}
|
|
123
123
|
const newName = firstElementChild.firstElementChild;
|
|
@@ -131,7 +131,7 @@ class ArgToken extends Token {
|
|
|
131
131
|
value = String(value);
|
|
132
132
|
const root = Parser.parse(`{{{|${value}}}}`, this.getAttribute('include'), 2, this.getAttribute('config')),
|
|
133
133
|
{childNodes: {length}, firstElementChild} = root;
|
|
134
|
-
if (length !== 1 || firstElementChild?.type !== 'arg' || firstElementChild.
|
|
134
|
+
if (length !== 1 || firstElementChild?.type !== 'arg' || firstElementChild.childNodes.length !== 2) {
|
|
135
135
|
throw new SyntaxError(`非法的参数预设值:${noWrap(value)}`);
|
|
136
136
|
}
|
|
137
137
|
const [, oldDefault] = this.children,
|
package/src/attribute.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
3
|
const {externalUse} = require('../util/debug'),
|
|
4
|
-
{toCase, removeComment} = require('../util/string'),
|
|
4
|
+
{toCase, removeComment, normalizeSpace} = require('../util/string'),
|
|
5
5
|
/** @type {Parser} */ Parser = require('..'),
|
|
6
6
|
Token = require('.');
|
|
7
7
|
|
|
@@ -241,13 +241,13 @@ class AttributeToken extends Token {
|
|
|
241
241
|
}
|
|
242
242
|
|
|
243
243
|
#leadingSpace(str = super.toString()) {
|
|
244
|
-
return str && !/^\s/.test(str) ? ' ' : '';
|
|
244
|
+
return this.type !== 'table-attr' && str && !/^\s/.test(str) ? ' ' : '';
|
|
245
245
|
}
|
|
246
246
|
|
|
247
|
+
/** @this {AttributeToken & Token} */
|
|
247
248
|
toString() {
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
return this.type === 'table-attr' ? str.replaceAll('\n', ' ') : str;
|
|
249
|
+
const str = this.type === 'table-attr' ? normalizeSpace(this) : super.toString();
|
|
250
|
+
return `${this.#leadingSpace(str)}${str}`;
|
|
251
251
|
}
|
|
252
252
|
|
|
253
253
|
getPadding() {
|
|
@@ -257,7 +257,7 @@ class AttributeToken extends Token {
|
|
|
257
257
|
text() {
|
|
258
258
|
let str = this.#updateFromAttr();
|
|
259
259
|
str = `${this.#leadingSpace(str)}${str}`;
|
|
260
|
-
return this.type === 'table-attr' ? str
|
|
260
|
+
return this.type === 'table-attr' ? normalizeSpace(str) : str;
|
|
261
261
|
}
|
|
262
262
|
|
|
263
263
|
/** @returns {[number, string][]} */
|
package/src/converter.js
ADDED
|
@@ -0,0 +1,135 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
const {text} = require('../util/string'),
|
|
4
|
+
/** @type {Parser} */ Parser = require('..'),
|
|
5
|
+
Token = require('.'),
|
|
6
|
+
ConverterFlagsToken = require('./converterFlags'),
|
|
7
|
+
ConverterRuleToken = require('./converterRule');
|
|
8
|
+
|
|
9
|
+
/**
|
|
10
|
+
* 转换
|
|
11
|
+
* @classdesc `{childNodes: [ConverterFlagsToken, ...ConverterRuleToken]}`
|
|
12
|
+
*/
|
|
13
|
+
class ConverterToken extends Token {
|
|
14
|
+
type = 'converter';
|
|
15
|
+
|
|
16
|
+
/**
|
|
17
|
+
* @param {string[]} flags
|
|
18
|
+
* @param {string[]} rules
|
|
19
|
+
* @param {accum} accum
|
|
20
|
+
*/
|
|
21
|
+
constructor(flags, rules, config = Parser.getConfig(), accum = []) {
|
|
22
|
+
super(undefined, config, false, accum);
|
|
23
|
+
this.append(new ConverterFlagsToken(flags, config, accum));
|
|
24
|
+
if (rules.length) {
|
|
25
|
+
const [firstRule] = rules,
|
|
26
|
+
hasColon = firstRule.includes(':'),
|
|
27
|
+
firstRuleToken = new ConverterRuleToken(firstRule, hasColon, config, accum);
|
|
28
|
+
if (hasColon && firstRuleToken.childNodes.length === 1) {
|
|
29
|
+
this.appendChild(new ConverterRuleToken(rules.join(';'), false, config, accum));
|
|
30
|
+
} else {
|
|
31
|
+
this.append(
|
|
32
|
+
firstRuleToken,
|
|
33
|
+
...rules.slice(1).map(rule => new ConverterRuleToken(rule, true, config, accum)),
|
|
34
|
+
);
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
this.protectChildren(0);
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
cloneNode() {
|
|
41
|
+
const [flags, ...rules] = this.cloneChildren(),
|
|
42
|
+
token = Parser.run(() => new ConverterToken([], [], this.getAttribute('config')));
|
|
43
|
+
token.firstElementChild.safeReplaceWith(flags);
|
|
44
|
+
token.append(...rules);
|
|
45
|
+
return token;
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
toString() {
|
|
49
|
+
const [flags, ...rules] = this.children;
|
|
50
|
+
return `-{${flags.toString()}${flags.childNodes.length ? '|' : ''}${rules.map(String).join(';')}}-`;
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
getPadding() {
|
|
54
|
+
return 2;
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
/** @param {number} i */
|
|
58
|
+
getGaps(i = 0) {
|
|
59
|
+
i = i < 0 ? i + this.childNodes.length : i;
|
|
60
|
+
return i || this.firstElementChild.childNodes.length ? 1 : 0;
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
text() {
|
|
64
|
+
const [flags, ...rules] = this.children;
|
|
65
|
+
return `-{${flags.text()}|${text(rules, ';')}}-`;
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
/** @returns {[number, string][]} */
|
|
69
|
+
plain() {
|
|
70
|
+
return this.children.slice(1).flatMap(child => child.plain());
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
/** @this {ConverterToken & {firstChild: ConverterFlagsToken}} */
|
|
74
|
+
getAllFlags() {
|
|
75
|
+
return this.firstChild.getAllFlags();
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
/** @this {ConverterToken & {firstChild: ConverterFlagsToken}} */
|
|
79
|
+
getEffectiveFlags() {
|
|
80
|
+
return this.firstChild.getEffectiveFlags();
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
/** @this {ConverterToken & {firstChild: ConverterFlagsToken}} */
|
|
84
|
+
getUnknownFlags() {
|
|
85
|
+
return this.firstChild.getUnknownFlags();
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
/**
|
|
89
|
+
* @this {ConverterToken & {firstChild: ConverterFlagsToken}}
|
|
90
|
+
* @param {string} flag
|
|
91
|
+
*/
|
|
92
|
+
hasFlag(flag) {
|
|
93
|
+
return this.firstChild.hasFlag(flag);
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
/**
|
|
97
|
+
* @this {ConverterToken & {firstChild: ConverterFlagsToken}}
|
|
98
|
+
* @param {string} flag
|
|
99
|
+
*/
|
|
100
|
+
hasEffectiveFlag(flag) {
|
|
101
|
+
return this.firstChild.hasEffectiveFlag(flag);
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
/**
|
|
105
|
+
* @this {ConverterToken & {firstChild: ConverterFlagsToken}}
|
|
106
|
+
* @param {string} flag
|
|
107
|
+
*/
|
|
108
|
+
removeFlag(flag) {
|
|
109
|
+
this.firstChild.removeFlag(flag);
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
/**
|
|
113
|
+
* @this {ConverterToken & {firstChild: ConverterFlagsToken}}
|
|
114
|
+
* @param {string} flag
|
|
115
|
+
*/
|
|
116
|
+
setFlag(flag) {
|
|
117
|
+
this.firstChild.setFlag(flag);
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
/**
|
|
121
|
+
* @this {ConverterToken & {firstChild: ConverterFlagsToken}}
|
|
122
|
+
* @param {string} flag
|
|
123
|
+
*/
|
|
124
|
+
toggleFlag(flag) {
|
|
125
|
+
this.firstChild.toggleFlag(flag);
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
/** @this {ConverterToken & {children: [ConverterFlagsToken, ConverterRuleToken]}} */
|
|
129
|
+
get noConvert() {
|
|
130
|
+
return this.childNodes.length < 3 && !this.children[1]?.variant;
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
Parser.classes.ConverterToken = __filename;
|
|
135
|
+
module.exports = ConverterToken;
|