I'm trying to inject a variable into forRoot({[...]})
method of an Angular module.
I got this variable in an asynchronous way, so I tried to get it before bootstrap Angular. (It comes from cordova.js)
The problem:
It seems that Angular import the modules (and call the 'forRoot' methods) before being bootstrapped.
Is there a way to achieve this ?
Thanks !
An example of what I tried:
app.module.ts
import {NgModule} from '@angular/core';
import {AgmCoreModule} from '@agm/core';
@NgModule({
imports: [
AgmCoreModule.forRoot({
apiKey: window['device'].platform, // value is 'null' instead of 'browser' or something else
libraries: ['places']
})
],
// [...]
bootstrap: [AppComponent]
})
export class AppModule {
}
src/main.ts
import { enableProdMode } from '@angular/core';
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
import { AppModule } from './app/app.module';
import { environment } from './environments/environment';
if (environment.production) {
enableProdMode();
}
document.addEventListener('deviceready', () => {
console.log(window['device'].platform); // log 'browser'
platformBrowserDynamic().bootstrapModule(AppModule)
.catch(err => console.log(err));
}, false);
/!\ Tips
The library I'm using (@agm/core) expect a string as apiKey, and not a function...
You can use APP_INITIALIZER to provide a factory which will be executed after module imports but before Bootstrap. So you can set the apiKey to any value and override it in the factory: Create a function to fetch die needed data and set the apiKey into the LAZY_MAPS_API_CONFIG
Object.
The Application bootstrap will continue once all the APP_INITIALIZERS
have resolved.
import { NgModule, APP_INITIALIZER } from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { HttpClientModule, HttpClient } from '@angular/common/http';
import { AgmCoreModule, LAZY_MAPS_API_CONFIG, LazyMapsAPILoaderConfigLiteral } from '@agm/core';
import { AppComponent } from './app.component';
import { map } from 'rxjs/operators';
export function agmConfigFactory(http: HttpClient, config: LazyMapsAPILoaderConfigLiteral) {
return () => http.get<{mapsApiKey: string}>("url").pipe(
map(response => {
config.apiKey = response.mapsApiKey;
return response;
})
).toPromise();
}
@NgModule({
imports: [ BrowserModule, HttpClientModule, AgmCoreModule.forRoot({ apiKey: "initialKey"}) ],
declarations: [ AppComponent ],
providers: [ {
provide: APP_INITIALIZER,
useFactory: agmConfigFactory,
deps: [HttpClient, LAZY_MAPS_API_CONFIG],
multi: true}
],
bootstrap: [ AppComponent ]
})
export class AppModule { }