Исходное значение обновляется инжектором в тесте

#javascript #angular #jasmine #karma-jasmine

#javascript #angular #jasmine #карма-жасмин

Вопрос:

Я пытаюсь протестировать один из моих вводимых компонентов. Я использую провайдера, чтобы присвоить ему фиктивное значение APP_CONFIG . Вот как выглядит компонент:

 export let APP_CONFIG = new InjectionToken<any>('app.config');

@Injectable()
export class ConfigService {

   private readonly config;

   constructor(private injector: Injector) {
      this.config = this.injector.get(APP_CONFIG);
   }


   public update(): void {
      this.config.context = 'some value'
   }

   public get config(): any {
     return this.config
   }
}
  

И вот как выглядит настройка теста:

 const CONFIG = { context: 'cat' };

beforeEach(() => {
    TestBed.configureTestingModule({
        providers: [
            ConfigService,
            { provide: APP_CONFIG, useValue: CONFIG },
        ]
    });

    service = TestBed.inject(AppConfigService);
});
  

Проблема, с которой я сталкиваюсь, заключается в том, что при this.config = 'some value' возникновении в методе обновления он обновляет исходную ссылку в CONFIG объекте в моем тесте. Это вызывает проблемы в моем тесте, потому что я не могу правильно проверить, this.config изменилось ли оно, потому что оно всегда равно CONFIG .

Например:

 it('provides updated config after update', () => {
   const result: any = service.config;
   // CONFIG is currently {context: 'cat'}
   service.update();
   // Once service.update() occurs CONFIG gets changed to {context: 'some value'} and the following test fails as a result. I expect it to pass because result should be different from the original reference.
   expect(result).not.toEqual(CONFIG);
})
  

В результате это приводит к сбою любых других последующих тестов, которые импортируют CONFIG объект для сравнения, по той же причине.

Могу ли я что-нибудь сделать, чтобы предотвратить эту регрессию? Это начало происходить после обновления с Angular 8 до 9, поэтому я не уверен, были ли внесены какие-то изменения под капотом, которые изменяют то, как это работает.

Ответ №1:

Похоже, вы просто передаете одну и ту же ссылку и сравниваете ее с самой собой. Вам нужно будет клонировать исходный объект.

Самый простой способ imo — использовать оператор распространения:

 { provide: APP_CONFIG, useValue: ...CONFIG },
  

Комментарии:

1. какова цель оператора распространения здесь?

2. @CCBet оператор распространения эффективно клонирует распространяемый объект.