From 69f42b76548d00f52b231ec91150e4f0b008c730 Mon Sep 17 00:00:00 2001 From: Igor Minar Date: Tue, 2 Jul 2013 17:23:51 -0700 Subject: fix($compile): prevent infinite loop w/ replace+transclude directives Previously if a template contained a directive that had a template (sync or async) and the directive template was to replace the original element and the directive template contained another directive on the root element of this template and this new directive was an element transclude directive then an infinite recursion would follow because the compiler kept on re-adding and reapplying the original directive to the replaced node. This change fixes that. Closes #2155 --- test/ng/directive/ngRepeatSpec.js | 57 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 57 insertions(+) (limited to 'test') diff --git a/test/ng/directive/ngRepeatSpec.js b/test/ng/directive/ngRepeatSpec.js index be4ff3e5..492f851d 100644 --- a/test/ng/directive/ngRepeatSpec.js +++ b/test/ng/directive/ngRepeatSpec.js @@ -454,6 +454,63 @@ describe('ngRepeat', function() { describe('nesting in replaced directive templates', function() { + it('should work when placed on a non-root element of attr directive with SYNC replaced template', + inject(function($templateCache, $compile, $rootScope) { + $compileProvider.directive('rr', function() { + return { + restrict: 'A', + replace: true, + template: '
{{i}}|
' + }; + }); + element = jqLite('
{{i}}|
'); + $compile(element)($rootScope); + $rootScope.$apply(); + expect(element.text()).toBe(''); + + $rootScope.items = [1, 2]; + $rootScope.$apply(); + expect(element.text()).toBe('1|2|'); + expect(sortedHtml(element)).toBe( + '
' + + '' + + '
1|
' + + '
2|
' + + '
' + ); + })); + + + it('should work when placed on a non-root element of attr directive with ASYNC replaced template', + inject(function($templateCache, $compile, $rootScope) { + $compileProvider.directive('rr', function() { + return { + restrict: 'A', + replace: true, + templateUrl: 'rr.html' + }; + }); + + $templateCache.put('rr.html', '
{{i}}|
'); + + element = jqLite('
{{i}}|
'); + $compile(element)($rootScope); + $rootScope.$apply(); + expect(element.text()).toBe(''); + + $rootScope.items = [1, 2]; + $rootScope.$apply(); + expect(element.text()).toBe('1|2|'); + expect(sortedHtml(element)).toBe( + '
' + + '' + + '
1|
' + + '
2|
' + + '
' + ); + })); + + it('should work when placed on a root element of attr directive with SYNC replaced template', inject(function($templateCache, $compile, $rootScope) { $compileProvider.directive('replaceMeWithRepeater', function() { -- cgit v1.2.3