最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Angular Testing Directive with templateUrl & isolate scope - Stack Overflow

programmeradmin0浏览0评论

New at angular.js and can't figure out how to write test for directive with templateUrl & isolate scope.

Here is my controller

(function(){
angular.module('buttons')
    .controller('buttonController', ['$scope', function($scope){

        //primary button
        $scope.primaryButton = { name: 'Submit'};
})();

Here is my views index.html &

<div class="layoutLeft">
        <p>Primary Button</p>
        <primary-button info="primaryButton"></primary-button>
    </div>

primary-button.html

<button class="{{buttonInfo.class}}">{{buttonInfo.name}}</button>

Here is my directive

(function(){
    angular.module('buttons')
        .directive('primaryButton', function() {
            return {
                restrict: 'EA',
                scope: {
                    buttonInfo: '=info'
                },
                templateUrl: 'scripts/local/views/primary-button.html'
            }
        })
    })();

Here is my test

(function(){
    beforeEach(angular.mock.module('buttons'));
describe('Buttons Directive Test', function(){

    var $pile, $scope, $httpBackend;

    beforeEach(module('templates'));

    beforeEach(inject(function(_$pile_, _$rootScope_) {
        $pile = _$pile_;
        $scope = _$rootScope_.$new();

        $scope.primaryButton = {name: 'Save'};

        elm = angular.element("<primary-button info='buttonInfo'></primary-button>");
        e = $pile(elm)($scope);
        e.digest();
    }));

    it('should do something', function(){
        expect(e.html()).toContain($scope.primaryButton);
    });
});

})();

I am using jasmine and karma for testing, can someone guide some light on what I am doing wrong

New at angular.js and can't figure out how to write test for directive with templateUrl & isolate scope.

Here is my controller

(function(){
angular.module('buttons')
    .controller('buttonController', ['$scope', function($scope){

        //primary button
        $scope.primaryButton = { name: 'Submit'};
})();

Here is my views index.html &

<div class="layoutLeft">
        <p>Primary Button</p>
        <primary-button info="primaryButton"></primary-button>
    </div>

primary-button.html

<button class="{{buttonInfo.class}}">{{buttonInfo.name}}</button>

Here is my directive

(function(){
    angular.module('buttons')
        .directive('primaryButton', function() {
            return {
                restrict: 'EA',
                scope: {
                    buttonInfo: '=info'
                },
                templateUrl: 'scripts/local/views/primary-button.html'
            }
        })
    })();

Here is my test

(function(){
    beforeEach(angular.mock.module('buttons'));
describe('Buttons Directive Test', function(){

    var $pile, $scope, $httpBackend;

    beforeEach(module('templates'));

    beforeEach(inject(function(_$pile_, _$rootScope_) {
        $pile = _$pile_;
        $scope = _$rootScope_.$new();

        $scope.primaryButton = {name: 'Save'};

        elm = angular.element("<primary-button info='buttonInfo'></primary-button>");
        e = $pile(elm)($scope);
        e.digest();
    }));

    it('should do something', function(){
        expect(e.html()).toContain($scope.primaryButton);
    });
});

})();

I am using jasmine and karma for testing, can someone guide some light on what I am doing wrong

Share Improve this question asked Dec 29, 2014 at 23:54 Varun ShethVarun Sheth 1561 gold badge1 silver badge13 bronze badges 1
  • Did my solution solve your problems? Please let me know. – Peter Ashwell Commented Jan 3, 2015 at 10:45
Add a ment  | 

2 Answers 2

Reset to default 6 +50

Edit: Here is a plunkr demonstrating pretty close to what your code was doing. There are multiple issues with the code you have in your question that I have fixed:

http://plnkr.co/edit/QXprEUof2Ps0Vivg4L34?p=preview

  1. In your test you call e.digest(), which will not work because you cannot digest an element... you should call $scope.$digest instead.
  2. e.html() will not contain that JSON blob. I interpreted this as wanting it to contain the name label...
  3. info='buttonInfo' binds info to the attribute buttonInfo in the outerscope, but you called it 'primaryButton'. Rename $scope.primaryButton to $scope.buttonInfo
  4. You used some underscores that weren't totally necessary, but that's not a big deal, when injecting pile, rootscope
  5. I used an inline template instead of loading it just for the plunkr, there is nothing wrong with loading it though
  6. Because your directive is an element I added 'replace', which replaces the element with a straight button. Consider making it an attribute instead.

My plunkr has passing jasmine tests and a working demonstration of the button. Let me know if you need some more help with this. Good luck with AngularJS.

(OLD ANSWER)

==============

You will need to use something like nghtml2js to load your templates and make them available with template cache.

using nghtml2js

That's your first issue. Your second issue is getting the isolate scope is done by calling isolateScope() on the element after it is piled. Log the result of calling that on elem and you'll find the attributes you're after.

e.isolateScope()

Not following why the above answer is marked accepted. The question asks how to acplish using templateUrl while @PeterAshwell's answer provides a solution with inline HTML that does not work when using templateUrl.

To gain access to the isolate scope when using templateUrl, you must wrap the isolateScope call in a $timeout to allow the $http call (made by templateUrl) to plete.

Code would look something like:

element = $pile("<myHTML />")($scope)

$timeout(function() {
     expect(element.isolateScope().myProp).toEqual(12);

}), 0 , false);

$timeout.flush();
发布评论

评论列表(0)

  1. 暂无评论