202

I've been reading the official docs and I'm unable to find anything on environment variables. Apparently there are some community projects that support environment variables but this might be overkill for me. So I was wondering if there's something simple out of the box that works natively when working on a project already created with Vue CLI.

For example, I can see that if I do the following the right environment prints out meaning this is already setup?

mounted() {
  console.log(process.env.ROOT_API)
}

I'm a kinda new to env variables and Node.

FYI using Vue CLI version 3.0 beta.

ux.engineer
  • 10,082
  • 13
  • 67
  • 112
Edgar Quintero
  • 4,223
  • 2
  • 34
  • 37

14 Answers14

298

Vue.js with Webpack

If you use vue cli with the Webpack template (default config), you can create and add your environment variables to a .env file.

The variables will automatically be accessible under process.env.variableName in your project. Loaded variables are also available to all vue-cli-service commands, plugins and dependencies.

You have a few options, this is from the Environment Variables and Modes documentation:

.env                # loaded in all cases
.env.local          # loaded in all cases, ignored by git
.env.[mode]         # only loaded in specified mode
.env.[mode].local   # only loaded in specified mode, ignored by git

Your .env file should look like this:

VUE_APP_MY_ENV_VARIABLE=value
VUE_APP_ANOTHER_VARIABLE=value

As noted in comment below: If you are using Vue cli 3, only variables that start with VUE_APP_ will be loaded.

Don't forget to restart serve if it is currently running.

Vue.js with Vite

Vite exposes env variables that start with VITE_ on the special import.meta.env object.

Your .env should look like this:

VITE_API_ENDPOINT=value
VITE_API_KEY=value

These variables can be accessed in Vue.js components or JavaScript files under import.meta.env.VITE_API_ENDPOINT and import.meta.env.VITE_API_KEY.

Tip: Remember to restart your development server whenever you change or add a variable in the .env file if it's running.

For more info, please see the Vite documentation for env variables.

RAH
  • 3,167
  • 1
  • 15
  • 10
  • 1
    Thanks will give it a try. Yes my project was created with the native Vue CLI, as per the docs. – Edgar Quintero Jun 13 '18 at 18:56
  • with `vue create my-app` – Edgar Quintero Jun 13 '18 at 19:01
  • 47
    Important to note: *Only variables that start with VUE_APP_ will be statically embedded into the client bundle with webpack.DefinePlugin.* – Edgar Quintero Jun 13 '18 at 21:27
  • can I still use `.env` file without using the vue-cli? – He Wang Sep 13 '18 at 07:38
  • 41
    **Only variables that start with `VUE_APP_` will be statically embedded** which means that if you want to have env-vars accessible on the client side code, then you must use `VUE_APP_` as prefix for keys in `.env` files – Yilmaz Guleryuz Dec 03 '18 at 18:20
  • Yap, just like I explained below a few months ago in https://stackoverflow.com/a/51745622/9661304. Upvotes are appreciated :D – Pedro Silva Dec 26 '18 at 18:21
  • 36
    Don't forget to restart **serve** if it is currently running. – ali6p Apr 11 '19 at 09:22
  • yes, the docs said .env.[mode] it means any [mode] like 'dev' or 'prod' should works, but, by default it uses env.development and env.production so when you npm run serve it will use env.development and not .env.dev – pabloRN Jan 10 '20 at 08:17
  • How is it acceptable that Vue enforces the need of prefixing with `VUE_APP_` for environment variables? I've just started implementing our environment variables and already come across an injected environment variable in prod that I can't change, so now I have to watch for both the local `VUE_APP_` prefixed and the production non-prefixed versions. – fredrivett Feb 03 '20 at 17:31
  • 5
    Important to note: We need to prefix all env variables with `VUE_APP_`, except for the `NODE_ENV` and `BASE_URL`. – palaѕн Jun 12 '20 at 17:04
  • Thank you for "only variables that start with VUE_APP_ will be loaded.". – Renan Coelho Feb 24 '21 at 19:57
  • VUE_APP_ -> this. wasted over 30 minutes of my time. ty. – zozo Jun 13 '21 at 06:35
  • 1
    As other answers helpfully point out, make sure you place your .env files at the root of the project, as a sibling of package.json (not in the src folder, for example). – Partik Aug 17 '21 at 19:31
  • What about another answer stating that the file name .env.production will be used with build ? Is that correct or will .env be used with build ? – chmike Sep 15 '21 at 07:29
  • I am using vite. There env variables must start with VITE_ and don't need to install dotenv. instead process use import.meta.env.VITE_env_variable. here is documentation https://vitejs.dev/guide/env-and-mode.html – Ozal Zarbaliyev Dec 03 '21 at 13:44
119

If you are using Vue cli 3, only variables that start with VUE_APP_ will be loaded.

In the root create a .env file with:

VUE_APP_ENV_VARIABLE=value

And, if it's running, you need to restart serve so that the new env vars can be loaded.

With this, you will be able to use process.env.VUE_APP_ENV_VARIABLE in your project (.js and .vue files).

Update

According to @ali6p, with Vue Cli 3, isn't necessary to install dotenv dependency.

Pedro Silva
  • 2,655
  • 1
  • 15
  • 24
99
  1. Create two files in root folder (near by package.json) .env and .env.production
  2. Add variables to theese files with prefix VUE_APP_ eg: VUE_APP_WHATEVERYOUWANT
  3. serve uses .env and build uses .env.production
  4. In your components (vue or js), use process.env.VUE_APP_WHATEVERYOUWANT to call value
  5. Don't forget to restart serve if it is currently running
  6. Clear browser cache

Be sure you are using vue-cli version 3 or above

For more information: https://cli.vuejs.org/guide/mode-and-env.html

ali6p
  • 1,683
  • 13
  • 17
  • 4
    This should be the only answer to this really nasty issue. Thank you! Pointing out where the root folder is and point 5 and 6 differentiate this from the rest of the answers. Also you need to install dotenv: npm install dotenv, I think. Well done. – HWJ Dec 31 '19 at 14:03
  • 1
    Always forgetting to restart the server! – christostsang Oct 07 '20 at 10:40
  • when you say 'restart serve', are you referring to web server? – Nguai al Jan 23 '21 at 21:22
  • 1
    @Nguaial I mean, re-run the serve script `npm run serve`... or different cmd that depends on your setup. – ali6p Jan 25 '21 at 00:58
  • This is the best answer here, to be honest. I didn't even need an `.env.development` like other recommended here, just use `.env` as my dev configuration file. – Narxx Feb 07 '21 at 16:56
  • Must the .env file be created in the src directory or the root directory ? – chmike Sep 15 '21 at 07:25
  • @chmike the root directory – ali6p Sep 16 '21 at 09:20
  • Thanks. Worked also for vue 4. Im having e.g. also .env.test for build my vue app for our test machine. Need to build it with `npm run build -- --mode test`, then it takes the correct file (I think .env + .env.test in combination). Furthermore: If you would like to use env-vars in your template, of course you need to put them into a data attribute like `data(){ return { ENV: process.env } }` and use them in template, e.g. `This is my env: {{ ENV.VUE_APP_WHATEVERYOUWANT }}`. Or is there any other smooth way? – phil Feb 01 '22 at 07:33
44

In the root of your project create your environment files:

  • .env
  • .env.someEnvironment1
  • .env.SomeEnvironment2

To then load those configs, you would specify the environment via mode i.e.

npm run serve --mode development //default mode
npm run serve --mode someEnvironment1

In your env files you simply declare the config as key-value pairs, but if you're using vue 3, you must prefix with VUE_APP_:

In your .env:

VUE_APP_TITLE=This will get overwritten if more specific available

.env.someEnvironment1:

VUE_APP_TITLE=My App (someEnvironment1)

You can then use this in any of your components via:

myComponent.vue:

<template>
  <div> 
    {{title}}
  </div>
</template>

<script>
export default {
  name: "MyComponent",
  data() {
    return {
      title: process.env.VUE_APP_TITLE
    };
  }
};
</script>

Now if you ran the app without a mode it will show the 'This will get...' but if you specify a someEnvironment1 as your mode then you will get the title from there.

You can create configs that are 'hidden' from git by appending .local to your file: .env.someEnvironment1.local - very useful for when you have secrets.

Read the docs for more info.

benscabbia
  • 17,592
  • 13
  • 51
  • 62
  • this is the only answer that worked for me . us the full variable name ...` title: process.env.VUE_APP_API_URL ` – Nassim Aug 10 '20 at 20:28
  • Same, this was the only way I could get it work. Once I added the file, ran npm run serve in the root of my projects directory I was able to reference the env variables. – R007 Apr 21 '21 at 02:20
  • This is great, one thing to keep in mind is that the "build" mode is different from the webpack `NODE_ENV` mode, so you can use this to setup modes like `staging` or even different "versions" or "deployments" of your application https://medium.com/rangle-io/custom-build-modes-with-vue-cli-3-16ab208b4bc3 – sMyles Jan 25 '22 at 16:36
12

A problem I was running into was that I was using the webpack-simple install for VueJS which didn't seem to include an Environment variable config folder. So I wasn't able to edit the env.test,development, and production.js config files. Creating them didn't help either.

Other answers weren't detailed enough for me, so I just "fiddled" with webpack.config.js. And the following worked just fine.

So to get Environment Variables to work, the webpack.config.js should have the following at the bottom:

if (process.env.NODE_ENV === 'production') {
  module.exports.devtool = '#source-map'
  // http://vue-loader.vuejs.org/en/workflow/production.html
  module.exports.plugins = (module.exports.plugins || []).concat([
    new webpack.DefinePlugin({
      'process.env': {
        NODE_ENV: '"production"'
      }
    }),
    new webpack.optimize.UglifyJsPlugin({
      sourceMap: true,
      compress: {
        warnings: false
      }
    }),
    new webpack.LoaderOptionsPlugin({
      minimize: true
    })
  ])
}

Based on the above, in production, you would be able to get the NODE_ENV variable

mounted() {
  console.log(process.env.NODE_ENV)
}

Now there may be better ways to do this, but if you want to use Environment Variables in Development you would do something like the following:

if (process.env.NODE_ENV === 'development') {

  module.exports.plugins = (module.exports.plugins || []).concat([
    new webpack.DefinePlugin({
      'process.env': {
        NODE_ENV: '"development"'
      }
    })
  ]);

} 

Now if you want to add other variables with would be as simple as:

if (process.env.NODE_ENV === 'development') {

  module.exports.plugins = (module.exports.plugins || []).concat([
    new webpack.DefinePlugin({
      'process.env': {
        NODE_ENV: '"development"',
        ENDPOINT: '"http://localhost:3000"',
        FOO: "'BAR'"
      }
    })
  ]);
}

I should also note that you seem to need the "''" double quotes for some reason.

So, in Development, I can now access these Environment Variables:

mounted() {
  console.log(process.env.ENDPOINT)
  console.log(process.env.FOO)
}

Here is the whole webpack.config.js just for some context:

var path = require('path')
var webpack = require('webpack')

module.exports = {
  entry: './src/main.js',
  output: {
    path: path.resolve(__dirname, './dist'),
    publicPath: '/dist/',
    filename: 'build.js'
  },
  module: {
    rules: [
      {
        test: /\.css$/,
        use: [
          'vue-style-loader',
          'css-loader'
        ],
      },      {
        test: /\.vue$/,
        loader: 'vue-loader',
        options: {
          loaders: {
          }
          // other vue-loader options go here
        }
      },
      {
        test: /\.js$/,
        loader: 'babel-loader',
        exclude: /node_modules/
      },
      {
        test: /\.(png|jpg|gif|svg)$/,
        loader: 'file-loader',
        options: {
          name: '[name].[ext]?[hash]'
        }
      }
    ]
  },
  resolve: {
    alias: {
      'vue$': 'vue/dist/vue.esm.js'
    },
    extensions: ['*', '.js', '.vue', '.json']
  },
  devServer: {
    historyApiFallback: true,
    noInfo: true,
    overlay: true
  },
  performance: {
    hints: false
  },
  devtool: '#eval-source-map'
}

if (process.env.NODE_ENV === 'production') {
  module.exports.devtool = '#source-map'
  // http://vue-loader.vuejs.org/en/workflow/production.html
  module.exports.plugins = (module.exports.plugins || []).concat([
    new webpack.DefinePlugin({
      'process.env': {
        NODE_ENV: '"production"'
      }
    }),
    new webpack.optimize.UglifyJsPlugin({
      sourceMap: true,
      compress: {
        warnings: false
      }
    }),
    new webpack.LoaderOptionsPlugin({
      minimize: true
    })
  ])
}

if (process.env.NODE_ENV === 'development') {

  module.exports.plugins = (module.exports.plugins || []).concat([
    new webpack.DefinePlugin({
      'process.env': {
        NODE_ENV: '"development"',
        ENDPOINT: '"http://localhost:3000"',
        FOO: "'BAR'"
      }
    })
  ]);

}
Aaron McKeehan
  • 410
  • 4
  • 6
  • I'm moving toward's Vue CLI 3 for future projects, but ran into the same problem on an App I built with the `webpack-simple` install. I expanded on your logic a little bit here and just created an "else" condition in which I just pass the `process.env.NODE_ENV` value into the DefinePlugin args. – slowFooMovement Dec 06 '18 at 23:07
  • Aaron McKeehan, I did the same addition to my webpack.config as you advised. But, how can I use that variable I wrote for development in my vue component for request beginning? – Nodira Feb 13 '19 at 12:21
  • @Aaron McKeehan For example, I added, `if (process.env.NODE_ENV === 'development') { module.exports.plugins = (module.exports.plugins || []).concat([ new webpack.DefinePlugin({ 'process.env': { NODE_ENV: '"development"', DEBUG_MODE: true, ROOT_API: '"http://localhost:8080/"' } }) ]); }` and in Setting.vue I want to add this ROOT_API variable in my post request: axios .post(`ENVIRONMENT_VARIABLE_HERE??/api/users/me/change-password`){...}. Please give me advice, I'm not pro in how webpack works – Nodira Feb 13 '19 at 12:22
  • The key for me was prefixing with `VUE_APP_` in both `.env` AND in the `file.vue` – fred Jun 03 '20 at 22:15
  • "Note that because the plugin does a direct text replacement, the value given to it must include actual quotes inside of the string itself. Typically, this is done either with alternate quotes, such as '"production"', or by using JSON.stringify('production')." https://webpack.js.org/plugins/define-plugin/#usage – Steven Almeroth Apr 30 '21 at 03:59
4

This is how I edited my vue.config.js so that I could expose NODE_ENV to the frontend (I'm using Vue-CLI):

vue.config.js

const webpack = require('webpack');

// options: https://github.com/vuejs/vue-cli/blob/dev/docs/config.md
module.exports = {
    // default baseUrl of '/' won't resolve properly when app js is being served from non-root location
    baseUrl: './',
    outputDir: 'dist',
    configureWebpack: {
        plugins: [
            new webpack.DefinePlugin({
                // allow access to process.env from within the vue app
                'process.env': {
                    NODE_ENV: JSON.stringify(process.env.NODE_ENV)
                }
            })
        ]
    }
};
Yashwardhan Pauranik
  • 5,370
  • 5
  • 42
  • 65
drussell
  • 509
  • 4
  • 5
  • 1
    This is what I was looking for a very long time. It is simple and understandable to throw values into variables from the command line at startup and later can be used in the application. Without additional libraries and difficulties. Thank you very much! Add for the same as me: 1. `CUSTOM_VAR: JSON.stringify (process.env.CUSTOM_VAR) || "default value"` 2. Setting the variable value at run: `set CUSTOM_VAR=value && npm run serve` 3. Use the variable in the application: `console.log (process.env.CUSTOM_VAR)` – Alex Shink Jan 19 '20 at 11:47
3

In vue-cli version 3:

There are the three options for .env files: Either you can use .env or:

  • .env.test
  • .env.development
  • .env.production

You can use custom .env variables by using the prefix regex as /^/ instead of /^VUE_APP_/ in /node_modules/@vue/cli-service/lib/util/resolveClientEnv.js:prefixRE

This is certainly not recommended for the sake of developing an open source app in different modes like test, development, and production of .env files. Because every time you npm install .. , it will be overridden.

frlzjosh
  • 410
  • 5
  • 17
cagcak
  • 3,894
  • 2
  • 21
  • 22
2

In addition to the previous answers, if you're looking to access VUE_APP_* env variables in your sass (either the sass section of a vue component or a scss file), then you can add the following to your vue.config.js (which you may need to create if you don't have one):

let sav = "";
for (let e in process.env) {
    if (/VUE_APP_/i.test(e)) {
        sav += `$${e}: "${process.env[e]}";`;
    }
}

module.exports = {
    css: {
        loaderOptions: {
            sass: {
                data: sav,
            },
        },
    },
}

The string sav seems to be prepended to every sass file that before processing, which is fine for variables. You could also import mixins at this stage to make them available for the sass section of each vue component.

You can then use these variables in your sass section of a vue file:

<style lang="scss">
.MyDiv {
    margin: 1em 0 0 0;
    background-image: url($VUE_APP_CDN+"/MyImg.png");
}
</style>

or in a .scss file:

.MyDiv {
    margin: 1em 0 0 0;
    background-image: url($VUE_APP_CDN+"/MyImg.png");
}

from https://www.matt-helps.com/post/expose-env-variables-vue-cli-sass/

Matt Parkins
  • 24,208
  • 8
  • 50
  • 59
  • This works fine for scss files inside vue components. But I'm using Vuetify and it's variables.scss file (https://vuetifyjs.com/en/customization/sass-variables/) and there is just not working. I get SassError: Undefined variable. And ideas? – dari0h Aug 03 '20 at 11:25
  • Note on this all depends on your version of loader you're using. For example in v8 you need to use `prependData` instead of `data` – sMyles Jan 25 '22 at 20:37
  • Also if you're having issues make sure if you're using `scss` that you use `scss` instead of `sass` (or just add them both) @dari0h – sMyles Jan 25 '22 at 20:38
1

Important (in Vue 4 and likely Vue 3+ as well!): I set VUE_APP_VAR but could NOT see it by console logging process and opening the env object. I could see it by logging or referencing process.env.VUE_APP_VAR. I'm not sure why this is but be aware that you have to access the variable directly!

willjfield
  • 33
  • 6
  • 2
    had the same issue -> in my case it was due to the fact, that i placed the .env file in the /src folder and not in the project root folder! – Christian Casutt Mar 31 '21 at 15:29
1

if you're using Laravel with Vue and Webpack, you could try putting a prefix of MIX_ onto your .env variables

i.e.:

MIX_SPACESHIP="U.S.S. Enterprise"

then pull that into a vue component via:

process.env.MIX_SPACESHIP
catomatic
  • 661
  • 8
  • 10
0

For those using Vue CLI 3 and the webpack-simple install, Aaron's answer did work for me however I wasn't keen on adding my environment variables to my webpack.config.js as I wanted to commit it to GitHub. Instead I installed the dotenv-webpack plugin and this appears to load environment variables fine from a .env file at the root of the project without the need to prepend VUE_APP_ to the environment variables.

0

Running multiple builds with different .env files

In my app I wanted to have multiple production builds, one for a web app, and another for a browser extension.

In my experience, changing build modes can have side effects as other parts of the build process can rely on being in production for example, so here's another way to provide a custom env file (based on @GrayedFox's answer):

package.json

{
  "scripts": {
    "build": "vue-cli-service build",
    "build:custom": "VUE_CLI_SERVICE_CONFIG_PATH=$PWD/vue.config.custom.js vue-cli-service build",
  }
}

vue.config.custom.js

// install `dotenv` with `yarn add -D dotenv`
const webpack = require("webpack");
require("dotenv").config({ override: true, path: "./.env.custom" });

module.exports = {
  plugins: [new webpack.EnvironmentPlugin({ ...process.env })],
};

Note 1: VUE_CLI_SERVICE_CONFIG_PATH swaps out the config from the default of vue.config.js, so any settings set in there will not apply for the custom build.

Note 2: this will load .env.production before .env.custom, so if you don't want any of the environment variables set in .env.production in your custom build, you'll want to set those to a blank string in .env.custom.

Note 3: If you don't set override: true then environment variables in .env.production will take precedence over .env.custom.

Note 4: If you are looking to have multiple different builds using vue-cli, the --skip-plugins option is very useful.

dKen
  • 3,078
  • 1
  • 28
  • 37
fredrivett
  • 5,419
  • 3
  • 35
  • 48
0

I am having same problem in vuecli@5. Trying to solve by reading official doc but can't get proper solution. After long time i got solution and it works fine.

  1. Create .env file on root dir. touch .env
  2. Set value on it i.e APP_NAME=name
  3. vue.config.js file past it process.env.VUE_APP_VERSION = require('./package.json').version
  4. Log to any method console.log(process.env.APP_NAME);
Md Al-Mahmud
  • 81
  • 1
  • 4
-1

**just install this **

npm install -g @vue/cli 

at your project it is worked with me

Doaa
  • 1
  • 2