角度测试用例错误:无法读取未定义的属性serviceUrl

问题描述 投票:0回答:1

MyService.ts文件当我们从secp文件serviceURl调用服务时变得未定义。

import { async, ComponentFixture, TestBed } from '@angular/core/testing';
    export class Sendnotificationservice {
      constructor(private http: HttpClient) {} 
      public sendnotification(
        notificationModel: SendnotificationToModel
      ): Observable<any> {
        return this.http.post<any>(
          AppConfig.settings.serviceUrl +
            'api/Sendnotificationservice/sendnotification',
          notificationModel
          //AppConfig.setting.serviceUrl getting cannot read property serviceurl of undefined
        );
      }
    }

Myservice.spec.ts 从这里我们在调用服务时无法调用appconfig.ts返回数据的规范

import { Injectable, Injector, OnInit } from "@angular/core";
import { HttpClient, HttpResponce } from "@angular/common/http";
import { IAppConfig } from "./app-config.model";
    describe('Sendnotificationservice', () => {
      let service: Sendnotificationservice;
      let httpSpy: HttpTestingController;
      beforeEach(() => {
        TestBed.configureTestingModule({
          imports: [HttpclientTestingModule],
          providers: [Sendnotificationservice],
        });
        service = TestBed.get(Sendnotificationservice);
        service = TestBed.get(HttpTestingController);
      });
      it('it should get mail', () => {
        const test = {
          clientno: '',
          firstName: 'dev',
          lastName: 'som',
          phoneNo: '484758373',
        };
        service.sendnotification(test).subscribe((data) => {
          expect(data).toEqual(false);
        });
      });
    });

AppConfig.ts无法将返回数据模拟到服务测试用例文件中

import { Injectable, Injector, OnInit } from "@angular/core";
import { HttpClient, HttpResponce } from "@angular/common/http";
import { IAppConfig } from "./app-config.model";
import { environment } from "src/environments/environment";
@Injectable()
export class AppConfig {
  static settings: iAppConfig;
  constructor(private http:HttpClient) {}
  load() {
    const jsonFile =
      window.location.hostname.toLowerCase().indexof("localhost") !== -1
        ? 'assets/config/config.local.json'
        : 'assets/config/config.${environment.name}.json';
      return new Promise<any>((resolve, reject) => {
        this.http
          .get(jsonFile)
          .toPromise()
          .them((response: Response) => {
            AppConfig.settings = <any>response;
            resolve();
          })
          .catch((response: any) => {
            reject(
              'could not load file '${jsonFile}': ${JSON.stringify(response)}
            );
          });
      });
    }
  }
angular karma-jasmine web-frontend angular-testing servicetestcase
1个回答
0
投票

这不是您应该在单元测试中模拟的方式。现在,您的应用程序代码中已经包含测试代码,并且还应该测试该测试代码,如果继续这样,您将陷入测试测试代码的无限循环中,以测试测试代码。

最好还是模拟AppConfig服务:

import appConfig from 'assets/config/config.local.json';

class MockAppConfig {
  static settings: IAppConfig = appConfig as IAppConfig;
}

TestBed.configureTestingModule({
  imports: [HttpclientTestingModule],
  providers: [
    Sendnotificationservice, 
    { provide: AppConfig, useClass: MockAppConfig }
  ],
});

为了使这项工作有效,您可能必须将"resolveJsonModule": true设置为tsconfig.spec.json。考虑到您很可能不再提供此JSON文件,您也可以仅导出对象而不是.json文件。这也可以通过代码提示确保事物的类型安全。

尽管如此,您还没有到那儿,因为您无法测试这样的Observable响应。您将收到一条错误消息,提示您“它没有期望”。有多种解决方法,一个简单的方法就是调用done

it('it should get mail', (done) => {
  const test = {
    clientno: '',
    firstName: 'dev',
    lastName: 'som',
    phoneNo: '484758373',
   };

   service.sendnotification(test).subscribe((data) => {
     expect(data).toEqual(false);
     done(); // here
   });
});

尽管这对我还是有点奇怪。您并没有真正测试服务对象,但是您似乎正在测试API响应。此测试应该在调用API的后端进行,或者通过使用Integration / e2e测试来确保API正常工作]

© www.soinside.com 2019 - 2024. All rights reserved.