unit test mocks karma e2e testing angularjs mocking inject

testing - test - karma angularjs



Error al obtener un proveedor desconocido al inyectar un servicio en una prueba de unidad angular (4)

¿Has intentado definir un módulo adicional que depende de tus otros módulos agregados de la siguiente manera:

angular.module( ''dashboard'', [ ''dashboard.services'', ''dashboard.controllers'' ] )

De modo que puede especificar en el beforeEach el único módulo que tiene ambos submódulos definidos de la siguiente manera:

describe(''Browse Controller Tests.'', function () { beforeEach(function () { module(''dashboard''); }); var controller, scope, eventingService; beforeEach(inject(function ($controller, $rootScope, EventingService) { scope = $rootScope.$new(); eventingService = EventingService controller = $controller(''Browse'', { $scope: scope, eventing: eventingService }); })); it(''Expect True to be True'', function () { expect(true).toBe(true); }); });

Soy bastante nuevo en Angular y he revisado todas las preguntas similares relacionadas con Stack Overflow pero ninguna me ha ayudado. Creo que tengo todo configurado correctamente pero sigo recibiendo un error de ''Proveedor desconocido'' cuando intento inyectar un servicio en una prueba unitaria. He presentado mi código a continuación - ¡con suerte alguien puede detectar un error obvio!

Defino mis módulos en un archivo .js separado como este:

angular.module(''dashboard.services'', []); angular.module(''dashboard.controllers'', []);

Aquí es donde defino un servicio llamado EventingService (con lógica eliminada por brevedad):

angular.module(''dashboard.services'').factory(''EventingService'', [function () { //Service logic here }]);

Aquí está mi controlador que usa el EventingService (todo funciona bien en tiempo de ejecución):

angular.module(''dashboard.controllers'') .controller(''Browse'', [''$scope'', ''EventingService'', function ($scope, eventing) { //Controller logic here }]);

Aquí está mi prueba unitaria: es la línea donde intento inyectar el EventingService que causa un error cuando ejecuto la prueba unitaria:

describe(''Browse Controller Tests.'', function () { beforeEach(function () { module(''dashboard.services''); module(''dashboard.controllers''); }); var controller, scope, eventingService; beforeEach(inject(function ($controller, $rootScope, EventingService) { scope = $rootScope.$new(); eventingService = EventingService controller = $controller(''Browse'', { $scope: scope, eventing: eventingService }); })); it(''Expect True to be True'', function () { expect(true).toBe(true); }); });

Cuando ejecuto la prueba obtengo este error:

Error: proveedor desconocido: EventingServiceProvider <- EventingService

Me he asegurado de que mi archivo jasmine specrunner.html tenga todos los archivos fuente necesarios (este es un proyecto Asp.Net MVC):

<!-- Include source files here... --> @Scripts.Render("~/bundles/jquery") <script type="text/javascript" src="@Url.Content("~/Scripts/angular.js")"></script> <script type="text/javascript" src="@Url.Content("~/Scripts/angular-mocks.js")"></script> <script type="text/javascript" src="@Url.Content("~/App/scripts/app.js")"></script> <!-- Angular modules defined in here --> <script type="text/javascript" src="@Url.Content("~/App/scripts/services/eventing.js")"></script> <!-- My Eventing service defined here --> <script type="text/javascript" src="@Url.Content("~/App/scripts/controllers/browse.js")"></script> <!-- My Browse controller defined here --> <!-- Include spec files here... --> <script type="text/javascript" src="@Url.Content("~/App/tests/browse.js")"></script> <!-- The actual unit test here -->

Simplemente no puedo entender por qué Angular está lanzando este error quejándose de mi EventingService. Mi controlador funciona bien en tiempo de ejecución; justo cuando intento probarlo, me aparece un error, así que tengo curiosidad de saber si he arruinado algo con la burla / inyección.

La ayuda de Angular en las pruebas es basura, así que estoy perplejo en este momento; cualquier ayuda o sugerencia que alguien pueda dar sería muy apreciada. Gracias.


Acabo de encontrarme con esto y lo resolví cambiando a obtener el servicio usando $ injector explícitamente:

var EventingService, $rootScope; beforeEach(inject(function($injector) { EventingService = $injector.get(''EventingService''); $rootScope = $injector.get(''$rootScope''); }));

Desearía poder decirte por qué funciona esto y por qué el simple

beforeEach(inject(function(EventingService) { .... }));

no, pero no tengo tiempo para investigar las partes internas. Siempre es mejor utilizar un estilo de codificación y atenerse a él.

Este estilo es mejor porque el nombre de la variable que usa en sus pruebas es el nombre correcto del Servicio. Pero es un poco detallado.

Hay otra característica de magia angular que usa nombres de variables extraños como $ rootScope pero no me gusta el aspecto hacky de eso.

Tenga en cuenta que la mayoría de las veces las personas obtienen este error porque no incluyeron los módulos:

beforeEach(module(''capsuling'')); beforeEach(module(''capsuling.capsules.services''));


Si bien esta pregunta es bastante antigua, perdí mucho tiempo resolviendo un problema similar a este, es decir:

Error: Unknown provider: SomeServiceProvider <- SomeService

Por lo tanto, me voy de aquí otra posible causa para este problema. Con suerte, sería útil para alguien.

En mi caso, tenía en mi proyecto dos módulos con exactamente el mismo nombre pero con diferentes dependencias que se creaban, es decir, dos archivos .js diferentes con:

angular.module(''moduleName'', [dependencies]))

De la documentación angular:

Pasar un argumento recupera un angular.Module existente, mientras que pasar más de un argumento crea un nuevo angular.Module

Conclusión : resultó que lo que se estaba inyectando en la prueba era el módulo con las dependencias incorrectas. La eliminación del segundo argumento del módulo que se estaba creando erróneamente resolvió el problema.


Si sus controladores (definidos en el módulo dashboard.controllers ) dependen de algunos servicios que están encerrados en un módulo diferente ( dashboard.services ) de lo que necesita para hacer referencia a los módulos de dependencia en la firma de su módulo:

angular.module(''dashboard.services'', []); angular.module(''dashboard.controllers'', [''dashboard.services'']);