Skip to content
This repository was archived by the owner on Apr 12, 2024. It is now read-only.

Commit feba017

Browse files
committed
fix($compile): remove comment nodes from templates before asserting single root node
The compiler will no longer throw if a directive template contains comment nodes in addition to a single root node. If a template contains less than 2 nodes, the nodes are unaltered. BREAKING CHANGE: If a template contains directives within comment nodes, and there is more than a single node in the template, those comment nodes are removed. The impact of this breaking change is expected to be quite low. Closes #9212 Closes #9215
1 parent 7b6c1d0 commit feba017

File tree

4 files changed

+58
-2
lines changed

4 files changed

+58
-2
lines changed

src/.jshintrc

+1
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111
"jqLite": false,
1212
"jQuery": false,
1313
"slice": false,
14+
"splice": false,
1415
"push": false,
1516
"toString": false,
1617
"ngMinErr": false,

src/Angular.js

+2
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
jqLite: true,
77
jQuery: true,
88
slice: true,
9+
splice: true,
910
push: true,
1011
toString: true,
1112
ngMinErr: true,
@@ -161,6 +162,7 @@ var /** holds major version number for IE or NaN for real browsers */
161162
jqLite, // delay binding since jQuery could be loaded after us.
162163
jQuery, // delay binding
163164
slice = [].slice,
165+
splice = [].splice,
164166
push = [].push,
165167
toString = Object.prototype.toString,
166168
ngMinErr = minErr('ng'),

src/ng/compile.js

+19-2
Original file line numberDiff line numberDiff line change
@@ -1623,7 +1623,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
16231623
if (jqLiteIsTextNode(directiveValue)) {
16241624
$template = [];
16251625
} else {
1626-
$template = jqLite(wrapTemplate(directive.templateNamespace, trim(directiveValue)));
1626+
$template = removeComments(wrapTemplate(directive.templateNamespace, trim(directiveValue)));
16271627
}
16281628
compileNode = $template[0];
16291629

@@ -2105,7 +2105,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
21052105
if (jqLiteIsTextNode(content)) {
21062106
$template = [];
21072107
} else {
2108-
$template = jqLite(wrapTemplate(templateNamespace, trim(content)));
2108+
$template = removeComments(wrapTemplate(templateNamespace, trim(content)));
21092109
}
21102110
compileNode = $template[0];
21112111

@@ -2519,3 +2519,20 @@ function tokenDifference(str1, str2) {
25192519
}
25202520
return values;
25212521
}
2522+
2523+
function removeComments(jqNodes) {
2524+
jqNodes = jqLite(jqNodes);
2525+
var i = jqNodes.length;
2526+
2527+
if (i <= 1) {
2528+
return jqNodes;
2529+
}
2530+
2531+
while (i--) {
2532+
var node = jqNodes[i];
2533+
if (node.nodeType === 8) {
2534+
splice.call(jqNodes, i, 1);
2535+
}
2536+
}
2537+
return jqNodes;
2538+
}

test/ng/compileSpec.js

+36
Original file line numberDiff line numberDiff line change
@@ -1078,6 +1078,22 @@ describe('$compile', function() {
10781078
});
10791079
});
10801080
}
1081+
1082+
it('should ignore comment nodes when replacing with a template', function() {
1083+
module(function() {
1084+
directive('replaceWithComments', valueFn({
1085+
replace: true,
1086+
template: '<!-- ignored comment --><p>Hello, world!</p><!-- ignored comment-->'
1087+
}));
1088+
});
1089+
inject(function($compile, $rootScope) {
1090+
expect(function() {
1091+
element = $compile('<div><div replace-with-comments></div></div>')($rootScope);
1092+
}).not.toThrow();
1093+
expect(element.find('p').length).toBe(1);
1094+
expect(element.find('p').text()).toBe('Hello, world!');
1095+
});
1096+
});
10811097
});
10821098

10831099

@@ -1977,6 +1993,26 @@ describe('$compile', function() {
19771993
});
19781994
});
19791995
}
1996+
1997+
it('should ignore comment nodes when replacing with a templateUrl', function() {
1998+
module(function() {
1999+
directive('replaceWithComments', valueFn({
2000+
replace: true,
2001+
templateUrl: 'templateWithComments.html'
2002+
}));
2003+
});
2004+
inject(function($compile, $rootScope, $httpBackend) {
2005+
$httpBackend.whenGET('templateWithComments.html').
2006+
respond('<!-- ignored comment --><p>Hello, world!</p><!-- ignored comment-->');
2007+
expect(function() {
2008+
element = $compile('<div><div replace-with-comments></div></div>')($rootScope);
2009+
}).not.toThrow();
2010+
$httpBackend.flush();
2011+
expect(element.find('p').length).toBe(1);
2012+
expect(element.find('p').text()).toBe('Hello, world!');
2013+
});
2014+
});
2015+
19802016
});
19812017

19822018

0 commit comments

Comments
 (0)