DEV Community

Cover image for Ability to change configuration after build. For containerized Angular and more
mixth for Zarewoft

Posted on • Edited on

3

Ability to change configuration after build. For containerized Angular and more

It is pretty normal to encounter an application that requires multiple environment configurations. But when it comes to web, we tend to build a whole new app once again when we change just the environment configurations. And the process takes minutes.

In the world of containerization, this strategy of building everything makes it difficult to achieve one image, deploy everywhere, which I am such a fan of. And when someone tries to do so, it always makes a BIG image with building tools and so on. Plus, a long starting time for the containers too.

So my goals here are:

  • We can build once and deploy everywhere.
  • We can have a small final product image.
  • We can have the ability to change those environment configuration just at the deployment time.

With a simple web concept, we can achieve that.

GLOBAL VARIABLES!!!!

Yep... you heard it right.

  1. I plan to put <script> in the <body>. Inside this <script>, I want to declare a global variable which is a simple object contains configuration of the environment. But, I am not going to put it in the index.html yet. Let's put a placeholder, say <!-- CONFIG -->, instead.
  2. In configuration file (such as what we have in typical Angular projects), I implement it to read global variable first, or else, assign a default configuration.
  3. Add a new sed command for docker image. Which basically do just replace the placeholder with a config from environment variables.

Just that. We are good to go! Here are gists just for an idea.

# Intermediate to build
FROM node:11.9.0-alpine as build-image
WORKDIR /home/node/app
COPY package.json package-lock.json ./
RUN npm ci
COPY . .
RUN npm run build:docker
# Using nginx as a final image
FROM nginx:1.15-alpine
WORKDIR /usr/share/nginx/html
COPY --from=build-image /home/node/app/dist/my-app .
COPY build/product/inject-env.sh /root
RUN chmod 700 /root/inject-env.sh
EXPOSE 80
ENV API_URL=http://foo.bar
CMD ["/root/inject-env.sh"]
view raw Dockerfile hosted with ❤ by GitHub
declare const CONFIG: { string: string };
let selectedEnvironment;
if (typeof CONFIG === 'undefined') {
selectedEnvironment = {
apiUrl: 'http://localhost:3000',
};
} else {
selectedEnvironment = CONFIG;
}
export const environment = selectedEnvironment;
<!doctype html>
<html lang="en">
<head>
<title>My Website</title>
</head>
<body>
<!-- CONFIG -->
<my-app></my-app>
</body>
</html>
view raw index.html hosted with ❤ by GitHub
#!/bin/sh
if [ -e /root/index.html ]
then
rm /usr/share/nginx/html/index.html
cp /root/index.html /usr/share/nginx/html/index.html
else
cp /usr/share/nginx/html/index.html /root/index.html
fi
sed -i 's_<!-- CONFIG -->_<script>const CONFIG = { "apiUrl": "'$API_URL'" };</script>_g' /usr/share/nginx/html/index.html
exec nginx -g "daemon off;"
view raw inject-env.sh hosted with ❤ by GitHub

Cons?

The config is plainly exposed.

This might let some users making weird things to your web. But I guess, it gonna have just a minimal impact since if they look hard enough, they might find it in any scenarios. Anyway, please proceed with caution.


That's it! Thanks for reading 😁
If you have any questions or some kind of improvement, please let me know in the comment below.

Sentry image

See why 4M developers consider Sentry, “not bad.”

Fixing code doesn’t have to be the worst part of your day. Learn how Sentry can help.

Learn more

Top comments (0)

The best way to debug slow web pages cover image

The best way to debug slow web pages

Tools like Page Speed Insights and Google Lighthouse are great for providing advice for front end performance issues. But what these tools can’t do, is evaluate performance across your entire stack of distributed services and applications.

Watch video

👋 Kindness is contagious

Please leave a ❤️ or a friendly comment on this post if you found it helpful!

Okay