DEV Community

Cover image for How to use dynamic environment variables in VueJS
Dani J. Pérez
Dani J. Pérez

Posted on • Edited on

How to use dynamic environment variables in VueJS

Leer en español

This is my first post to DEV.TO community and the first one in English so I'll try to do my best :D

Imagine that you need an app based in an API to fetch the data, and we have 3 different development stages:

  • Test
  • Dev
  • Prod

What we want is, depending on the stage we are, the app can call the right API and don't want to deploy our app every time we change between stages or change URLs.
What we will do is create a new file in our statics folder, this example structure is:

/static/config.json

The example file will have the URL used by default:

{
    "URL": "https://bydefault.something"
}

Now in our Vue app where we use the URL, declare in created() function a false API GET call to that file, in this example, we use axios:

created: function() {
    axios.get("static/config.json").then(response => {
      this.URL = response.data.URL;
    });
  }

Now our app will fetch that URL dynamically, and we can change it later without
the need to deploy it.

Well, now we have to create a file for every stage we need, in this case, we have 3 stages, so we need to create 3 files in the environments directory (plus the default created before), the example structure will be:

/environments/test/config.json
/environments/dev/config.json
/environments/pro/config.json

So, we have the 3 files for every stage (plus the default) and the app can call dynamically at the file to fetch the URL, now we have to make sure to copy the environment folder to the same destination when we deploy the app (npm run build). We can do this done in multiple automatic forms (CopyWebpackPlugin, npm run script...) or can we do it manually by copying the folder to the destination, in this example will use the CopyWebpackPlugin plugin, what let us copy files automatically by adding the following to our config file, in this case, /build/webpack.base.conf.js (change it based on your configuration):

output: {
    path: path.resolve(__dirname, '../dist')
  },
  plugins: [
    new CopyWebpackPlugin([
      {
        from: path.resolve(__dirname, '../static/js'),
        to: path.resolve(__dirname, '../dist/js')
      },
      {
        from: path.resolve(__dirname, '../static/config.json'),
        to: path.resolve(__dirname, '../dist/static')
      },
      {
        from: path.resolve(__dirname, '../config/environments/'),
        to: path.resolve(__dirname, '../dist')
      }
    ])]

Finally, our structure after deploy will be:

/dist/index.html
/dist/static/config.json
/dist/environments/test/config.json
/dist/environments/dev/config.json
/dist/environments/pro/config.json
/dist/static/js/...

Now every time we deploy our app, we have to make sure to replace /static/config.json with the right environment file, we can do this manually or if we have any CI (Continuous Integration) process such as Jenkins, we can configure it to automatically copy the right file based on deployment stage.

Thanks to the entire dev.to community!

Top comments (6)

Collapse
 
entioentio profile image
entio

Thanks for the article, I was struggling with this issue not too long ago. Interesting approach. Personally I used DotEnv plugin for webpack and I saved configuration per environment in .env file. But then it requires different builds (or building on the server and picking right .env file).

What you present here solves the problem, but adds one call before the app can launch.

Since you have to manually (or using some pipeline) replace the file - wouldn't it be easier to build app with parameter? Let's say npm run build --test or npm run build --dev and pass the arguments?

Collapse
 
djdany01 profile image
Dani J. Pérez

I'm glad it helped you!

And yes, i think you can develop a npm script to build with the file you want automatically, but i want to just build one time and then, with Jenkins, deploy the right file.
But yes, this can be done in a very different ways.

Collapse
 
sauloco profile image
Saulo Vargas

Hola, perdoname el SPAM, pero es por una buena causa, comencé una pequeña discusión en:
dev.to/sauloco/proposal-translate-...

Veo que tenemos objetivos alineados, si quisieras participar en la misma, te agradecería muchísimo!

Collapse
 
mikebernal profile image
Mike Bernal SP0701

should have a git repo link for us to check the codebase :)

Collapse
 
aasingla profile image
Aashish Singla

Does this hold well for Vue-cli-3 since their documentation mentions about .env.development, .env.production kind of files?

Collapse
 
djdany01 profile image
Dani J. Pérez • Edited

Yes, my environment files are for use with bussiness internal environments (dev, pre, pro).

These included with Vue-cli-3 are for vue internal modes:

  • development is used by vue-cli-service serve
  • production is used by vue-cli-service build and vue-cli-service test:e2e
  • test is used by vue-cli-service test:unit