Pass environment variables to an Angular2 app?

I need to pass the backend url to my Angular2 app, since production and dev servers are hosted on different locations.

I know I could store such things in an external config.json and load upon startup. This, however, seems like unnecessary extra call to server before the app can get started.

Alternatively, what I do now is I do create a single global variable, which I inject in gulp depending on build. My app isn’t a lib that needs to be reusable I don’t believe I should hit unexpected global name clashes. But it’s not a good practice.

I wonder if there’s a third, better solution?

6
Leave a Reply

avatar
6 Comment threads
0 Thread replies
0 Followers
 
Most reacted comment
Hottest comment thread
1 Comment authors
Jason Recent comment authors
  Subscribe  
newest oldest most voted
Notify of
Jason
Guest

I think this might be useful to you.
Passing asp.net server parameters to Angular 2 app

This way you can inject any value from html page (which can get value from the server, like current environment variable)

Jason
Guest

I have implemented this using the following approach:

  1. Created ts files for each environment.
  2. Modified package.json and added a new entry for every environment in scripts section.

for eg:-

“start:local”: “copy “config/config.local.ts” “constants/global.constants.ts” && npm run start”

  1. Import global.constants into your app.
  2. You can start your HTTP server using : npm run start:local
Jason
Guest

In different environments, the value of location.host will be different.

Use this as the key and load the values from the corresponding json having all the URLs.

The relevant code may look like this:

let env = location.host;
if (env === 'prod.example.com') {
  config = 'ProdConfig.json';
} else if (env === 'test.example.com') {
  config = 'TestConfig.json';
} else if (env === 'localhost') {
  config = 'DevConfig.json';
}

Jason
Guest

I would see two ways to do that: Leverage a JSON configuration in a file. This file would be loaded before boostrapping the application: var app = platform(BROWSER_PROVIDERS) .application([BROWSER_APP_PROVIDERS, appProviders]); var http = app.injector.get(Http); http.get('config.json').subscribe((config) => { return app.bootstrap(AppComponent, [ provide('config', { useValue: config }) ]); }).toPromise(); Here is a corresponding plunkr describing the global approach: https://plnkr.co/edit/ooMNzEw2ptWrumwAX5zP?p=preview. Leverage a configuration module: export const CONFIG = { (...) }; that will be imported and included in providers when bootstrapping the application: import {CONFIG} from './config'; bootstrap(AppComponent, [ provide('config', { useValue: CONFIG }) ]); With the two approaches, configuration can be defined… Read more »

Jason
Guest

Just put variables inside the environment object.

export const environment = {
  production: false,
  url: 'http://localhost:3000/api'
};

After that, you could import and use it. Angular Cli will swap files automatically.

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

P.S. Variables are available in environment object.

this.url = environment.url

Jason
Guest

I have been struggling with the above for a while too. And even though Thierry’s answer is very good, but I somehow find it too complicated for simply having env vars, so I thought I present my thoughts too. 1) I first created an interface describing my env vars app.settings.ts: export interface IEnvVars { ENV: string; API_URL: string; } export class AppSettings { public static env_vars: IEnvVars; } 2) I added the JavaScript fetch API type definitions to my .d.ts file. (Not absolutely needed if you don’t mind having fetch as unresolved, but I did mind it, so added the… Read more »