Angular 如何在函数中以编程方式注入 @Injectable

问题描述

我试图以编程方式将提供者注入到 reducer 函数中,但它失败了。我曾尝试在各种组合中使用 Injector.create(...) 以及 inject(DependencyClass),但由于缺少 LocaleId 或“inject() must从注入上下文中调用”。 欢迎任何建议。

依赖项和客户端代码位于不同的模块中。依赖项通过@Inject(InjectionToken)注入另一个角度资源。

依赖(提供者)

我尝试注入的依赖项如下所示:

import {Inject,Injectable,LOCALE_ID} from '@angular/core';
import {DecimalPipe} from '@angular/common';


@Injectable({
  providedIn: 'root'
})
export class LocalizeUtil {
  constructor(
    @Inject(LOCALE_ID) private locale,private decimalPipe: DecimalPipe
  ) { }

  localize(...): string {
    ...
  }

  // business methods omitted

}

它 - 连同它自己的依赖 - 在应用模块中声明为提供者:

@NgModule({
  declarations: [
    AppComponent
  ],imports: [
    browserModule,CoreModule,RootStoreModule,HomeModule,StoreDevtoolsModule,],providers: [
    LocalizeUtil,DecimalPipe
  ],bootstrap: [
    AppComponent
  ]
})
export class AppModule { }

在客户端代码模块中:

@NgModule({
  declarations: [
    ...
  ],exports: [
    ...
  ],imports: [
    CommonModule,ReactiveFormsModule,HttpClientModule,SharedModule,providers: [
    ...
    LocalizeUtil,DecimalPipe,...
  ]
})
export class ClientModule { }

甚至在它自己的模块中:

@NgModule({
  ...
  providers: [
    DecimalPipe,LocalizeUtil
  ]
})
export class SharedModule { }

客户端代码

像这样在客户端模块中使用注入器创建/获取

import {Injector} from '@angular/core';
import {LocalizeUtil} from '@shared/utils/localize-util';    
function localize(numerical: number): string {
      
      const injector = Injector.create({
          providers: [{provide: LocalizeUtil,deps:[LOCALE_ID]}]
      });
      
      let localizer: LocalizeUtil;
      try {
        localizer = injector.get(LocalizeUtil);
      } catch (e) {
        console.log(e);
      }  
      return localizer.localize(numerical,1,2);
    }

生产

NullInjectorError: R3InjectorError[LocalizeUtil -> InjectionToken LocaleId]: NullInjectorError: No provider for InjectionToken LocaleId! at NullInjector.get

像这样在客户端模块中使用 inject()

import {inject} from '@angular/core';
import {LocalizeUtil} from '@shared/utils/localize-util';

function localize(numerical: number): string {
  let localizer: LocalizeUtil;
  try {
    localizer = inject(LocalizeUtil);          
  } catch (e) {
    console.log(e);
  }
  
  return localizer.localize(numerical,2);
}
          
          

产生:

Error: inject() must be called from an injection context at injectInjectorOnly

编辑

我最终可以通过将实用程序类注入到触发此 reducer 的效果类中来避免这个问题,在那里正常注入照常工作。我真的不认为这个特殊的实用程序是一个副作用,因为它没有调用任何异步的东西。尽管如此,对于偶尔的路人来说,它可能看起来像是一种副作用,所以我喜欢将其视为一种改进。问题仍然存在,为什么不能通过调用 inject()Injector 进行注入。

解决方法

暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!

如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。

小编邮箱:dio#foxmail.com (将#修改为@)