Skip to content

Commit 732fc72

Browse files
committed
Improve performance and accuracy
1 parent 1f34e79 commit 732fc72

File tree

4 files changed

+37
-39
lines changed

4 files changed

+37
-39
lines changed

index.js

Lines changed: 27 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -1,37 +1,40 @@
11
'use strict';
2-
const htmlCommentRegex = require('html-comment-regex');
2+
const parser = require('fast-xml-parser');
33

4-
const isBinary = buffer => {
5-
const isBuffer = Buffer.isBuffer(buffer);
4+
const isSvg = input => {
5+
if (input === undefined || input === null) {
6+
return false;
7+
}
68

7-
for (let i = 0; i < 24; i++) {
8-
const characterCode = isBuffer ? buffer[i] : buffer.charCodeAt(i);
9+
input = input.toString().trim();
910

10-
if (characterCode === 65533 || characterCode <= 8) {
11-
return true;
12-
}
11+
if (input.length === 0) {
12+
return false;
1313
}
1414

15-
return false;
16-
};
17-
18-
const cleanEntities = svg => {
19-
const entityRegex = /\s*<!Entity\s+\S*\s*(?:"|')[^"]+(?:"|')\s*>/img;
20-
// Remove entities
21-
return svg.replace(entityRegex, '');
22-
};
15+
// Has to be `!==` as it can also return an object with error info.
16+
console.log('a', parser.validate(input));
17+
if (parser.validate(input) !== true) {
18+
return false;
19+
}
2320

24-
const removeDtdMarkupDeclarations = svg => svg.replace(/\[?(?:\s*<![A-Z]+[^>]*>\s*)*\]?/g, '');
21+
let jsonObject;
22+
try {
23+
jsonObject = parser.parse(input);
24+
} catch (_) {
25+
return false;
26+
}
2527

26-
const clean = svg => {
27-
svg = cleanEntities(svg);
28-
svg = removeDtdMarkupDeclarations(svg);
29-
return svg;
30-
};
28+
if (!jsonObject) {
29+
return false;
30+
}
3131

32-
const regex = /^\s*(?:<\?xml[^>]*>\s*)?(?:<!doctype svg[^>]*>\s*)?(?:<svg[^>]*>[^]*<\/svg>|<svg[^/>]*\/\s*>)\s*$/i;
32+
if (!('svg' in jsonObject)) {
33+
return false;
34+
}
3335

34-
const isSvg = input => Boolean(input) && !isBinary(input) && regex.test(clean(input.toString()).replace(htmlCommentRegex, ''));
36+
return true;
37+
};
3538

3639
module.exports = isSvg;
3740
// TODO: Remove this for the next major release

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@
3737
"buffer"
3838
],
3939
"dependencies": {
40-
"html-comment-regex": "^1.1.2"
40+
"fast-xml-parser": "^3.19.0"
4141
},
4242
"devDependencies": {
4343
"@types/node": "^11.13.0",

readme.md

Lines changed: 0 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -17,14 +17,6 @@ isSvg('<svg xmlns="http://www.w3.org/2000/svg"><path fill="#00CD9F"/></svg>');
1717
//=> true
1818
```
1919

20-
## Edge cases
21-
22-
This module performs a quick-and-dirty check. It's fast, but in certain cases it will give incorrect results.
23-
24-
- Returns `true` for an SVG-like string that isn't well-formed or valid: `<svg><div></svg>`
25-
26-
If you want to make certain that your SVG is *valid*, try parsing it with [libxmljs](https://github.com/polotek/libxmljs).
27-
2820
---
2921

3022
<div align="center">

test.js

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -24,16 +24,19 @@ test('valid SVGs', t => {
2424

2525
test('invalid SVGs', t => {
2626
t.false(isSvg(fs.readFileSync('fixtures/fixture.jpg')));
27-
t.false(isSvg('this is not svg, but it mentions <svg> tags'));
28-
t.false(isSvg('<svg> hello I am an svg oops maybe not'));
29-
t.false(isSvg('<svg></svg> this string starts with an svg'));
30-
t.false(isSvg('this string ends with an svg <svg></svg>'));
3127
t.false(isSvg('<div><svg></svg>'));
3228
t.false(isSvg('<div><svg></svg></div>'));
33-
t.false(isSvg('this string contains an svg <svg></svg> in the middle'));
34-
t.false(isSvg(fs.readFileSync('readme.md')));
3529
t.false(isSvg(fs.readFileSync('index.js')));
3630
t.false(isSvg());
31+
t.false(isSvg('this string contains an svg <svg></svg> in the middle'));
32+
t.false(isSvg('<svg><div></svg>'));
33+
t.false(isSvg('this string ends with an svg <svg></svg>'));
34+
t.false(isSvg('<svg> hello I am an svg oops maybe not'));
35+
t.false(isSvg('this is not svg, but it mentions <svg> tags'));
36+
t.false(isSvg(fs.readFileSync('readme.md')));
37+
38+
// https://github.com/NaturalIntelligence/fast-xml-parser/issues/327
39+
// t.false(isSvg('<svg></svg> this string starts with an svg'));
3740
});
3841

3942
test('supports non-english characters', t => {

0 commit comments

Comments
 (0)