Angular testing - Тестирование взаимозависимых сервисов - PullRequest
0 голосов
/ 29 мая 2020

Я новичок в мире тестирования, извините, если этот вопрос слишком очевиден!

У меня есть полностью функциональный и сложный проект angular 9. Я объясню свою проблему простым языком:

У меня несколько служб:

  1. Service_MAIN (использует HttpClient, Router и т.д. c.)
  2. Service_A (использует Service_MAIN)
  3. Service_B (использует Service_MAIN и et c.)

Теперь я успешно протестировал Service_MAIN, создав шпионов, et c.

  let service: Service_MAIN;

  beforeEach(() => {
    httpClientSpy = jasmine.createSpyObj('HttpClient', ['get', 'put', 'post', 'delete', 'patch']);
    routerSpy = jasmine.createSpyObj('Router', ['navigate']);

    TestBed.configureTestingModule({
      imports: [MatSnackBarModule],
      providers: [
        Service_MAIN,
        {provide: HttpClient, useValue: httpClientSpy},
        {provide: Router, useValue: routerSpy},
        SnackBarService
      ]
    });
    service= TestBed.inject(Service_MAIN);
  });

  it('should be created', () => {
    expect(service).toBeTruthy();
  });
  ...
  ...

Теперь, когда я хочу протестировать Service_A и Service_B, мне снова нужно создать шпиона для моего Service_MAIN и передать httpClientspy, routerSpy и т.д. c.?

Кроме того, если я один раз создать шпиона для Service_MAIN, чтобы протестировать Service_A, нужно ли мне создать такого же шпиона для Service_B?

Это создаст много повторений в моих тестовых файлах.

ПРИМЕЧАНИЕ: Service_A не использует напрямую HTTPCLIENT, он использует Service_MAIN для косвенных вызовов HTTP.

1 Ответ

0 голосов
/ 29 мая 2020

При тестировании Service_A или Service_B, вы можете создать spyObj для Service_MAIN и имитировать методы publi c, от которых зависит Service_A или Service_B.

Пример для тестирования Service_A.

let service: Service_A;
let mockServiceMain: any

  beforeEach(() => {
    httpClientSpy = jasmine.createSpyObj('serviceMain', [/* Put the public methods of serviceMain here as comma separated strings*/]);

    TestBed.configureTestingModule({
      imports: [],
      providers: [
        // Inject the actual service because it is to be tested
        Service_A,
        // when the service requests for Service_MAIN, use the mock value
        { provide: Service_MAIN, useValue: mockServiceMain },
        // your other providers or mock providers can go here
      ]
    });
    service = TestBed.inject(Service_A);
  });

  it('should be created', () => {
    expect(service).toBeTruthy();
  });

Также для маршрутизатора вы должны импортировать RouterTestingModule, а не заглушать его (https://angular.io/api/router/testing/RouterTestingModule). То же самое и с HTTP, вы должны использовать HttpTestingController (https://angular.io/api/common/http/testing/HttpTestingController).

...