fast-xml-parser 5.5.12 → 5.6.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/CHANGELOG.md +6 -0
- package/lib/fxp.cjs +1 -1
- package/lib/fxp.min.js +1 -1
- package/lib/fxp.min.js.map +1 -1
- package/lib/fxparser.min.js +1 -1
- package/lib/fxparser.min.js.map +1 -1
- package/package.json +2 -1
- package/src/fast-xml-parser.zip +0 -0
- package/src/xmlparser/OrderedObjParser.js +13 -114
- package/src/xmlparser/XMLParser.js +1 -1
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "fast-xml-parser",
|
|
3
|
-
"version": "5.
|
|
3
|
+
"version": "5.6.0",
|
|
4
4
|
"description": "Validate XML, Parse XML, Build XML without C/C++ based libraries",
|
|
5
5
|
"main": "./lib/fxp.cjs",
|
|
6
6
|
"type": "module",
|
|
@@ -87,6 +87,7 @@
|
|
|
87
87
|
}
|
|
88
88
|
],
|
|
89
89
|
"dependencies": {
|
|
90
|
+
"@nodable/entities": "^1.1.0",
|
|
90
91
|
"fast-xml-builder": "^1.1.4",
|
|
91
92
|
"path-expression-matcher": "^1.5.0",
|
|
92
93
|
"strnum": "^2.2.3"
|
|
Binary file
|
|
@@ -8,6 +8,7 @@ import toNumber from "strnum";
|
|
|
8
8
|
import getIgnoreAttributesFn from "../ignoreAttributes.js";
|
|
9
9
|
import { Expression, Matcher } from 'path-expression-matcher';
|
|
10
10
|
import { ExpressionSet } from 'path-expression-matcher';
|
|
11
|
+
import EntityReplacer, { COMMON_HTML, NUMERIC_ENTITIES, CURRENCY_ENTITIES } from '@nodable/entities';
|
|
11
12
|
|
|
12
13
|
// const regx =
|
|
13
14
|
// '<((!\\[CDATA\\[([\\s\\S]*?)(]]>))|((NAME:)?(NAME))([^>]*)>|((\\/)(NAME)\\s*>))([^<]*)'
|
|
@@ -72,32 +73,6 @@ export default class OrderedObjParser {
|
|
|
72
73
|
this.options = options;
|
|
73
74
|
this.currentNode = null;
|
|
74
75
|
this.tagsNodeStack = [];
|
|
75
|
-
this.docTypeEntities = {};
|
|
76
|
-
this.lastEntities = {
|
|
77
|
-
"apos": { regex: /&(apos|#39|#x27);/g, val: "'" },
|
|
78
|
-
"gt": { regex: /&(gt|#62|#x3E);/g, val: ">" },
|
|
79
|
-
"lt": { regex: /&(lt|#60|#x3C);/g, val: "<" },
|
|
80
|
-
"quot": { regex: /&(quot|#34|#x22);/g, val: "\"" },
|
|
81
|
-
};
|
|
82
|
-
this.ampEntity = { regex: /&(amp|#38|#x26);/g, val: "&" };
|
|
83
|
-
this.htmlEntities = {
|
|
84
|
-
"space": { regex: /&(nbsp|#160);/g, val: " " },
|
|
85
|
-
// "lt" : { regex: /&(lt|#60);/g, val: "<" },
|
|
86
|
-
// "gt" : { regex: /&(gt|#62);/g, val: ">" },
|
|
87
|
-
// "amp" : { regex: /&(amp|#38);/g, val: "&" },
|
|
88
|
-
// "quot" : { regex: /&(quot|#34);/g, val: "\"" },
|
|
89
|
-
// "apos" : { regex: /&(apos|#39);/g, val: "'" },
|
|
90
|
-
"cent": { regex: /&(cent|#162);/g, val: "¢" },
|
|
91
|
-
"pound": { regex: /&(pound|#163);/g, val: "£" },
|
|
92
|
-
"yen": { regex: /&(yen|#165);/g, val: "¥" },
|
|
93
|
-
"euro": { regex: /&(euro|#8364);/g, val: "€" },
|
|
94
|
-
"copyright": { regex: /&(copy|#169);/g, val: "©" },
|
|
95
|
-
"reg": { regex: /&(reg|#174);/g, val: "®" },
|
|
96
|
-
"inr": { regex: /&(inr|#8377);/g, val: "₹" },
|
|
97
|
-
"num_dec": { regex: /&#([0-9]{1,7});/g, val: (_, str) => fromCodePoint(str, 10, "&#") },
|
|
98
|
-
"num_hex": { regex: /&#x([0-9a-fA-F]{1,6});/g, val: (_, str) => fromCodePoint(str, 16, "&#x") },
|
|
99
|
-
};
|
|
100
|
-
this.addExternalEntities = addExternalEntities;
|
|
101
76
|
this.parseXml = parseXml;
|
|
102
77
|
this.parseTextData = parseTextData;
|
|
103
78
|
this.resolveNameSpace = resolveNameSpace;
|
|
@@ -111,6 +86,16 @@ export default class OrderedObjParser {
|
|
|
111
86
|
this.entityExpansionCount = 0;
|
|
112
87
|
this.currentExpandedLength = 0;
|
|
113
88
|
|
|
89
|
+
this.entityReplacer = new EntityReplacer({
|
|
90
|
+
default: true,
|
|
91
|
+
// amp: true,
|
|
92
|
+
system: this.options.htmlEntities ? { ...COMMON_HTML, ...NUMERIC_ENTITIES, ...CURRENCY_ENTITIES } : {},
|
|
93
|
+
maxTotalExpansions: this.options.processEntities.maxTotalExpansions,
|
|
94
|
+
maxExpandedLength: this.options.processEntities.maxExpandedLength,
|
|
95
|
+
applyLimitsTo: "all",
|
|
96
|
+
//postCheck: resolved => resolved
|
|
97
|
+
});
|
|
98
|
+
|
|
114
99
|
// Initialize path matcher for path-expression-matcher
|
|
115
100
|
this.matcher = new Matcher();
|
|
116
101
|
|
|
@@ -141,17 +126,6 @@ export default class OrderedObjParser {
|
|
|
141
126
|
|
|
142
127
|
}
|
|
143
128
|
|
|
144
|
-
function addExternalEntities(externalEntities) {
|
|
145
|
-
const entKeys = Object.keys(externalEntities);
|
|
146
|
-
for (let i = 0; i < entKeys.length; i++) {
|
|
147
|
-
const ent = entKeys[i];
|
|
148
|
-
const escaped = ent.replace(/[.\-+*:]/g, '\\.');
|
|
149
|
-
this.lastEntities[ent] = {
|
|
150
|
-
regex: new RegExp("&" + escaped + ";", "g"),
|
|
151
|
-
val: externalEntities[ent]
|
|
152
|
-
}
|
|
153
|
-
}
|
|
154
|
-
}
|
|
155
129
|
|
|
156
130
|
/**
|
|
157
131
|
* @param {string} val
|
|
@@ -308,9 +282,6 @@ const parseXml = function (xmlData) {
|
|
|
308
282
|
// Reset entity expansion counters for this document
|
|
309
283
|
this.entityExpansionCount = 0;
|
|
310
284
|
this.currentExpandedLength = 0;
|
|
311
|
-
this.docTypeEntitiesKeys = [];
|
|
312
|
-
this.lastEntitiesKeys = Object.keys(this.lastEntities);
|
|
313
|
-
this.htmlEntitiesKeys = this.options.htmlEntities ? Object.keys(this.htmlEntities) : [];
|
|
314
285
|
const options = this.options;
|
|
315
286
|
const docTypeReader = new DocTypeReader(options.processEntities);
|
|
316
287
|
const xmlLen = xmlData.length;
|
|
@@ -390,8 +361,7 @@ const parseXml = function (xmlData) {
|
|
|
390
361
|
} else if (c1 === 33
|
|
391
362
|
&& xmlData.charCodeAt(i + 2) === 68) { //'!D'
|
|
392
363
|
const result = docTypeReader.readDocType(xmlData, i);
|
|
393
|
-
this.
|
|
394
|
-
this.docTypeEntitiesKeys = Object.keys(this.docTypeEntities) || []
|
|
364
|
+
this.entityReplacer.addInputEntities(result.entities);
|
|
395
365
|
i = result.i;
|
|
396
366
|
} else if (c1 === 33
|
|
397
367
|
&& xmlData.charCodeAt(i + 2) === 91) { // '!['
|
|
@@ -632,78 +602,7 @@ function replaceEntitiesValue(val, tagName, jPath) {
|
|
|
632
602
|
}
|
|
633
603
|
}
|
|
634
604
|
|
|
635
|
-
|
|
636
|
-
for (const entityName of this.docTypeEntitiesKeys) {
|
|
637
|
-
const entity = this.docTypeEntities[entityName];
|
|
638
|
-
const matches = val.match(entity.regx);
|
|
639
|
-
|
|
640
|
-
if (matches) {
|
|
641
|
-
// Track expansions
|
|
642
|
-
this.entityExpansionCount += matches.length;
|
|
643
|
-
|
|
644
|
-
// Check expansion limit
|
|
645
|
-
if (entityConfig.maxTotalExpansions &&
|
|
646
|
-
this.entityExpansionCount > entityConfig.maxTotalExpansions) {
|
|
647
|
-
throw new Error(
|
|
648
|
-
`Entity expansion limit exceeded: ${this.entityExpansionCount} > ${entityConfig.maxTotalExpansions}`
|
|
649
|
-
);
|
|
650
|
-
}
|
|
651
|
-
|
|
652
|
-
// Store length before replacement
|
|
653
|
-
const lengthBefore = val.length;
|
|
654
|
-
val = val.replace(entity.regx, entity.val);
|
|
655
|
-
|
|
656
|
-
// Check expanded length immediately after replacement
|
|
657
|
-
if (entityConfig.maxExpandedLength) {
|
|
658
|
-
this.currentExpandedLength += (val.length - lengthBefore);
|
|
659
|
-
|
|
660
|
-
if (this.currentExpandedLength > entityConfig.maxExpandedLength) {
|
|
661
|
-
throw new Error(
|
|
662
|
-
`Total expanded content size exceeded: ${this.currentExpandedLength} > ${entityConfig.maxExpandedLength}`
|
|
663
|
-
);
|
|
664
|
-
}
|
|
665
|
-
}
|
|
666
|
-
}
|
|
667
|
-
}
|
|
668
|
-
if (val.indexOf('&') === -1) return val;
|
|
669
|
-
// Replace standard entities
|
|
670
|
-
for (const entityName of this.lastEntitiesKeys) {
|
|
671
|
-
const entity = this.lastEntities[entityName];
|
|
672
|
-
const matches = val.match(entity.regex);
|
|
673
|
-
if (matches) {
|
|
674
|
-
this.entityExpansionCount += matches.length;
|
|
675
|
-
if (entityConfig.maxTotalExpansions &&
|
|
676
|
-
this.entityExpansionCount > entityConfig.maxTotalExpansions) {
|
|
677
|
-
throw new Error(
|
|
678
|
-
`Entity expansion limit exceeded: ${this.entityExpansionCount} > ${entityConfig.maxTotalExpansions}`
|
|
679
|
-
);
|
|
680
|
-
}
|
|
681
|
-
}
|
|
682
|
-
val = val.replace(entity.regex, entity.val);
|
|
683
|
-
}
|
|
684
|
-
if (val.indexOf('&') === -1) return val;
|
|
685
|
-
|
|
686
|
-
// Replace HTML entities if enabled
|
|
687
|
-
for (const entityName of this.htmlEntitiesKeys) {
|
|
688
|
-
const entity = this.htmlEntities[entityName];
|
|
689
|
-
const matches = val.match(entity.regex);
|
|
690
|
-
if (matches) {
|
|
691
|
-
//console.log(matches);
|
|
692
|
-
this.entityExpansionCount += matches.length;
|
|
693
|
-
if (entityConfig.maxTotalExpansions &&
|
|
694
|
-
this.entityExpansionCount > entityConfig.maxTotalExpansions) {
|
|
695
|
-
throw new Error(
|
|
696
|
-
`Entity expansion limit exceeded: ${this.entityExpansionCount} > ${entityConfig.maxTotalExpansions}`
|
|
697
|
-
);
|
|
698
|
-
}
|
|
699
|
-
}
|
|
700
|
-
val = val.replace(entity.regex, entity.val);
|
|
701
|
-
}
|
|
702
|
-
|
|
703
|
-
// Replace ampersand entity last
|
|
704
|
-
val = val.replace(this.ampEntity.regex, this.ampEntity.val);
|
|
705
|
-
|
|
706
|
-
return val;
|
|
605
|
+
return this.entityReplacer.replace(val);
|
|
707
606
|
}
|
|
708
607
|
|
|
709
608
|
|
|
@@ -32,7 +32,7 @@ export default class XMLParser {
|
|
|
32
32
|
}
|
|
33
33
|
}
|
|
34
34
|
const orderedObjParser = new OrderedObjParser(this.options);
|
|
35
|
-
orderedObjParser.
|
|
35
|
+
orderedObjParser.entityReplacer.setExternalEntities(this.externalEntities);
|
|
36
36
|
const orderedResult = orderedObjParser.parseXml(xmlData);
|
|
37
37
|
if (this.options.preserveOrder || orderedResult === undefined) return orderedResult;
|
|
38
38
|
else return prettify(orderedResult, this.options, orderedObjParser.matcher, orderedObjParser.readonlyMatcher);
|