Angular 6依赖注入问题

时间:2018-10-29 19:35:58

标签: angular typescript dependency-injection angular6

我有一个跨平台的Angular应用程序,我需要检查该应用程序正在运行的平台,然后根据此信息决定注入服务。这是我的结构:

@NgModule({
  providers: [
    ConfigService,
     {
       provide: APP_INITIALIZER,
       useFactory: configFactory,
       deps: [ConfigService],
       multi: true
    },
    {
      provide: UserService,
      useFactory: userServiceFactory,
      deps: [
        ConfigService
      ],
      multi: true
    },

  ],
  bootstrap: [AppComponent]
})
export class AppModule { }

配置工厂返回Promise:

export function configFactory(configService: ConfigService): () => Promise<any> {
  return (): Promise<any> => {
    return new Promise(resolve => {
       Device.getInfo().then(info => {
          configService.platform = info.platform; // it either ios or web
       });
    });
  }
}

需要configService.platform来决定UserService提供程序,因此我拥有工厂方法:

const userServiceFactory = (configService: ConfigService): any => {
    if(configService.platform === 'ios') {
        return new UserServiceDevice()
    } else {
        return new UserWebServiceWeb();
    }
  }

config服务正确初始化,但是在它完成之前,growerServiceFactory运行并获得未定义的config.platform,因此,即使将ConfigService设置为依赖项,它实际上也不会等待configFactory解析。我该如何实现?对于这种情况有更好的方法吗?

1 个答案:

答案 0 :(得分:0)

与其在模块实例化时解决这个问题,不如使服务本身更灵活?我知道这不能解决您的原始问题,但可以解决您的问题。

修改后的UserService:

class PlatformAgnosticUserService implements IUserService {
   private service: IUserService;

   constructor(
      private _PLAT : Platform,
      private mobileUserService: MobileUserService,
      private webUserService: WebUserService
   ) {
      if (this._PLAT.is('ios') || this._PLAT.is('android'))
      {
         this.service = mobileUserService;
      }
      else
      {
         this.service = webUserService;
      }
   }

   userCreate(param: any) {
      this.service.userCreate(param);
   }

}

我知道那不是很好,但是这是我能想到的最好的了。

下面的旧答案

我认为您可能使事情复杂化了。为什么不简化为这样:

@NgModule({
  providers: [
    {
      provide: UserService,
      useFactory: userServiceFactory,
      deps: [],
      multi: true
    },

  ],
  bootstrap: [AppComponent]
})
export class AppModule { }

这:

    const growerServiceFactory = (configService: ConfigService): () => Promise<any> => {
return (): Promise<any> => {
    return new Promise(
       resolve => {
         Device.getInfo().then(info => {
            return new UserServiceDevice();
       },
       () => {
         return new UserWebServiceWeb()
       });
    });
  }

不确定是否将config服务用于其他任何用途,但至少在这种情况下可以“跳过”。