@lowlighter/xml 6.0.0 → 8.0.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 +77 -22
- package/_parser.d.ts +45 -0
- package/_parser.js +266 -0
- package/_types.d.ts +29 -0
- package/_types.js +2 -0
- package/bench/assets/medium.xml +1 -1
- package/bench/assets/small.xml +1 -1
- package/bench/bench.ts +6 -2
- package/deno.lock +17 -97
- package/mod.d.ts +3 -0
- package/mod.js +3 -0
- package/package.json +27 -23
- package/parse.d.ts +81 -0
- package/parse.js +227 -0
- package/stringify.d.ts +79 -0
- package/stringify.js +263 -0
- package/wasm/parse.d.ts +77 -0
- package/wasm/parse.js +123 -0
- package/wasm/wasm_xml_parser.js +3 -0
- package/_types.ts +0 -49
- package/_types_test.ts +0 -1
- package/deno.jsonc +0 -98
- package/mod.mjs +0 -1
- package/mod.ts +0 -3
- package/mod_test.ts +0 -1
- package/parse.mjs +0 -1
- package/parse.ts +0 -442
- package/parse_test.ts +0 -1303
- package/stringify.mjs +0 -1
- package/stringify.ts +0 -287
- package/stringify_test.ts +0 -303
- package/wasm_xml_parser/Cargo.lock +0 -159
- package/wasm_xml_parser/Cargo.toml +0 -16
- package/wasm_xml_parser/src/lib.rs +0 -234
- package/wasm_xml_parser/wasm_xml_parser.js +0 -2
package/parse_test.ts
DELETED
|
@@ -1,1303 +0,0 @@
|
|
|
1
|
-
import { parse } from "./parse.ts"
|
|
2
|
-
import { expect, test, type testing } from "@libs/testing"
|
|
3
|
-
import { fromFileUrl } from "@std/path/from-file-url"
|
|
4
|
-
import { exists } from "@std/fs/exists"
|
|
5
|
-
|
|
6
|
-
//Huge xml file generator
|
|
7
|
-
export async function write(size: number) {
|
|
8
|
-
const path = fromFileUrl(import.meta.resolve(`./bench/assets/x-${size}x-large.xml`))
|
|
9
|
-
if (await exists(path)) {
|
|
10
|
-
return
|
|
11
|
-
}
|
|
12
|
-
using file = await Deno.open(path, { write: true, create: true })
|
|
13
|
-
const encoder = new TextEncoder()
|
|
14
|
-
await file.write(encoder.encode("<root>"))
|
|
15
|
-
for (let i = 0; i < (2 ** size) * 15500; i++) {
|
|
16
|
-
await file.write(encoder.encode(`<child>${Math.random()}</child>`))
|
|
17
|
-
}
|
|
18
|
-
await file.write(encoder.encode("</root>"))
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
test("all")("`parse()` xml syntax tag", () =>
|
|
22
|
-
expect(
|
|
23
|
-
parse(`
|
|
24
|
-
<root>hello world</root>
|
|
25
|
-
`),
|
|
26
|
-
).toEqual(
|
|
27
|
-
{
|
|
28
|
-
root: "hello world",
|
|
29
|
-
},
|
|
30
|
-
))
|
|
31
|
-
|
|
32
|
-
test("all")("`parse()` xml syntax tag with attributes", () =>
|
|
33
|
-
expect(
|
|
34
|
-
parse(`
|
|
35
|
-
<root lang="en" type="greeting">hello world</root>
|
|
36
|
-
`),
|
|
37
|
-
).toEqual(
|
|
38
|
-
{
|
|
39
|
-
root: {
|
|
40
|
-
"@lang": "en",
|
|
41
|
-
"@type": "greeting",
|
|
42
|
-
"#text": "hello world",
|
|
43
|
-
},
|
|
44
|
-
},
|
|
45
|
-
))
|
|
46
|
-
|
|
47
|
-
test("all")("`parse()` xml syntax self-closing tag", () =>
|
|
48
|
-
expect(
|
|
49
|
-
parse(`
|
|
50
|
-
<root/>
|
|
51
|
-
`),
|
|
52
|
-
).toEqual(
|
|
53
|
-
{
|
|
54
|
-
root: null,
|
|
55
|
-
},
|
|
56
|
-
))
|
|
57
|
-
|
|
58
|
-
test("all")("`parse()` xml syntax self-closing with attributes", () =>
|
|
59
|
-
expect(
|
|
60
|
-
parse(`
|
|
61
|
-
<root lang="en" type="greeting" text="hello world"></root>
|
|
62
|
-
`),
|
|
63
|
-
).toEqual(
|
|
64
|
-
{
|
|
65
|
-
root: {
|
|
66
|
-
"@lang": "en",
|
|
67
|
-
"@type": "greeting",
|
|
68
|
-
"@text": "hello world",
|
|
69
|
-
},
|
|
70
|
-
},
|
|
71
|
-
))
|
|
72
|
-
|
|
73
|
-
test("all")("`parse()` xml syntax empty tag", () =>
|
|
74
|
-
expect(
|
|
75
|
-
parse(`
|
|
76
|
-
<root></root>
|
|
77
|
-
`),
|
|
78
|
-
).toEqual(
|
|
79
|
-
{
|
|
80
|
-
root: null,
|
|
81
|
-
},
|
|
82
|
-
))
|
|
83
|
-
|
|
84
|
-
test("all")("`parse()` xml syntax empty tag with attributes", () =>
|
|
85
|
-
expect(
|
|
86
|
-
parse(`
|
|
87
|
-
<root type="test"></root>
|
|
88
|
-
`),
|
|
89
|
-
).toEqual(
|
|
90
|
-
{
|
|
91
|
-
root: {
|
|
92
|
-
"@type": "test",
|
|
93
|
-
},
|
|
94
|
-
},
|
|
95
|
-
))
|
|
96
|
-
|
|
97
|
-
test("all")("`parse()` xml syntax simple tree", () =>
|
|
98
|
-
expect(
|
|
99
|
-
parse(`
|
|
100
|
-
<root>
|
|
101
|
-
<child>
|
|
102
|
-
<subchild>.....</subchild>
|
|
103
|
-
</child>
|
|
104
|
-
</root>
|
|
105
|
-
`),
|
|
106
|
-
).toEqual(
|
|
107
|
-
{
|
|
108
|
-
root: {
|
|
109
|
-
child: {
|
|
110
|
-
subchild: ".....",
|
|
111
|
-
},
|
|
112
|
-
},
|
|
113
|
-
},
|
|
114
|
-
))
|
|
115
|
-
|
|
116
|
-
test("all")("`parse()` xml syntax simple tree with same tags", () =>
|
|
117
|
-
expect(
|
|
118
|
-
parse(`
|
|
119
|
-
<root>
|
|
120
|
-
<child>world</child>
|
|
121
|
-
<child>monde</child>
|
|
122
|
-
<child>世界</child>
|
|
123
|
-
<child>🌏</child>
|
|
124
|
-
</root>
|
|
125
|
-
`),
|
|
126
|
-
).toEqual(
|
|
127
|
-
{
|
|
128
|
-
root: {
|
|
129
|
-
child: ["world", "monde", "世界", "🌏"],
|
|
130
|
-
},
|
|
131
|
-
},
|
|
132
|
-
))
|
|
133
|
-
|
|
134
|
-
test("all")("`parse()` xml syntax simple tree with same tags and attributes", () =>
|
|
135
|
-
expect(
|
|
136
|
-
parse(`
|
|
137
|
-
<root>
|
|
138
|
-
<child lang="en">world</child>
|
|
139
|
-
<child lang="fr">monde</child>
|
|
140
|
-
<child lang="zh">世界</child>
|
|
141
|
-
<child lang="🦕">🌏</child>
|
|
142
|
-
</root>
|
|
143
|
-
`),
|
|
144
|
-
).toEqual(
|
|
145
|
-
{
|
|
146
|
-
root: {
|
|
147
|
-
child: [
|
|
148
|
-
{ "@lang": "en", "#text": "world" },
|
|
149
|
-
{ "@lang": "fr", "#text": "monde" },
|
|
150
|
-
{ "@lang": "zh", "#text": "世界" },
|
|
151
|
-
{ "@lang": "🦕", "#text": "🌏" },
|
|
152
|
-
],
|
|
153
|
-
},
|
|
154
|
-
},
|
|
155
|
-
))
|
|
156
|
-
|
|
157
|
-
test("all")("`parse()` xml syntax simple tree with nested tags of same name", () =>
|
|
158
|
-
expect(
|
|
159
|
-
parse(`
|
|
160
|
-
<root>
|
|
161
|
-
<child>
|
|
162
|
-
<child>
|
|
163
|
-
<child>
|
|
164
|
-
<child/>
|
|
165
|
-
</child>
|
|
166
|
-
</child>
|
|
167
|
-
</child>
|
|
168
|
-
</root>
|
|
169
|
-
`),
|
|
170
|
-
).toEqual(
|
|
171
|
-
{
|
|
172
|
-
root: {
|
|
173
|
-
child: { child: { child: { child: null } } },
|
|
174
|
-
},
|
|
175
|
-
},
|
|
176
|
-
))
|
|
177
|
-
|
|
178
|
-
test("all")("`parse()` xml syntax mixed content", () =>
|
|
179
|
-
expect(
|
|
180
|
-
parse(`
|
|
181
|
-
<root>some <b>bold</b> text</root>
|
|
182
|
-
`),
|
|
183
|
-
).toEqual(
|
|
184
|
-
{
|
|
185
|
-
root: {
|
|
186
|
-
"#text": "some bold text",
|
|
187
|
-
b: "bold",
|
|
188
|
-
},
|
|
189
|
-
},
|
|
190
|
-
))
|
|
191
|
-
|
|
192
|
-
test("all")("`parse()` xml syntax nested mixed content", () =>
|
|
193
|
-
expect(
|
|
194
|
-
parse(`
|
|
195
|
-
<root>some <b>bold <i>italic</i> </b> text</root>
|
|
196
|
-
`),
|
|
197
|
-
).toEqual(
|
|
198
|
-
{
|
|
199
|
-
root: {
|
|
200
|
-
"#text": "some bold italic text",
|
|
201
|
-
b: {
|
|
202
|
-
"#text": "bold italic",
|
|
203
|
-
i: "italic",
|
|
204
|
-
},
|
|
205
|
-
},
|
|
206
|
-
},
|
|
207
|
-
))
|
|
208
|
-
|
|
209
|
-
test("all")("`parse()` xml syntax xml prolog", () =>
|
|
210
|
-
expect(
|
|
211
|
-
parse(
|
|
212
|
-
`
|
|
213
|
-
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
|
214
|
-
<root></root>
|
|
215
|
-
`,
|
|
216
|
-
),
|
|
217
|
-
).toEqual(
|
|
218
|
-
{
|
|
219
|
-
"@version": "1.0",
|
|
220
|
-
"@encoding": "UTF-8",
|
|
221
|
-
"@standalone": "yes",
|
|
222
|
-
root: null,
|
|
223
|
-
},
|
|
224
|
-
))
|
|
225
|
-
|
|
226
|
-
test("all")("`parse()` xml syntax xml stylesheet", () =>
|
|
227
|
-
expect(
|
|
228
|
-
parse(
|
|
229
|
-
`
|
|
230
|
-
<?xml version="1.0" encoding="UTF-8"?>
|
|
231
|
-
<?xml-stylesheet href="styles1.xsl" type="text/xsl"?>
|
|
232
|
-
<?xml-stylesheet href="styles2.xsl" type="text/xsl"?>
|
|
233
|
-
<?xml-stylesheet href="styles3.xsl" type="text/xsl"?>
|
|
234
|
-
<root></root>
|
|
235
|
-
`,
|
|
236
|
-
),
|
|
237
|
-
).toEqual(
|
|
238
|
-
{
|
|
239
|
-
"@version": "1.0",
|
|
240
|
-
"@encoding": "UTF-8",
|
|
241
|
-
"#instructions": {
|
|
242
|
-
"xml-stylesheet": [{
|
|
243
|
-
"@href": "styles1.xsl",
|
|
244
|
-
"@type": "text/xsl",
|
|
245
|
-
}, {
|
|
246
|
-
"@href": "styles2.xsl",
|
|
247
|
-
"@type": "text/xsl",
|
|
248
|
-
}, {
|
|
249
|
-
"@href": "styles3.xsl",
|
|
250
|
-
"@type": "text/xsl",
|
|
251
|
-
}],
|
|
252
|
-
},
|
|
253
|
-
root: null,
|
|
254
|
-
},
|
|
255
|
-
))
|
|
256
|
-
|
|
257
|
-
test("all")("`parse()` xml syntax doctype", () =>
|
|
258
|
-
expect(
|
|
259
|
-
parse(
|
|
260
|
-
`
|
|
261
|
-
<!DOCTYPE type "quoted attribute">
|
|
262
|
-
<root></root>
|
|
263
|
-
`,
|
|
264
|
-
),
|
|
265
|
-
).toEqual(
|
|
266
|
-
{
|
|
267
|
-
"#doctype": {
|
|
268
|
-
"@type": "",
|
|
269
|
-
"@quoted attribute": "",
|
|
270
|
-
},
|
|
271
|
-
root: null,
|
|
272
|
-
},
|
|
273
|
-
))
|
|
274
|
-
|
|
275
|
-
test("all")("`parse()` xml syntax doctype with element", () =>
|
|
276
|
-
expect(
|
|
277
|
-
parse(
|
|
278
|
-
`
|
|
279
|
-
<!DOCTYPE type "quoted attribute"
|
|
280
|
-
[
|
|
281
|
-
<!ELEMENT note (to,from,heading,body)>
|
|
282
|
-
<!ELEMENT to (#PCDATA)>
|
|
283
|
-
<!ELEMENT from (#PCDATA)>
|
|
284
|
-
<!ELEMENT heading (#PCDATA)>
|
|
285
|
-
<!ELEMENT body (#PCDATA)>
|
|
286
|
-
]
|
|
287
|
-
>
|
|
288
|
-
<root></root>
|
|
289
|
-
`,
|
|
290
|
-
),
|
|
291
|
-
).toEqual(
|
|
292
|
-
{
|
|
293
|
-
"#doctype": {
|
|
294
|
-
"@type": "",
|
|
295
|
-
"@quoted attribute": "",
|
|
296
|
-
note: "to,from,heading,body",
|
|
297
|
-
to: "#PCDATA",
|
|
298
|
-
from: "#PCDATA",
|
|
299
|
-
heading: "#PCDATA",
|
|
300
|
-
body: "#PCDATA",
|
|
301
|
-
},
|
|
302
|
-
root: null,
|
|
303
|
-
},
|
|
304
|
-
))
|
|
305
|
-
|
|
306
|
-
test("all")("`parse()` xml syntax case sensitive", () =>
|
|
307
|
-
expect(
|
|
308
|
-
parse(`
|
|
309
|
-
<root>
|
|
310
|
-
<child>
|
|
311
|
-
<subchild>1</subchild>
|
|
312
|
-
<subchild>2</subchild>
|
|
313
|
-
</child>
|
|
314
|
-
<Child>
|
|
315
|
-
<subchild></subchild>
|
|
316
|
-
<SubChild></SubChild>
|
|
317
|
-
</Child>
|
|
318
|
-
<CHILD></CHILD>
|
|
319
|
-
</root>
|
|
320
|
-
`),
|
|
321
|
-
).toEqual(
|
|
322
|
-
{
|
|
323
|
-
root: {
|
|
324
|
-
child: {
|
|
325
|
-
subchild: ["1", "2"],
|
|
326
|
-
},
|
|
327
|
-
Child: {
|
|
328
|
-
subchild: null,
|
|
329
|
-
SubChild: null,
|
|
330
|
-
},
|
|
331
|
-
CHILD: null,
|
|
332
|
-
},
|
|
333
|
-
},
|
|
334
|
-
))
|
|
335
|
-
|
|
336
|
-
test("all")("`parse()` xml syntax defined entities", () =>
|
|
337
|
-
expect(
|
|
338
|
-
parse(`
|
|
339
|
-
<root>
|
|
340
|
-
< > & ' "
|
|
341
|
-
</root>
|
|
342
|
-
`),
|
|
343
|
-
).toEqual(
|
|
344
|
-
{
|
|
345
|
-
root: `< > & ' "`,
|
|
346
|
-
},
|
|
347
|
-
))
|
|
348
|
-
|
|
349
|
-
test("all")("`parse()` xml syntax decimal entity reference", () =>
|
|
350
|
-
expect(
|
|
351
|
-
parse(`
|
|
352
|
-
<root>
|
|
353
|
-
&
|
|
354
|
-
</root>
|
|
355
|
-
`),
|
|
356
|
-
).toEqual(
|
|
357
|
-
{
|
|
358
|
-
root: "&",
|
|
359
|
-
},
|
|
360
|
-
))
|
|
361
|
-
|
|
362
|
-
test("all")("`parse()` xml syntax hexadecimal entity reference", () =>
|
|
363
|
-
expect(
|
|
364
|
-
parse(`
|
|
365
|
-
<root>
|
|
366
|
-
&
|
|
367
|
-
</root>
|
|
368
|
-
`),
|
|
369
|
-
).toEqual(
|
|
370
|
-
{
|
|
371
|
-
root: "&",
|
|
372
|
-
},
|
|
373
|
-
))
|
|
374
|
-
|
|
375
|
-
test("all")("`parse()` xml syntax comments", () =>
|
|
376
|
-
expect(
|
|
377
|
-
parse(`
|
|
378
|
-
<root>
|
|
379
|
-
<!-- COMMENT 1 -->
|
|
380
|
-
<child type="test" />
|
|
381
|
-
<!-- COMMENT 2 -->
|
|
382
|
-
<!--+++++++++++++++++++++-->
|
|
383
|
-
</root>
|
|
384
|
-
`),
|
|
385
|
-
).toEqual(
|
|
386
|
-
{
|
|
387
|
-
root: {
|
|
388
|
-
"#comments": ["COMMENT 1", "COMMENT 2", "+++++++++++++++++++++"],
|
|
389
|
-
child: {
|
|
390
|
-
"@type": "test",
|
|
391
|
-
},
|
|
392
|
-
},
|
|
393
|
-
},
|
|
394
|
-
))
|
|
395
|
-
|
|
396
|
-
test("all")("`parse()` xml syntax comments in-between text nodes", () =>
|
|
397
|
-
expect(
|
|
398
|
-
parse(`
|
|
399
|
-
<root>
|
|
400
|
-
Hello
|
|
401
|
-
<!-- COMMENT -->
|
|
402
|
-
world
|
|
403
|
-
</root>
|
|
404
|
-
`),
|
|
405
|
-
).toEqual(
|
|
406
|
-
{
|
|
407
|
-
root: {
|
|
408
|
-
"#comments": ["COMMENT"],
|
|
409
|
-
"#text": "Hello world",
|
|
410
|
-
},
|
|
411
|
-
},
|
|
412
|
-
))
|
|
413
|
-
|
|
414
|
-
test("all")("`parse()` xml syntax white spaces preserved", () =>
|
|
415
|
-
expect(
|
|
416
|
-
parse(`
|
|
417
|
-
<root>
|
|
418
|
-
Hello world how
|
|
419
|
-
are you?
|
|
420
|
-
</root>
|
|
421
|
-
`),
|
|
422
|
-
).toEqual(
|
|
423
|
-
{
|
|
424
|
-
root: `Hello world how
|
|
425
|
-
are you?`,
|
|
426
|
-
},
|
|
427
|
-
))
|
|
428
|
-
|
|
429
|
-
test("all")("`parse()` xml syntax CDATA", () =>
|
|
430
|
-
expect(
|
|
431
|
-
parse(`
|
|
432
|
-
<root>
|
|
433
|
-
<script type="text/javascript"><![CDATA[function match(a,b) {
|
|
434
|
-
if (a < b && a < 0) { return 1; }
|
|
435
|
-
else { return 0; }
|
|
436
|
-
}]]></script>
|
|
437
|
-
</root>
|
|
438
|
-
`),
|
|
439
|
-
).toEqual(
|
|
440
|
-
{
|
|
441
|
-
root: {
|
|
442
|
-
script: {
|
|
443
|
-
"@type": "text/javascript",
|
|
444
|
-
"#text": `function match(a,b) {
|
|
445
|
-
if (a < b && a < 0) { return 1; }
|
|
446
|
-
else { return 0; }
|
|
447
|
-
}`,
|
|
448
|
-
},
|
|
449
|
-
},
|
|
450
|
-
},
|
|
451
|
-
))
|
|
452
|
-
|
|
453
|
-
test("all")("`parse()` xml syntax mixed content with CDATA", () =>
|
|
454
|
-
expect(
|
|
455
|
-
parse(`
|
|
456
|
-
<root>
|
|
457
|
-
<script type="text/javascript">this is a <b>test</b> <![CDATA[function match(a,b) {
|
|
458
|
-
if (a < b && a < 0) { return 1; }
|
|
459
|
-
else { return 0; }
|
|
460
|
-
}]]></script>
|
|
461
|
-
</root>
|
|
462
|
-
`),
|
|
463
|
-
).toEqual(
|
|
464
|
-
{
|
|
465
|
-
root: {
|
|
466
|
-
script: {
|
|
467
|
-
"@type": "text/javascript",
|
|
468
|
-
"#text": `this is a test function match(a,b) {
|
|
469
|
-
if (a < b && a < 0) { return 1; }
|
|
470
|
-
else { return 0; }
|
|
471
|
-
}`,
|
|
472
|
-
b: "test",
|
|
473
|
-
},
|
|
474
|
-
},
|
|
475
|
-
},
|
|
476
|
-
))
|
|
477
|
-
|
|
478
|
-
test("all")("`parse()` xml syntax with multiple CDATA's", () =>
|
|
479
|
-
expect(
|
|
480
|
-
parse(`
|
|
481
|
-
<root>
|
|
482
|
-
<text><![CDATA[ a ]]></text>
|
|
483
|
-
<text><![CDATA[ b ]]></text>
|
|
484
|
-
</root>`),
|
|
485
|
-
).toEqual(
|
|
486
|
-
{
|
|
487
|
-
root: {
|
|
488
|
-
text: [
|
|
489
|
-
"a",
|
|
490
|
-
"b",
|
|
491
|
-
],
|
|
492
|
-
},
|
|
493
|
-
},
|
|
494
|
-
))
|
|
495
|
-
|
|
496
|
-
test("all")("`parse()` xml space preserve", () =>
|
|
497
|
-
expect(
|
|
498
|
-
parse(`
|
|
499
|
-
<root>
|
|
500
|
-
<text xml:space="preserve"> hello<b> the</b> world </text>
|
|
501
|
-
</root>`),
|
|
502
|
-
).toEqual(
|
|
503
|
-
{
|
|
504
|
-
root: {
|
|
505
|
-
text: {
|
|
506
|
-
"#text": " hello the world ",
|
|
507
|
-
"@xml:space": "preserve",
|
|
508
|
-
b: "the",
|
|
509
|
-
},
|
|
510
|
-
},
|
|
511
|
-
},
|
|
512
|
-
))
|
|
513
|
-
|
|
514
|
-
//Errors checks
|
|
515
|
-
|
|
516
|
-
test("all")("`parse()` xml syntax unique root", () =>
|
|
517
|
-
expect(() =>
|
|
518
|
-
parse(`
|
|
519
|
-
<root>
|
|
520
|
-
<child>
|
|
521
|
-
<subchild>.....</subchild>
|
|
522
|
-
</child>
|
|
523
|
-
</root>
|
|
524
|
-
<root>
|
|
525
|
-
<child>
|
|
526
|
-
<subchild>.....</subchild>
|
|
527
|
-
</child>
|
|
528
|
-
</root>
|
|
529
|
-
`)
|
|
530
|
-
).toThrow(SyntaxError))
|
|
531
|
-
|
|
532
|
-
test("all")("`parse()` xml syntax closing tag", () =>
|
|
533
|
-
expect(() =>
|
|
534
|
-
parse(`
|
|
535
|
-
<root>
|
|
536
|
-
<child>
|
|
537
|
-
</root>
|
|
538
|
-
`)
|
|
539
|
-
).toThrow(SyntaxError))
|
|
540
|
-
|
|
541
|
-
test("all")("`parse()` xml syntax closing properly nested", () =>
|
|
542
|
-
expect(() =>
|
|
543
|
-
parse(`
|
|
544
|
-
<root>
|
|
545
|
-
<child><subchild></child></subchild>
|
|
546
|
-
</root>
|
|
547
|
-
`)
|
|
548
|
-
).toThrow(SyntaxError))
|
|
549
|
-
|
|
550
|
-
test("all")("`parse()` xml syntax attributes quoted", () =>
|
|
551
|
-
expect(() =>
|
|
552
|
-
parse(`
|
|
553
|
-
<root>
|
|
554
|
-
<child test=hey></child>
|
|
555
|
-
</root>
|
|
556
|
-
`)
|
|
557
|
-
).toThrow(SyntaxError))
|
|
558
|
-
|
|
559
|
-
test("all")("`parse()` xml syntax attributes properly quoted", () =>
|
|
560
|
-
expect(() =>
|
|
561
|
-
parse(`
|
|
562
|
-
<root>
|
|
563
|
-
<child test="hey></child>
|
|
564
|
-
</root>
|
|
565
|
-
`)
|
|
566
|
-
).toThrow(SyntaxError))
|
|
567
|
-
|
|
568
|
-
test("all")("`parse()` xml syntax first character", () => {
|
|
569
|
-
expect(() => parse(`a>1</a>`)).toThrow(SyntaxError)
|
|
570
|
-
expect(() => parse(`xml`)).toThrow(SyntaxError)
|
|
571
|
-
expect(() => parse(`""`)).toThrow(SyntaxError)
|
|
572
|
-
expect(() => parse(`{a: 1}`)).toThrow(SyntaxError)
|
|
573
|
-
})
|
|
574
|
-
|
|
575
|
-
test("all")("`parse()` wasm crashed", () => {
|
|
576
|
-
expect(() => parse(Symbol("Expected error") as testing)).toThrow(EvalError)
|
|
577
|
-
})
|
|
578
|
-
|
|
579
|
-
//Example below were taken from https://www.w3schools.com/xml/default.asp
|
|
580
|
-
|
|
581
|
-
test("all")("`parse()` xml example w3schools.com#1", () =>
|
|
582
|
-
expect(
|
|
583
|
-
parse(`
|
|
584
|
-
<note>
|
|
585
|
-
<to>Tove</to>
|
|
586
|
-
<from>Jani</from>
|
|
587
|
-
<heading>Reminder</heading>
|
|
588
|
-
<body>Don't forget me this weekend!</body>
|
|
589
|
-
</note>
|
|
590
|
-
`),
|
|
591
|
-
).toEqual(
|
|
592
|
-
{
|
|
593
|
-
note: {
|
|
594
|
-
to: "Tove",
|
|
595
|
-
from: "Jani",
|
|
596
|
-
heading: "Reminder",
|
|
597
|
-
body: "Don't forget me this weekend!",
|
|
598
|
-
},
|
|
599
|
-
},
|
|
600
|
-
))
|
|
601
|
-
|
|
602
|
-
test("all")("`parse()` xml example w3schools.com#2", () =>
|
|
603
|
-
expect(
|
|
604
|
-
parse(`
|
|
605
|
-
<note>
|
|
606
|
-
<date>2015-09-01</date>
|
|
607
|
-
<hour>08:30</hour>
|
|
608
|
-
<to>Tove</to>
|
|
609
|
-
<from>Jani</from>
|
|
610
|
-
<body>Don't forget me this weekend!</body>
|
|
611
|
-
</note>
|
|
612
|
-
`),
|
|
613
|
-
).toEqual(
|
|
614
|
-
{
|
|
615
|
-
note: {
|
|
616
|
-
date: "2015-09-01",
|
|
617
|
-
hour: "08:30",
|
|
618
|
-
to: "Tove",
|
|
619
|
-
from: "Jani",
|
|
620
|
-
body: "Don't forget me this weekend!",
|
|
621
|
-
},
|
|
622
|
-
},
|
|
623
|
-
))
|
|
624
|
-
|
|
625
|
-
test("all")("`parse()` xml example w3schools.com#3", () =>
|
|
626
|
-
expect(
|
|
627
|
-
parse(`
|
|
628
|
-
<bookstore>
|
|
629
|
-
|
|
630
|
-
<book category="cooking">
|
|
631
|
-
<title lang="en">Everyday Italian</title>
|
|
632
|
-
<author>Giada De Laurentiis</author>
|
|
633
|
-
<year>2005</year>
|
|
634
|
-
<price>30.00</price>
|
|
635
|
-
</book>
|
|
636
|
-
|
|
637
|
-
<book category="children">
|
|
638
|
-
<title lang="en">Harry Potter</title>
|
|
639
|
-
<author>J K. Rowling</author>
|
|
640
|
-
<year>2005</year>
|
|
641
|
-
<price>29.99</price>
|
|
642
|
-
</book>
|
|
643
|
-
|
|
644
|
-
<book category="web">
|
|
645
|
-
<title lang="en">XQuery Kick Start</title>
|
|
646
|
-
<author>James McGovern</author>
|
|
647
|
-
<author>Per Bothner</author>
|
|
648
|
-
<author>Kurt Cagle</author>
|
|
649
|
-
<author>James Linn</author>
|
|
650
|
-
<author>Vaidyanathan Nagarajan</author>
|
|
651
|
-
<year>2003</year>
|
|
652
|
-
<price>49.99</price>
|
|
653
|
-
</book>
|
|
654
|
-
|
|
655
|
-
<book category="web" cover="paperback">
|
|
656
|
-
<title lang="en">Learning XML</title>
|
|
657
|
-
<author>Erik T. Ray</author>
|
|
658
|
-
<year>2003</year>
|
|
659
|
-
<price>39.95</price>
|
|
660
|
-
</book>
|
|
661
|
-
|
|
662
|
-
</bookstore>
|
|
663
|
-
`),
|
|
664
|
-
).toEqual(
|
|
665
|
-
{
|
|
666
|
-
bookstore: {
|
|
667
|
-
book: [
|
|
668
|
-
{
|
|
669
|
-
"@category": "cooking",
|
|
670
|
-
title: { "@lang": "en", "#text": "Everyday Italian" },
|
|
671
|
-
author: "Giada De Laurentiis",
|
|
672
|
-
year: "2005",
|
|
673
|
-
price: "30.00",
|
|
674
|
-
},
|
|
675
|
-
{
|
|
676
|
-
"@category": "children",
|
|
677
|
-
title: { "@lang": "en", "#text": "Harry Potter" },
|
|
678
|
-
author: "J K. Rowling",
|
|
679
|
-
year: "2005",
|
|
680
|
-
price: "29.99",
|
|
681
|
-
},
|
|
682
|
-
{
|
|
683
|
-
"@category": "web",
|
|
684
|
-
title: { "@lang": "en", "#text": "XQuery Kick Start" },
|
|
685
|
-
author: [
|
|
686
|
-
"James McGovern",
|
|
687
|
-
"Per Bothner",
|
|
688
|
-
"Kurt Cagle",
|
|
689
|
-
"James Linn",
|
|
690
|
-
"Vaidyanathan Nagarajan",
|
|
691
|
-
],
|
|
692
|
-
year: "2003",
|
|
693
|
-
price: "49.99",
|
|
694
|
-
},
|
|
695
|
-
{
|
|
696
|
-
"@category": "web",
|
|
697
|
-
"@cover": "paperback",
|
|
698
|
-
title: { "@lang": "en", "#text": "Learning XML" },
|
|
699
|
-
author: "Erik T. Ray",
|
|
700
|
-
year: "2003",
|
|
701
|
-
price: "39.95",
|
|
702
|
-
},
|
|
703
|
-
],
|
|
704
|
-
},
|
|
705
|
-
},
|
|
706
|
-
))
|
|
707
|
-
|
|
708
|
-
test("all")("`parse()` xml example w3schools.com#4", () =>
|
|
709
|
-
expect(
|
|
710
|
-
parse(`
|
|
711
|
-
<nitf>
|
|
712
|
-
<head>
|
|
713
|
-
<title>Colombia Earthquake</title>
|
|
714
|
-
</head>
|
|
715
|
-
<body>
|
|
716
|
-
<headline>
|
|
717
|
-
<hl1>143 Dead in Colombia Earthquake</hl1>
|
|
718
|
-
</headline>
|
|
719
|
-
<byline>
|
|
720
|
-
<bytag>By Jared Kotler, Associated Press Writer</bytag>
|
|
721
|
-
</byline>
|
|
722
|
-
<dateline>
|
|
723
|
-
<location>Bogota, Colombia</location>
|
|
724
|
-
<date>Monday January 25 1999 7:28 ET</date>
|
|
725
|
-
</dateline>
|
|
726
|
-
</body>
|
|
727
|
-
</nitf>
|
|
728
|
-
`),
|
|
729
|
-
).toEqual(
|
|
730
|
-
{
|
|
731
|
-
nitf: {
|
|
732
|
-
head: {
|
|
733
|
-
title: "Colombia Earthquake",
|
|
734
|
-
},
|
|
735
|
-
body: {
|
|
736
|
-
headline: {
|
|
737
|
-
hl1: "143 Dead in Colombia Earthquake",
|
|
738
|
-
},
|
|
739
|
-
byline: {
|
|
740
|
-
bytag: "By Jared Kotler, Associated Press Writer",
|
|
741
|
-
},
|
|
742
|
-
dateline: {
|
|
743
|
-
location: "Bogota, Colombia",
|
|
744
|
-
date: "Monday January 25 1999 7:28 ET",
|
|
745
|
-
},
|
|
746
|
-
},
|
|
747
|
-
},
|
|
748
|
-
},
|
|
749
|
-
))
|
|
750
|
-
|
|
751
|
-
test("all")("`parse()` xml example w3schools.com#5", () =>
|
|
752
|
-
expect(
|
|
753
|
-
parse(
|
|
754
|
-
`
|
|
755
|
-
<current_observation>
|
|
756
|
-
|
|
757
|
-
<credit>NOAA's National Weather Service</credit>
|
|
758
|
-
<credit_URL>http://weather.gov/</credit_URL>
|
|
759
|
-
|
|
760
|
-
<image>
|
|
761
|
-
<url>http://weather.gov/images/xml_logo.gif</url>
|
|
762
|
-
<title>NOAA's National Weather Service</title>
|
|
763
|
-
<link>http://weather.gov</link>
|
|
764
|
-
</image>
|
|
765
|
-
|
|
766
|
-
<location>New York/John F. Kennedy Intl Airport, NY</location>
|
|
767
|
-
<station_id>KJFK</station_id>
|
|
768
|
-
<latitude>40.66</latitude>
|
|
769
|
-
<longitude>-73.78</longitude>
|
|
770
|
-
<observation_time_rfc822>Mon, 11 Feb 2008 06:51:00 -0500 EST
|
|
771
|
-
</observation_time_rfc822>
|
|
772
|
-
|
|
773
|
-
<weather>A Few Clouds</weather>
|
|
774
|
-
<temp_f>11</temp_f>
|
|
775
|
-
<temp_c>-12</temp_c>
|
|
776
|
-
<relative_humidity>36</relative_humidity>
|
|
777
|
-
<wind_dir>West</wind_dir>
|
|
778
|
-
<wind_degrees>280</wind_degrees>
|
|
779
|
-
<wind_mph>18.4</wind_mph>
|
|
780
|
-
<wind_gust_mph>29</wind_gust_mph>
|
|
781
|
-
<pressure_mb>1023.6</pressure_mb>
|
|
782
|
-
<pressure_in>30.23</pressure_in>
|
|
783
|
-
<dewpoint_f>-11</dewpoint_f>
|
|
784
|
-
<dewpoint_c>-24</dewpoint_c>
|
|
785
|
-
<windchill_f>-7</windchill_f>
|
|
786
|
-
<windchill_c>-22</windchill_c>
|
|
787
|
-
<visibility_mi>10.00</visibility_mi>
|
|
788
|
-
|
|
789
|
-
<icon_url_base>http://weather.gov/weather/images/fcicons/</icon_url_base>
|
|
790
|
-
<icon_url_name>nfew.jpg</icon_url_name>
|
|
791
|
-
<disclaimer_url>http://weather.gov/disclaimer.html</disclaimer_url>
|
|
792
|
-
<copyright_url>http://weather.gov/disclaimer.html</copyright_url>
|
|
793
|
-
|
|
794
|
-
</current_observation>
|
|
795
|
-
`,
|
|
796
|
-
{ revive: { numbers: true } },
|
|
797
|
-
),
|
|
798
|
-
).toEqual(
|
|
799
|
-
{
|
|
800
|
-
current_observation: {
|
|
801
|
-
credit: "NOAA's National Weather Service",
|
|
802
|
-
credit_URL: "http://weather.gov/",
|
|
803
|
-
image: {
|
|
804
|
-
url: "http://weather.gov/images/xml_logo.gif",
|
|
805
|
-
title: "NOAA's National Weather Service",
|
|
806
|
-
link: "http://weather.gov",
|
|
807
|
-
},
|
|
808
|
-
location: "New York/John F. Kennedy Intl Airport, NY",
|
|
809
|
-
station_id: "KJFK",
|
|
810
|
-
latitude: 40.66,
|
|
811
|
-
longitude: -73.78,
|
|
812
|
-
observation_time_rfc822: "Mon, 11 Feb 2008 06:51:00 -0500 EST",
|
|
813
|
-
weather: "A Few Clouds",
|
|
814
|
-
temp_f: 11,
|
|
815
|
-
temp_c: -12,
|
|
816
|
-
relative_humidity: 36,
|
|
817
|
-
wind_dir: "West",
|
|
818
|
-
wind_degrees: 280,
|
|
819
|
-
wind_mph: 18.4,
|
|
820
|
-
wind_gust_mph: 29,
|
|
821
|
-
pressure_mb: 1023.6,
|
|
822
|
-
pressure_in: 30.23,
|
|
823
|
-
dewpoint_f: -11,
|
|
824
|
-
dewpoint_c: -24,
|
|
825
|
-
windchill_f: -7,
|
|
826
|
-
windchill_c: -22,
|
|
827
|
-
visibility_mi: 10.00,
|
|
828
|
-
icon_url_base: "http://weather.gov/weather/images/fcicons/",
|
|
829
|
-
icon_url_name: "nfew.jpg",
|
|
830
|
-
disclaimer_url: "http://weather.gov/disclaimer.html",
|
|
831
|
-
copyright_url: "http://weather.gov/disclaimer.html",
|
|
832
|
-
},
|
|
833
|
-
},
|
|
834
|
-
))
|
|
835
|
-
|
|
836
|
-
test("all")("`parse()` xml example w3schools.com#6", () =>
|
|
837
|
-
expect(
|
|
838
|
-
parse(`
|
|
839
|
-
<breakfast_menu>
|
|
840
|
-
<food>
|
|
841
|
-
<name>Belgian Waffles</name>
|
|
842
|
-
<price>$5.95</price>
|
|
843
|
-
<description>
|
|
844
|
-
Two of our famous Belgian Waffles with plenty of real maple syrup
|
|
845
|
-
</description>
|
|
846
|
-
<calories>650</calories>
|
|
847
|
-
</food>
|
|
848
|
-
<food>
|
|
849
|
-
<name>Strawberry Belgian Waffles</name>
|
|
850
|
-
<price>$7.95</price>
|
|
851
|
-
<description>
|
|
852
|
-
Light Belgian waffles covered with strawberries and whipped cream
|
|
853
|
-
</description>
|
|
854
|
-
<calories>900</calories>
|
|
855
|
-
</food>
|
|
856
|
-
<food>
|
|
857
|
-
<name>Berry-Berry Belgian Waffles</name>
|
|
858
|
-
<price>$8.95</price>
|
|
859
|
-
<description>
|
|
860
|
-
Belgian waffles covered with assorted fresh berries and whipped cream
|
|
861
|
-
</description>
|
|
862
|
-
<calories>900</calories>
|
|
863
|
-
</food>
|
|
864
|
-
<food>
|
|
865
|
-
<name>French Toast</name>
|
|
866
|
-
<price>$4.50</price>
|
|
867
|
-
<description>
|
|
868
|
-
Thick slices made from our homemade sourdough bread
|
|
869
|
-
</description>
|
|
870
|
-
<calories>600</calories>
|
|
871
|
-
</food>
|
|
872
|
-
<food>
|
|
873
|
-
<name>Homestyle Breakfast</name>
|
|
874
|
-
<price>$6.95</price>
|
|
875
|
-
<description>
|
|
876
|
-
Two eggs, bacon or sausage, toast, and our ever-popular hash browns
|
|
877
|
-
</description>
|
|
878
|
-
<calories>950</calories>
|
|
879
|
-
</food>
|
|
880
|
-
</breakfast_menu>
|
|
881
|
-
`),
|
|
882
|
-
).toEqual(
|
|
883
|
-
{
|
|
884
|
-
breakfast_menu: {
|
|
885
|
-
food: [
|
|
886
|
-
{
|
|
887
|
-
name: "Belgian Waffles",
|
|
888
|
-
price: "$5.95",
|
|
889
|
-
description: "Two of our famous Belgian Waffles with plenty of real maple syrup",
|
|
890
|
-
calories: "650",
|
|
891
|
-
},
|
|
892
|
-
{
|
|
893
|
-
name: "Strawberry Belgian Waffles",
|
|
894
|
-
price: "$7.95",
|
|
895
|
-
description: "Light Belgian waffles covered with strawberries and whipped cream",
|
|
896
|
-
calories: "900",
|
|
897
|
-
},
|
|
898
|
-
{
|
|
899
|
-
name: "Berry-Berry Belgian Waffles",
|
|
900
|
-
price: "$8.95",
|
|
901
|
-
description: "Belgian waffles covered with assorted fresh berries and whipped cream",
|
|
902
|
-
calories: "900",
|
|
903
|
-
},
|
|
904
|
-
{
|
|
905
|
-
name: "French Toast",
|
|
906
|
-
price: "$4.50",
|
|
907
|
-
description: "Thick slices made from our homemade sourdough bread",
|
|
908
|
-
calories: "600",
|
|
909
|
-
},
|
|
910
|
-
{
|
|
911
|
-
name: "Homestyle Breakfast",
|
|
912
|
-
price: "$6.95",
|
|
913
|
-
description: "Two eggs, bacon or sausage, toast, and our ever-popular hash browns",
|
|
914
|
-
calories: "950",
|
|
915
|
-
},
|
|
916
|
-
],
|
|
917
|
-
},
|
|
918
|
-
},
|
|
919
|
-
))
|
|
920
|
-
|
|
921
|
-
// Parser options
|
|
922
|
-
|
|
923
|
-
test("all")("`parse()` xml parser option no flatten text", () =>
|
|
924
|
-
expect(
|
|
925
|
-
parse(
|
|
926
|
-
`
|
|
927
|
-
<root>
|
|
928
|
-
<child>
|
|
929
|
-
<grand-child>family</grand-child>
|
|
930
|
-
</child>
|
|
931
|
-
</root>
|
|
932
|
-
`,
|
|
933
|
-
{ flatten: { text: false } },
|
|
934
|
-
),
|
|
935
|
-
).toEqual(
|
|
936
|
-
{
|
|
937
|
-
root: {
|
|
938
|
-
child: {
|
|
939
|
-
"grand-child": {
|
|
940
|
-
"#text": "family",
|
|
941
|
-
},
|
|
942
|
-
},
|
|
943
|
-
},
|
|
944
|
-
},
|
|
945
|
-
))
|
|
946
|
-
|
|
947
|
-
test("all")("`parse()` xml parser option revive", () =>
|
|
948
|
-
expect(
|
|
949
|
-
parse(
|
|
950
|
-
`
|
|
951
|
-
<?xml version="1.0"?>
|
|
952
|
-
<root>
|
|
953
|
-
<empty></empty>
|
|
954
|
-
<number>1</number>
|
|
955
|
-
<number_negative>-1</number_negative>
|
|
956
|
-
<number_hex>0xAC</number_hex>
|
|
957
|
-
<number_octal>0o667</number_octal>
|
|
958
|
-
<boolean>true</boolean>
|
|
959
|
-
</root>
|
|
960
|
-
`,
|
|
961
|
-
{ revive: { booleans: true, numbers: true } },
|
|
962
|
-
),
|
|
963
|
-
).toEqual(
|
|
964
|
-
{
|
|
965
|
-
"@version": "1.0",
|
|
966
|
-
root: {
|
|
967
|
-
empty: null,
|
|
968
|
-
number: 1,
|
|
969
|
-
number_negative: -1,
|
|
970
|
-
number_hex: 0xac,
|
|
971
|
-
number_octal: 0o667,
|
|
972
|
-
boolean: true,
|
|
973
|
-
},
|
|
974
|
-
},
|
|
975
|
-
))
|
|
976
|
-
|
|
977
|
-
test("all")("`parse()` xml parser option no-revive", () =>
|
|
978
|
-
expect(
|
|
979
|
-
parse(
|
|
980
|
-
`
|
|
981
|
-
<?xml version="1.0"?>
|
|
982
|
-
<root>
|
|
983
|
-
<empty></empty>
|
|
984
|
-
<number>1</number>
|
|
985
|
-
<number_negative>-1</number_negative>
|
|
986
|
-
<number_hex>0xac</number_hex>
|
|
987
|
-
<number_octal>0o667</number_octal>
|
|
988
|
-
<boolean>true</boolean>
|
|
989
|
-
</root>
|
|
990
|
-
`,
|
|
991
|
-
{ flatten: { empty: false }, revive: { booleans: false, numbers: false } },
|
|
992
|
-
),
|
|
993
|
-
).toEqual(
|
|
994
|
-
{
|
|
995
|
-
"@version": "1.0",
|
|
996
|
-
root: {
|
|
997
|
-
empty: "",
|
|
998
|
-
number: "1",
|
|
999
|
-
number_negative: "-1",
|
|
1000
|
-
number_hex: "0xac",
|
|
1001
|
-
number_octal: "0o667",
|
|
1002
|
-
boolean: "true",
|
|
1003
|
-
},
|
|
1004
|
-
},
|
|
1005
|
-
))
|
|
1006
|
-
|
|
1007
|
-
test("all")("`parse()` xml parser reviver", () =>
|
|
1008
|
-
expect(
|
|
1009
|
-
parse(
|
|
1010
|
-
`
|
|
1011
|
-
<root>
|
|
1012
|
-
<not>true</not>
|
|
1013
|
-
<attribute delete="true"/>
|
|
1014
|
-
<delete/>
|
|
1015
|
-
</root>
|
|
1016
|
-
`,
|
|
1017
|
-
{
|
|
1018
|
-
revive: {
|
|
1019
|
-
custom({ name, key, value }) {
|
|
1020
|
-
if (name === "not") {
|
|
1021
|
-
return !value
|
|
1022
|
-
}
|
|
1023
|
-
if (name === "delete") {
|
|
1024
|
-
return undefined
|
|
1025
|
-
}
|
|
1026
|
-
if ((name === "attribute") && (key === "@delete")) {
|
|
1027
|
-
return undefined
|
|
1028
|
-
}
|
|
1029
|
-
return value
|
|
1030
|
-
},
|
|
1031
|
-
},
|
|
1032
|
-
},
|
|
1033
|
-
),
|
|
1034
|
-
).toEqual(
|
|
1035
|
-
{
|
|
1036
|
-
root: {
|
|
1037
|
-
not: false,
|
|
1038
|
-
attribute: null,
|
|
1039
|
-
},
|
|
1040
|
-
},
|
|
1041
|
-
))
|
|
1042
|
-
|
|
1043
|
-
test("all")("`parse()` xml parser option clean", () =>
|
|
1044
|
-
expect(
|
|
1045
|
-
parse(
|
|
1046
|
-
`
|
|
1047
|
-
<?xml version="1.0" encoding="UTF-8"?>
|
|
1048
|
-
<?xml-stylesheet href="styles.xsl" type="text/xsl"?>
|
|
1049
|
-
<!DOCTYPE type "quoted attribute">
|
|
1050
|
-
<root>
|
|
1051
|
-
<a attr="test">foo</a>
|
|
1052
|
-
</root>
|
|
1053
|
-
`,
|
|
1054
|
-
{ clean: { attributes: true, comments: true, doctype: true, instructions: true } },
|
|
1055
|
-
),
|
|
1056
|
-
).toEqual(
|
|
1057
|
-
{
|
|
1058
|
-
root: {
|
|
1059
|
-
a: "foo",
|
|
1060
|
-
},
|
|
1061
|
-
},
|
|
1062
|
-
))
|
|
1063
|
-
|
|
1064
|
-
test("all")("`parse()` xml parser option clean (no matching elements)", () =>
|
|
1065
|
-
expect(
|
|
1066
|
-
parse(
|
|
1067
|
-
`
|
|
1068
|
-
<?xml version="1.0" encoding="UTF-8"?>
|
|
1069
|
-
<root>
|
|
1070
|
-
<a attr="test">foo</a>
|
|
1071
|
-
</root>
|
|
1072
|
-
`,
|
|
1073
|
-
{ clean: { attributes: true, comments: true, doctype: true, instructions: true } },
|
|
1074
|
-
),
|
|
1075
|
-
).toEqual(
|
|
1076
|
-
{
|
|
1077
|
-
root: {
|
|
1078
|
-
a: "foo",
|
|
1079
|
-
},
|
|
1080
|
-
},
|
|
1081
|
-
))
|
|
1082
|
-
|
|
1083
|
-
test("all")("`parse()` xml parser option no clean", () =>
|
|
1084
|
-
expect(
|
|
1085
|
-
parse(
|
|
1086
|
-
`
|
|
1087
|
-
<?xml version="1.0" encoding="UTF-8"?>
|
|
1088
|
-
<?xml-stylesheet href="styles.xsl" type="text/xsl"?>
|
|
1089
|
-
<!DOCTYPE type "quoted attribute">
|
|
1090
|
-
<root>
|
|
1091
|
-
<a attr="test">foo</a>
|
|
1092
|
-
</root>
|
|
1093
|
-
`,
|
|
1094
|
-
{ clean: { attributes: false, comments: false, doctype: false, instructions: false } },
|
|
1095
|
-
),
|
|
1096
|
-
).toEqual(
|
|
1097
|
-
{
|
|
1098
|
-
"@version": "1.0",
|
|
1099
|
-
"@encoding": "UTF-8",
|
|
1100
|
-
"#instructions": {
|
|
1101
|
-
"xml-stylesheet": {
|
|
1102
|
-
"@href": "styles.xsl",
|
|
1103
|
-
"@type": "text/xsl",
|
|
1104
|
-
},
|
|
1105
|
-
},
|
|
1106
|
-
"#doctype": {
|
|
1107
|
-
"@type": "",
|
|
1108
|
-
"@quoted attribute": "",
|
|
1109
|
-
},
|
|
1110
|
-
root: {
|
|
1111
|
-
a: {
|
|
1112
|
-
"@attr": "test",
|
|
1113
|
-
"#text": "foo",
|
|
1114
|
-
},
|
|
1115
|
-
},
|
|
1116
|
-
},
|
|
1117
|
-
))
|
|
1118
|
-
|
|
1119
|
-
test("all")("`parse()` xml parser option flatten", () =>
|
|
1120
|
-
expect(
|
|
1121
|
-
parse(
|
|
1122
|
-
`
|
|
1123
|
-
<root>
|
|
1124
|
-
<attributes foo="1" bar="2"></attributes>
|
|
1125
|
-
<text>foo</text>
|
|
1126
|
-
<empty></empty>
|
|
1127
|
-
</root>
|
|
1128
|
-
`,
|
|
1129
|
-
{ flatten: { attributes: true, text: true, empty: true } },
|
|
1130
|
-
),
|
|
1131
|
-
).toEqual(
|
|
1132
|
-
{
|
|
1133
|
-
root: {
|
|
1134
|
-
attributes: { foo: "1", bar: "2" },
|
|
1135
|
-
text: "foo",
|
|
1136
|
-
empty: null,
|
|
1137
|
-
},
|
|
1138
|
-
},
|
|
1139
|
-
))
|
|
1140
|
-
|
|
1141
|
-
test("all")("`parse()` xml parser option no flatten", () =>
|
|
1142
|
-
expect(
|
|
1143
|
-
parse(
|
|
1144
|
-
`
|
|
1145
|
-
<root>
|
|
1146
|
-
<attributes foo="1" bar="2"></attributes>
|
|
1147
|
-
<text>foo</text>
|
|
1148
|
-
<empty></empty>
|
|
1149
|
-
</root>
|
|
1150
|
-
`,
|
|
1151
|
-
{ flatten: { attributes: false, text: false, empty: false } },
|
|
1152
|
-
),
|
|
1153
|
-
).toEqual(
|
|
1154
|
-
{
|
|
1155
|
-
root: {
|
|
1156
|
-
attributes: { "@foo": "1", "@bar": "2" },
|
|
1157
|
-
text: { "#text": "foo" },
|
|
1158
|
-
empty: { "#text": "" },
|
|
1159
|
-
},
|
|
1160
|
-
},
|
|
1161
|
-
))
|
|
1162
|
-
|
|
1163
|
-
test("all")("`parse()` xml parser option revive", () =>
|
|
1164
|
-
expect(
|
|
1165
|
-
parse(
|
|
1166
|
-
`
|
|
1167
|
-
<root>
|
|
1168
|
-
<trim> hello </trim>
|
|
1169
|
-
<preserve xml:space="preserve"> world </preserve>
|
|
1170
|
-
<entities>< > & ' "</entities>
|
|
1171
|
-
<boolean>true</boolean>
|
|
1172
|
-
<boolean>false</boolean>
|
|
1173
|
-
<integer>1</integer>
|
|
1174
|
-
<float>3.14</float>
|
|
1175
|
-
</root>
|
|
1176
|
-
`,
|
|
1177
|
-
{ revive: { trim: true, entities: true, booleans: true, numbers: true } },
|
|
1178
|
-
),
|
|
1179
|
-
).toEqual(
|
|
1180
|
-
{
|
|
1181
|
-
root: {
|
|
1182
|
-
trim: "hello",
|
|
1183
|
-
preserve: { "@xml:space": "preserve", "#text": " world " },
|
|
1184
|
-
entities: `< > & ' "`,
|
|
1185
|
-
boolean: [true, false],
|
|
1186
|
-
integer: 1,
|
|
1187
|
-
float: 3.14,
|
|
1188
|
-
},
|
|
1189
|
-
},
|
|
1190
|
-
))
|
|
1191
|
-
|
|
1192
|
-
test("all")("`parse()` xml parser option no revive", () =>
|
|
1193
|
-
expect(
|
|
1194
|
-
parse(
|
|
1195
|
-
`
|
|
1196
|
-
<root>
|
|
1197
|
-
<trim> hello </trim>
|
|
1198
|
-
<preserve xml:space="preserve"> world </preserve>
|
|
1199
|
-
<entities>< > & ' "</entities>
|
|
1200
|
-
<boolean>true</boolean>
|
|
1201
|
-
<boolean>false</boolean>
|
|
1202
|
-
<integer>1</integer>
|
|
1203
|
-
<float>3.14</float>
|
|
1204
|
-
</root>
|
|
1205
|
-
`,
|
|
1206
|
-
{ revive: { trim: false, entities: false, booleans: false, numbers: false } },
|
|
1207
|
-
),
|
|
1208
|
-
).toEqual(
|
|
1209
|
-
{
|
|
1210
|
-
root: {
|
|
1211
|
-
trim: " hello ",
|
|
1212
|
-
preserve: { "@xml:space": "preserve", "#text": " world " },
|
|
1213
|
-
entities: `< > & ' "`,
|
|
1214
|
-
boolean: ["true", "false"],
|
|
1215
|
-
integer: "1",
|
|
1216
|
-
float: "3.14",
|
|
1217
|
-
},
|
|
1218
|
-
},
|
|
1219
|
-
))
|
|
1220
|
-
|
|
1221
|
-
test("all")("`parse()` xml parser option mode 'xml'", () =>
|
|
1222
|
-
expect(() =>
|
|
1223
|
-
parse(
|
|
1224
|
-
`
|
|
1225
|
-
<root foo=bar></root>
|
|
1226
|
-
`,
|
|
1227
|
-
{ mode: "xml" },
|
|
1228
|
-
)
|
|
1229
|
-
).toThrow(SyntaxError))
|
|
1230
|
-
|
|
1231
|
-
test("all")("`parse()` xml parser option mode 'html'", () =>
|
|
1232
|
-
expect(
|
|
1233
|
-
parse(
|
|
1234
|
-
`
|
|
1235
|
-
<root foo=bar></root>
|
|
1236
|
-
`,
|
|
1237
|
-
{ mode: "html" },
|
|
1238
|
-
),
|
|
1239
|
-
).toEqual({
|
|
1240
|
-
root: {
|
|
1241
|
-
"@foo": "bar",
|
|
1242
|
-
},
|
|
1243
|
-
}))
|
|
1244
|
-
|
|
1245
|
-
// Metadata
|
|
1246
|
-
|
|
1247
|
-
test("all")("`parse()` xml parser option metadata", () => {
|
|
1248
|
-
const xml = parse(
|
|
1249
|
-
`
|
|
1250
|
-
<root>
|
|
1251
|
-
<child>
|
|
1252
|
-
<grand-child></grand-child>
|
|
1253
|
-
</child>
|
|
1254
|
-
<sibling>A</sibling>
|
|
1255
|
-
<sibling>B</sibling>
|
|
1256
|
-
<sibling>C</sibling>
|
|
1257
|
-
<sibling>D</sibling>
|
|
1258
|
-
</root>
|
|
1259
|
-
`,
|
|
1260
|
-
{ flatten: { text: false, empty: false } },
|
|
1261
|
-
) as testing
|
|
1262
|
-
|
|
1263
|
-
expect(xml.root?.child?.["grand-child"]?.["~parent"]).toEqual(xml.root.child)
|
|
1264
|
-
expect(xml.root?.child?.["grand-child"]?.["~name"]).toBe("grand-child")
|
|
1265
|
-
expect(xml.root?.child?.["~parent"]).toEqual(xml.root)
|
|
1266
|
-
expect(xml.root?.child?.["~name"]).toBe("child")
|
|
1267
|
-
expect(xml.root?.["~parent"]).toBe(xml)
|
|
1268
|
-
expect(xml.root?.["~name"]).toBe("root")
|
|
1269
|
-
expect(xml["~parent"]).toBeNull()
|
|
1270
|
-
expect(xml.root?.sibling?.["~parent"]).toEqual(xml.root)
|
|
1271
|
-
expect(xml.root?.sibling?.["~name"]).toBe("sibling")
|
|
1272
|
-
})
|
|
1273
|
-
|
|
1274
|
-
// Other inputs
|
|
1275
|
-
|
|
1276
|
-
test("deno")("`parse()` using a reader", async () => {
|
|
1277
|
-
using file = await Deno.open("bench/assets/small.xml")
|
|
1278
|
-
expect(
|
|
1279
|
-
parse(file),
|
|
1280
|
-
).toEqual(
|
|
1281
|
-
{
|
|
1282
|
-
"#comments": [
|
|
1283
|
-
"From https://www.w3schools.com/xml/note.xml",
|
|
1284
|
-
],
|
|
1285
|
-
note: {
|
|
1286
|
-
body: "Don't forget me this weekend!",
|
|
1287
|
-
from: "Jani",
|
|
1288
|
-
heading: "Reminder",
|
|
1289
|
-
to: "Tove",
|
|
1290
|
-
},
|
|
1291
|
-
},
|
|
1292
|
-
)
|
|
1293
|
-
}, { permissions: { read: ["bench"] } })
|
|
1294
|
-
|
|
1295
|
-
// Size tests
|
|
1296
|
-
|
|
1297
|
-
for (let i = 0; i <= 5; i++) {
|
|
1298
|
-
const ignore = false && (i > 2) && (!Deno.env.get("CI"))
|
|
1299
|
-
test("all")(`\`parse()\` parse large files ~${(2 ** i)}Mb`, async () => {
|
|
1300
|
-
await write(i)
|
|
1301
|
-
expect(parse(await Deno.readTextFile(`bench/assets/x-${i}x-large.xml`))).not.toThrow()
|
|
1302
|
-
}, { permissions: { read: ["bench"], write: ["bench"] }, ignore } as testing)
|
|
1303
|
-
}
|