角服务-子类构造函数是否必需或无法解析ClassName的所有参数(?)

时间:2019-05-20 14:50:34

标签: angular typescript

最近,我正在研究一组全部从基Service类继承的服务。基类采用HttpClient的构造函数(DI)参数。

当对子类使用自动完成功能时,我可以看到它们的构造函数参数正确说明了基类需要HttpClient的事实。但是,除非我在子类中明确地放置一个虚拟构造函数,否则Angular会在运行时抱怨以下内容:

  

错误:无法解析MyService的所有参数:(?)。

为什么子类中需要一个无用的构造函数?

请注意我的代码结构如下:

export abstract class MyBaseService {

    constructor(protected http: HttpClient) {     }

    ...
}

export class MyService extends MyBaseService {

    constructor(http: HttpClient) {     
      super(http);   // don't understand why we need this...
    }

    ...
}

注意:这似乎与抽象类严格相关;常规类的子类似乎没有表现出这种行为。

2 个答案:

答案 0 :(得分:1)

您是否尝试删除MyService类中的构造函数?
我已经遇到了同样的问题,但这是针对组件的。
在这种情况下,我使用以下解决方案:

MyBaseService如下所示。

export abstract class MyBaseService {

    constructor(
      @Injectable(HttpClient) protected http: HttpClient
    ){}

    ...
}

MyService类使您离开:

export class MyService extends MyBaseService {
    // do something here
}

尝试一下,如果不起作用,请告诉我

答案 1 :(得分:1)

我们遇到了同样的问题,解决方案是(稍微违反直觉)用Injectable()装饰器装饰基类定义。示例:

import { Injectable } from '@angular/core';

@Injectable()
export abstract class MyBaseService {

    constructor(protected http: HttpClient) {     }

    // ...
}

export class MyService extends MyBaseService {

    // ? A constructor is no longer required!

    // ...
}

装饰器使TypeScript编译器发出包含某些类型元数据的JavaScript代码,否则这些元数据将丢失。 Angular JIT编译器(与Angular AOT编译器不同)需要此元数据来解决问题。

我从Angular仓库的this helpful GitHub issue thread中学到了这一点。