1

I use msal to do authentication. In my AppModule.ts (from the example)

    @NgModule({
  declarations: [
    AppComponent,
    HomeComponent,
    ProfileComponent
  ],
  imports: [
    BrowserModule,
    AppRoutingModule,
    MsalModule.forRoot( new PublicClientApplication({
      auth: {
        clientId: 'Enter_the_Application_Id_here', // This is your client ID
        authority: 'Enter_the_Cloud_Instance_Id_Here'/'Enter_the_Tenant_Info_Here', // This is your tenant ID
        redirectUri: 'Enter_the_Redirect_Uri_Here'// This is your redirect URI
      },
      cache: {
        cacheLocation: 'localStorage',
        storeAuthStateInCookie: isIE, // Set to true for Internet Explorer 11
      }
    }), null, null)
  ],
  providers: [],
  bootstrap: [AppComponent]
})
export class AppModule { }

For the clientId, I don't want to hard code here. It is in the a config file. The question is that I have different environment such as dev/qa and prod etc. The clientId is different in each endpoint.

How to pass the value rather than hardcode to AppModule?

Hello
  • 796
  • 8
  • 30

1 Answers1

1

You could create environment.[stage].ts files for every stage under './src/environments/'.

// environment.ts
export const environment = {
  production: false,
  clientId: 'Enter_the_Application_Id_here',
  authority: 'Enter_the_Cloud_Instance_Id_Here',
  redirectUri: 'Enter_the_Redirect_Uri_Here'
}

// environment.qa.ts
export const environment = {
  production: true,
  clientId: 'Enter_the_Application_Id_here',
  authority: 'Enter_the_Cloud_Instance_Id_Here',
  redirectUri: 'Enter_the_Redirect_Uri_Here'
}

When finished you should have N files for each stage. For example:

  1. environment.ts
  2. environment.qa.ts
  3. environment.prod.ts

With some additional configuration of each [stage] inside angular.json you can easily do this:

import { environment } from './../environments/environment';

//inside app.module
   MsalModule.forRoot( new PublicClientApplication({
      auth: {
        clientId: environment.clientId,
        authority: environment.authority,
        redirectUri: environment.redirectUri
      },

The addtional configuration inside angular.json adds a "fileReplacements" to replace environment.ts with envirnment.[stage].ts:

"configurations": {
  "qa": {
    "fileReplacements": [
      {
        "replace": "src/environments/environment.ts",
        "with": "src/environments/environment.qa.ts"
      }
    ],

Now you can run stage specific builds:

ng build --configuration=qa

The official angular documentation has a page about this topic: https://angular.io/guide/build

Martin Godzina
  • 1,470
  • 11
  • 17
  • That is a good advice. I have `useFactory()` in providers. Just wonder can I use it or using `useValue` to retrieve the value? – Hello Jul 27 '21 at 23:45
  • Sure. As long you use the stage specific build. – Martin Godzina Jul 27 '21 at 23:53
  • The only concern is that this method load data before bootstrap or after bootstrap. I want before bootstrap. See https://stackoverflow.com/questions/42534930/angular-2-external-configuration-befor-bootstrap-passing-the-value-to-appmodu. – Hello Jul 28 '21 at 00:50
  • this solution works for both pre- and afer-bootstrap because you simply substitute the json and the import always got the recent values you need – Martin Godzina Jul 28 '21 at 01:56
  • just import environment like mentioned in my anwser and use it where ether you whant to use it. Due to ng build --configuration=N you get the right data – Martin Godzina Jul 28 '21 at 01:57
  • I have a similar [question](https://stackoverflow.com/questions/68561263/i-already-got-environment-by-usefactory-then-how-to-pass-value-per-environment). If you could help, that would be greatly appreciated. – Hello Jul 28 '21 at 20:04