18

verwende ich John Papa Winkel Stil mein Controller führen wie folgt aussieht:Wie testen John Papa vm.model Komponententests mit Jasmin?

nach dem Stil John papa style controller style guide:

function testController() { 

    var vm = this; 

    vm.model = { name: "controllerAs vm test" }; 
} 

Mein Code Tests wie folgt aussieht:

describe('Controller: testController', function() { 

    beforeEach(module('myApp')); 

    var testController; 

    beforeEach(inject(function ($controller) { 
     scope = {}; 

     testController = $controller('testController', { 
     }); 

    })); 

    it('should have vm.model defined and testController.vm.model is equal to controllerAs vm test', function() { 
     expect(testController.vm).toBeDefined(); 
     expect(testController.vm.model).toBeDefined();  
     expect(testController.vm.model.name).toEqual("controllerAs vm test"); 
    }); 
}); 

Ergebnis:

-Test fehlgeschlagen: Ergebnismeldung: Erwartet undefiniert definiert. bei Stapel

Also meine Frage ist, wie können wir vm.model und andere Variablen aus diesem testen? controllers

Antwort

24

Die vm ist gleich der Instanz selbst über vm = this;

Daher werden alle Eigenschaften hängen direkt ab von dem Objekt: Ich habe nicht die richtige Führungslinie in den Führungslinien gefunden.

function foo(){ 
    var vm = this; 

    vm.name = 'Josh'; 
} 

var myFoo = new foo(); 
myFoo.name; // 'Josh'; 

Also alles, was Sie tun müssen, ist Ihre Erwartungen zu ändern, um die vm Eigenschaft zu entfernen.

expect(testController).toBeDefined(); 
expect(testController.model).toBeDefined();  
expect(testController.model.name).toEqual("controllerAs vm test"); 

Um diesen zu beweisen, hier ist Ihr genaues Beispiel, und die Jasmin-Tests verbunden ist.

function testController() { 
 

 
    var vm = this; 
 

 
    vm.model = { 
 
    name: "controllerAs vm test" 
 
    }; 
 
} 
 

 

 
angular.module('myApp', []) 
 
    .controller('testController', testController); 
 

 
describe('Controller: testController', function() { 
 

 
    beforeEach(module('myApp')); 
 

 
    var testController; 
 

 
    beforeEach(inject(function($controller) { 
 
    scope = {}; 
 

 
    testController = $controller('testController', {}); 
 

 
    })); 
 

 
    it('should have model defined and testController.model.name is equal to controllerAs vm test', function() { 
 
    expect(testController).toBeDefined(); 
 
    expect(testController.model).toBeDefined(); 
 
    expect(testController.model.name).toEqual("controllerAs vm test"); 
 
    }); 
 

 
    it('should not have a property called vm', function() { 
 
    expect(testController.vm).toBeUndefined(); 
 
    }); 
 
});
<link href="https://cdnjs.cloudflare.com/ajax/libs/jasmine/2.2.1/jasmine.css" rel="stylesheet" /> 
 
<script src="https://cdnjs.cloudflare.com/ajax/libs/jasmine/2.2.1/jasmine.js"></script> 
 
<script src="https://cdnjs.cloudflare.com/ajax/libs/jasmine/2.2.1/jasmine-html.js"></script> 
 
<script src="https://cdnjs.cloudflare.com/ajax/libs/jasmine/2.2.1/boot.js"></script> 
 
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.0-beta.4/angular.min.js"></script> 
 
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.0-beta.4/angular-mocks.js"></script>

+0

als eine Funktion sieht Ihre Antwort in Ordnung, aber hier ist mein Problem, wenn ich die Controller-Instanz initialisieren durch: testController = $ controller ('testController', { }); dann sollte testController.vm funktionieren, funktioniert aber nicht.Also meine Frage ist an die Jungs, die mit Winker John Papa's Controller als vm-Syntax gearbeitet und mit Jasmin getestet haben. –

+0

@UtpalKumarDas - Unter der Haube ruft '$ controller' gerade' new() 'auf, also funktioniert es genauso. – Josh

+2

@UtpalKumarDas - Ich arbeite seit einigen Jahren mit Angular und habe viele Tests mit Jasmine gemacht. Ich versuche zu erklären, dass das keine Winkelsache ist, sondern ein JavaScript. 'vm' ist keine Eigenschaft auf dem Controller ... es ist eine Variable, die vom Funktionsumfang geschlossen wird. Daher wird es ** niemals ** auf Ihrem Controller vorhanden sein, wenn Sie auf diese Weise verwendet werden. '$ controller' ändert nicht die Funktionsweise von JS. – Josh

6

testControllerist die vm weil Sie var vm = this in der Steuerung gesetzt. Also, um Ihren Testcode ähnlich Ihren Controller-Code zu machen, können Sie versuchen, Ihren Controller vm im Test gesetzt zu statttestController

describe('Controller: testController', function() { 
    // we work with "vm" instead of "testController" to have consistent verbiage 
    // in test and controller 
    var vm; 

    beforeEach(module('app')); 
    beforeEach(inject(function ($controller) { 
     vm = $controller('testController', {}, {}); 
    })); 

    it('should have vm.model defined and testController.vm.model is equal to controllerAs vm test', function() { 

     // vm=this in controller 
     expect(vm) 
      .toBeDefined(); 

     // Testing primitives 
     expect(vm.foo) 
      .toBeDefined(); 
     expect(vm.foo) 
      .toEqual('bar'); 

     // Testing objects 
     expect(vm.model) 
      .toBeDefined(); 
     expect(vm.model.name) 
      .toEqual("Batman"); 

     // Testing a method 
     expect(vm.greet()) 
      .toBeDefined(); 
     expect(vm.greet()) 
      .toEqual('Hello There'); 
    }); 
}); 

-Code für den Controller

(function() { 
    'use strict'; 

    angular 
     .module('app') 
     .controller('testController', testController); 

    /* @ngInject */ 
    function testController() { 
     var vm = this; 

     // Primitives 
     vm.foo = 'bar'; 

     // Objects 
     vm.model = { 
      name: 'Batman' 
     }; 

     // Methods 
     vm.greet = function() { 
      return 'Hello There'; 
     }; 
    } 
})(); 

Hoffe das hilft. Viel Glück.

1

Ich würde ein neues Modul erstellen und es als Abhängigkeit in die App-Modul injizieren, um es einfach und testbar zu machen. Style Guide Testen der Controller mit John Papas:

(function() { 
    'use strict'; 

    angular 
    .module('test') 
    .controller('testController', testController); 

    function testController() { 
    var vm = this; 
    vm.model = { name: "controllerAs vm test" }; 
    } 
})(); 

Die Spezifikation nun wie folgt aussehen:

'use strict'; 

describe('testController', function() { 
    var testController; 
    beforeEach(module('test')); 

    beforeEach(function() { 
    inject(function($injector) { 
     testController = $injector.get('$controller')('testController', {}); 
    }); 
    }); 

    it('should have model defined and testController.name is equal to controllerAs vm test', function() { 
    expect(testController).toBeDefined(); 
    expect(testController.name).toEqual("controllerAs vm test"); 
    }); 
}); 

hoffe, das hilft jemand der Suche nach ähnlichen Lösungen.

Verwandte Themen