Тестирование компонента, который зависит от 2 сервисов - PullRequest
1 голос
/ 08 июня 2019

У меня есть компонент, который использует сервис для получения информации. Но эта служба также получает конфиги от службы конфигурации от статической переменной conf При запуске тестов кармы переменная const не определена.

Мне известно, что я могу создать фиктивный сервис, однако мне нужно создать 2 сервиса для тестирования этого компонента? И если да, у меня есть другие сервисы, которые также используют Сервис конфигурации, поэтому мне нужно создать фиктивный сервис для каждого из них? Похоже, много работы, но я не нашел лучшего решения :( Я предоставил и ConfigurationService, и сервис, которым я пользуюсь, если это что-то меняет.

TypeError: Cannot read property 'apiUrl' of undefined

apiUrl - это свойство conf, которое является статической переменной в ConfigurationService.

ConfigService.ts

import {Injectable} from '@angular/core';
import {HttpClient} from '@angular/common/http';

import * as YAML from 'js-yaml';
import {Config} from './models/Config';


@Injectable()
export class ConfigService {
  public static  conf: Config;

  constructor(private http: HttpClient) {}
   async load() {
       const res = await this.http.get<Config>('assets/config.yml', {responseType: 'text' as 'json'}).toPromise();
       ConfigService.conf = YAML.load(res).environment;
  }
}

InfoService.ts

export class InfoService {
  private InfoUrl = ConfigService.conf.apiUrl + '/info';

  constructor(private http: HttpClient) {}
  getInfo(){
    return http.get(InfoUrl);
  }
}

InfoComponent.ts

export class InfoComponent implements OnInit {
  private info;
  constructor(private infoService: InfoService) {}

  ngOnInit() {}

  loadInfo() {
    this.info = this.infoService.getInfo();
  }

InfoComponent.spec.ts

import { async, ComponentFixture, TestBed } from '@angular/core/testing';
import { InfoComponent } from './info.component';
import {HttpClientModule} from '@angular/common/http';
import {InfoService} from './info.service';
import {ConfigService} from '../shared/config.service';


describe('InfoComponent', () => {
  let component: InfoComponent;
  let fixture: ComponentFixture<InfoComponent>;

  beforeEach(async(() => {
    TestBed.configureTestingModule({
      imports: [HttpClientModule],
      declarations: [InfoComponent],
      providers: [
          ConfigService
          InfoService,
      ],
    })
    .compileComponents();
  }));

  beforeEach(() => {
    fixture = TestBed.createComponent(InfoComponent);
    component = fixture.componentInstance;
    fixture.detectChanges();
  });

   it('should create', () => {
     expect(component).toBeTruthy();
   });
});

1 Ответ

1 голос
/ 10 июня 2019

В основном ваш компонент нуждается в InfoService. Основная концепция модульного тестирования вращается вокруг изоляции целевого кода и его тестирования. Итак, в вашем случае вам не нужно создавать зависимость от ConfigService. Должен быть отдельный юнит-тест для проверки поведения ConfigService

class InfoServiceStub {
  getInfo(){
    return of({
        /// your mock data
     });
  }
}


describe('InfoComponent', () => {
  let component: InfoComponent;
  let fixture: ComponentFixture<InfoComponent>;

  beforeEach(async(() => {
    TestBed.configureTestingModule({
      imports: [HttpClientModule],
      declarations: [InfoComponent],
      providers: [
          {provide: InfoService, useClass: InfoServiceStub },
      ],
    })
    .compileComponents();
  }));

  beforeEach(() => {
    fixture = TestBed.createComponent(InfoComponent);
    component = fixture.componentInstance;
    fixture.detectChanges();
  });

   it('should create', () => {
     expect(component).toBeTruthy();
   });
});
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...