Skip to content

Commit b0e7897

Browse files
authored
Merge pull request #28 from kranges/master
Better Attr Parsing
2 parents b55a8d9 + 6222dba commit b0e7897

File tree

2 files changed

+53
-18
lines changed

2 files changed

+53
-18
lines changed

lib/parse-tag.js

Lines changed: 36 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
1-
var attrRE = /([\w-]+)|['"]{1}([^'"]*)['"]{1}/g;
1+
var attrRE = /\s([^'"/\s><]+?)[\s/>]|([^\s=]+)=\s?(".*?"|'.*?')/g
22

33
// create optimized lookup object for
4-
// void elements as listed here:
4+
// void elements as listed here:
55
// http://www.w3.org/html/wg/drafts/html/master/syntax.html#void-elements
66
var lookup = (Object.create) ? Object.create(null) : {};
77
lookup.area = true;
@@ -22,8 +22,6 @@ lookup.track = true;
2222
lookup.wbr = true;
2323

2424
module.exports = function (tag) {
25-
var i = 0;
26-
var key;
2725
var res = {
2826
type: 'tag',
2927
name: '',
@@ -32,21 +30,41 @@ module.exports = function (tag) {
3230
children: []
3331
};
3432

35-
tag.replace(attrRE, function (match) {
36-
if (i % 2) {
37-
key = match;
38-
} else {
39-
if (i === 0) {
40-
if (lookup[match] || tag.charAt(tag.length - 2) === '/') {
41-
res.voidElement = true;
42-
}
43-
res.name = match;
44-
} else {
45-
res.attrs[key] = match.replace(/['"]/g, '');
46-
}
33+
let tagMatch = tag.match(/<\/?([^\s]+?)[/\s>]/)
34+
if(tagMatch)
35+
{
36+
res.name = tagMatch[1];
37+
if (lookup[tagMatch[1].toLowerCase()] || tag.charAt(tag.length - 2) === '/')
38+
res.voidElement = true;
39+
40+
}
41+
42+
let reg = new RegExp(attrRE)
43+
let result = null;
44+
for (; ;)
45+
{
46+
result = reg.exec(tag);
47+
48+
if (result === null)
49+
break;
50+
51+
if (!result[0].trim())
52+
continue;
53+
54+
if (result[1])
55+
{
56+
let attr = result[1].trim();
57+
let arr = [attr, ""];
58+
59+
if(attr.indexOf("=") > -1)
60+
arr = attr.split("=");
61+
62+
res.attrs[arr[0]] = arr[1];
63+
reg.lastIndex--;
4764
}
48-
i++;
49-
});
65+
else if (result[2])
66+
res.attrs[result[2]] = result[3].trim().substring(1,result[3].length - 1);
67+
}
5068

5169
return res;
5270
};

test/parse-tag.js

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -53,5 +53,22 @@ test('parseTag', function (t) {
5353
children: []
5454
});
5555

56+
tag = '<svg aria-hidden="true" style="position: absolute; width: 0; height: 0; overflow: hidden;" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" data-id="175">'
57+
58+
t.deepEqual(parseTag(tag), {
59+
type: 'tag',
60+
name: 'svg',
61+
attrs: {
62+
'aria-hidden': 'true',
63+
'data-id': '175',
64+
style: 'position: absolute; width: 0; height: 0; overflow: hidden;',
65+
version: '1.1',
66+
xmlns: 'http://www.w3.org/2000/svg',
67+
'xmlns:xlink': 'http://www.w3.org/1999/xlink'
68+
},
69+
voidElement: false,
70+
children: []
71+
}, 'should parse tags containing attributes with hyphens and/or colons');
72+
5673
t.end();
5774
});

0 commit comments

Comments
 (0)