Angular environment.ts with Github actions

Krishna Santosh Nidri
4 min readFeb 8, 2021

I have recently created an application using Angular and Firebase. The project uses Firebase for authentication and as backend. The application is hosted on Firebase. Github is used as remote repository for this project.

In my application, I used environment.ts to store Firebase project configuration. Since, this file contains secrets and keys it cannot be pushed to remote repository. So, this file is included in .gitignore.

environment.ts with Firebase configuration
environment files in .gitignore

When ever there is an update to the application, I used firebase deploy command to manually push the latest version to Firebase. I started exploring CI/CD pipeline for continuous development and automatic deployment to Firebase.

I came across a Github action by Firebase (Deploy to Firebase Hosting) and started exploring. What this does is copy the master branch to the hosting container, run the build script. This will run perfectly fine if all the necessary configuration is in place.

In my case, environment.ts and environment.prod.ts files won’t be in the github repository and the github action will fail because the reference to the file(usually in app.module.ts) is missing.

Importing and referring environment configuration in app.module.ts

So, I started looking for workarounds and learnt that secrets can be stored securely in github project repository secrets and can be referred while running github action. Github while executing the action will place these secrets in environment variables so that they can be referred during runtime in your workflow (process.env).

I came up with an idea to create a github secret with firebase object configuration, then create a environment.ts file dynamically and load this firebase object into that file. From there, github action will run and do what it needs to do.

  1. Create a github secret. FIREBASE_DETAILS in my case.
Github repository secrets section

2. Enter your firebase configuration into the secret. Remember that you can edit the details in the secret, you need to enter all details again if you want to update.

New Github secret creation

3. Create a js file in root director to include steps to create environment.ts file and load firebase configuration. I created a file called server.js. ‘${process.env.FIREBASE_DETAILS}’ has the firebase configuration object.

/* server.js in root directory */
const fs = require('fs');
const path = require('path');

const dir = "src/environments";
const file = "environment.ts";
const prodFile = "environment.prod.ts"; // For production deployment

const content = `${process.env.FIREBASE_DETAILS}`;

fs.access(dir, fs.constants.F_OK, (err) => {
if (err) {
// Directory doesn't exist
console.log("src doesn't exist, creating now", process.cwd());
// Create /src
try {
fs.mkdirSync(dir, { recursive: true });
}
catch (error) {
console.log(`Error while creating ${dir}. Error is ${error}`);
process.exit(1);
}
}
// Now write to file
try {
fs.writeFileSync(dir + "/" + file, content);
fs.writeFileSync(dir + "/" + prodFile, content);
console.log("Created successfully in", process.cwd());
if (fs.existsSync(dir + "/" + file)) {
console.log("File is created", path.resolve(dir + "/" + file));
const str = fs.readFileSync(dir + "/" + file).toString();
console.log(str);
}
} catch (error) {
console.error(error);
process.exit(1);
}
});

4. Now, update your github action configuration file (firebase-hosting-merge.yml if you let firebase create it) to add step that executes server.js (or whatever file you created). Make sure this step should get executed before build script runs. That way environment.ts file will be available for the reference later in the build steps.

Test your configuration. To debug, add log messages to server.js (or whatever file you created). Remember, the github secrets won’t be printed in log file. They are masked for security reasons.

Thank you and I will be glad if it helped in your project workflow.

--

--