Building Ionic Apps for Different Environments

May 4th 2018 Ionic Framework

In one of my previous posts, I've written about changing the config.xml file when building an app for different environments. However, sometimes that's not enough. You might want to make other changes in the application which are only possible in code, e.g. have a different tracking ID for Google Analytics or allow sharing the console log only from non-production builds.

To my knowledge, there is no built-in functionality in Ionic to allow that, nor is there a component or a plugin available for this purpose. Following the KISS design principle, I decided to implement the simplest possible solution I could think of which would get the job done. I created a dedicated configuration object and put it into a separate config.ts file:

export let CONFIG = {
    GA_TRACKING_ID = 'UA-00000000-0',
    LOG_SHARING_ENABLED = true
    // ...
}

In it, I set all the values which would vary between different environments. Wherever I needed to use one of these values, I imported the object and read the value from it:

import { CONFIG } from '../config/config';

// ...

private initializeGoogleAnalytics() {
    this.ga.startTrackerWithId(CONFIG.GA_TRACKING_ID).then(() => {
        // ...
    });
}

Now, I could create a copy of my config.ts file for each target environment. E.g. config.prod.ts would contain the values for the production build:

export let CONFIG = {
    GA_TRACKING_ID = 'UA-99999999-9',
    LOG_SHARING_ENABLED = false
    // ...
}

With this setup, the default build from source control will use the values from config.ts targeting the development environment. To build the application for a different environment, the corresponding configuration file needs to be copied over config.ts, e.g. config.prod.ts for the production environment. To make this step as simple as possible, a Bash script can be used:

#!/bin/bash

if [ "$1" != "stage" ] && [ "$1" != "prod" ] ; then
  echo "You must specify target environment, one of: stage, prod."
  exit 1
fi

cat ./src/config/config.$1.ts > ./src/config/config.ts

The target environment is passed as a parameter, e.g.:

./change-env.sh prod

This will work with Linux and macOS, but will require the Windows Subsystem for Linux to be installed on Windows. If you want to avoid that, an equivalent script can be written in PowerShell:

If ($args[0] -ne "stage" -And $args[0] -ne "prod") {
  Write-Output "You must specify target environment, one of: stage, prod."
  exit
}

Copy-Item ".\src\config\config.$($args[0]).ts" -Destination ".\src\config\config.ts"

The target environment is again passed in as a parameter:

.\change-env.ps1 prod

The script is primarily meant for the build server, but it can also be used by developers when they want to manually build the application for a different environment. They just need to take care that they don't accidentally commit the modified config.ts file with the wrong values.

Copyright
Creative Commons License