Angular 使用 APP_INITIALIZER 加载配置
Angular loading config with APP_INITIALIZER
我正在尝试通过 Angular 8 中使用 APP_INITIALIZER 的服务加载配置文件 (json)。
配置包含缩略图的图像和道具路径
app-config.json
{
"substitutePictureLink": "../images/not_found.png",
"noImageFound": "../images/404_not_found.png",
"thumbnailProps": {
"width": "400",
"height": "400",
"format": "PNG",
"view": "Interior",
"withdimensions": "true",
"withdescription": "true"
}
}
为了加载配置,我创建了一个如下所示的服务 [app-config-service]:
app-config-service.ts
export class AppConfigService {
public get appConfig(): any {
return this._appConfig;
}
public set appConfig(value: any) {
this._appConfig = value;
}
private _appConfig: any;
constructor(
private _httpClient: HttpClient,
) {
console.log('constructor app-config-service');
this.loadAppConfig();
}
public loadAppConfig(): any {
//also tried a promise here
return this._httpClient.get('../../../assets/configs/app-config.json')
.pipe(
take(1)
)
.subscribe(
(config) => {
this._appConfig = config;
}
);
}
所以我需要在启动时加载配置;
app-module.ts
providers: [
AppConfigService,
{
provide: APP_INITIALIZER,
multi: true,
deps: [AppConfigService],
useFactory: (appConfigService: AppConfigService) => {
return () => {
return appConfigService.loadAppConfig();
};
}
}
],
bootstrap: [AppComponent],
})
export class AppModule {
}
当我尝试加载配置时,它看起来像这样:
一些-service.ts
export class someService {
private _noImageFound = this._appConfigService.appConfig.noImageFound;
constructor(
private _appConfigService: AppConfigService
) {
}
...
public getThumbnail(): Observable<SafeUrl> {
return this._httpClient.get(this._apiUrl + '/visual-tree/thumbnail?width=400&height=400', {
responseType: 'blob',
})
.pipe(
map((res: Blob): SafeUrl => this._blobToUrl.transform(res)),
catchError((err: HttpErrorResponse): Observable<string> => {
this._logger.error(ErrorMessage.thumbnailNotLoaded, err);
return of(this._noImageFound);
})
);
}
...
错误:
- 未捕获的类型错误:无法读取未定义的 属性 'noImageFound'
登录后直接出现此错误。
有趣的是,app-config-service 的构造函数被调用了两次。
我的猜测是该服务的引用发生了一些奇怪的事情。
原因是因为 Angular 只等待 Promises 而不是 Observables。如果您将 loadAppConfig 函数转换为 return Promise(尽管您的评论说您已经尝试过),它应该可以解决您的问题。我已经创建了您在此堆栈中概述的场景,希望这对您有所帮助!
低于
return this._httpClient.get('../../../assets/configs/app-config.json')
.pipe(take(1))
.subscribe((config) => { this._appConfig = config; });
至
return this._httpClient.get('assets/config/config.json')
.toPromise()
.then(result => {
this.appConfig = result;
return Promise.resolve(result);});}
我正在尝试通过 Angular 8 中使用 APP_INITIALIZER 的服务加载配置文件 (json)。 配置包含缩略图的图像和道具路径
app-config.json
{
"substitutePictureLink": "../images/not_found.png",
"noImageFound": "../images/404_not_found.png",
"thumbnailProps": {
"width": "400",
"height": "400",
"format": "PNG",
"view": "Interior",
"withdimensions": "true",
"withdescription": "true"
}
}
为了加载配置,我创建了一个如下所示的服务 [app-config-service]:
app-config-service.ts
export class AppConfigService {
public get appConfig(): any {
return this._appConfig;
}
public set appConfig(value: any) {
this._appConfig = value;
}
private _appConfig: any;
constructor(
private _httpClient: HttpClient,
) {
console.log('constructor app-config-service');
this.loadAppConfig();
}
public loadAppConfig(): any {
//also tried a promise here
return this._httpClient.get('../../../assets/configs/app-config.json')
.pipe(
take(1)
)
.subscribe(
(config) => {
this._appConfig = config;
}
);
}
所以我需要在启动时加载配置;
app-module.ts
providers: [
AppConfigService,
{
provide: APP_INITIALIZER,
multi: true,
deps: [AppConfigService],
useFactory: (appConfigService: AppConfigService) => {
return () => {
return appConfigService.loadAppConfig();
};
}
}
],
bootstrap: [AppComponent],
})
export class AppModule {
}
当我尝试加载配置时,它看起来像这样:
一些-service.ts
export class someService {
private _noImageFound = this._appConfigService.appConfig.noImageFound;
constructor(
private _appConfigService: AppConfigService
) {
}
...
public getThumbnail(): Observable<SafeUrl> {
return this._httpClient.get(this._apiUrl + '/visual-tree/thumbnail?width=400&height=400', {
responseType: 'blob',
})
.pipe(
map((res: Blob): SafeUrl => this._blobToUrl.transform(res)),
catchError((err: HttpErrorResponse): Observable<string> => {
this._logger.error(ErrorMessage.thumbnailNotLoaded, err);
return of(this._noImageFound);
})
);
}
...
错误:
- 未捕获的类型错误:无法读取未定义的 属性 'noImageFound'
登录后直接出现此错误。 有趣的是,app-config-service 的构造函数被调用了两次。 我的猜测是该服务的引用发生了一些奇怪的事情。
原因是因为 Angular 只等待 Promises 而不是 Observables。如果您将 loadAppConfig 函数转换为 return Promise(尽管您的评论说您已经尝试过),它应该可以解决您的问题。我已经创建了您在此堆栈中概述的场景,希望这对您有所帮助!
低于
return this._httpClient.get('../../../assets/configs/app-config.json')
.pipe(take(1))
.subscribe((config) => { this._appConfig = config; });
至
return this._httpClient.get('assets/config/config.json')
.toPromise()
.then(result => {
this.appConfig = result;
return Promise.resolve(result);});}