Consider the following situation (Angular v7):
- Retrieve configuration settings (API server URL and Auth server URL) from an external source (JSON), prior to loading the AppModule
- Provide configuration to the AppModule (OAuth2 module)
- Compile the application with AOT
The crucial step is number 2, and it appears as follows:
@NgModule({
imports: [
...
OAuthModule.forRoot({
resourceServer: {
allowedUrls: [API_SERVER_URL], // <== we need to set the value that we retrieved from the external source (JSON) here
sendAccessToken: true
}
}),
...
],
declarations: [AppComponent],
bootstrap: [AppComponent]
})
export class AppModule { }
What I have attempted so far:
- An approach using APP_INITIALIZER. This method fails because the
OAuthModule.forRoot()
is triggered before theAPP_INITIALIZER
can fetch the external configuration JSON. - Loading the configuration via an async function in the
main.ts
into the Angular environment variables, then bootstrapping the AppModule. However, this also does not work due to the
statement inimport { AppModule } from './app/app.module';
main.ts
, which causes the AppModule to load and triggerOAuthModule.forRoot()
before the external configuration is fetched (this comment confirms this behavior). - Dynamically loading the AppModule in
main.ts
, without theimport
statement on top. Here is the StackBlitz example provided in that comment. It does work, but 1) it disrupts lazy loading
and 2) it is incompatible with AOT compiling. Nonetheless, it comes very close to meeting my requirements.WARNING in Lazy routes discovery is not enabled.
I am interested in knowing if there is another approach to ensure external configuration is loaded prior to the AppModule being loaded.
StackBlitz for option 3 (Dynamically load the AppModule): https://stackblitz.com/edit/angular-n8hdty