15

I'm wondering if it is possible to let to a Vue App to read an external configuration file. I imagine something in which I deploy the application, ship the application with the config file; at this point it should be possibile to change the configuration in the external file without having to rebuilt the entire application. Is there someway I can achieve that result? Now I am using a separated Vuex store but i cannot change configuration without rebuilding the entire app.

I forgot to mention that the project is made with Vue CLI.

4 Answers 4

34

You can fetch config.json from public folder and then load your Vue app in the resolve callback

Place your configuration keys in /public/config.json file

{
  "KEY": "value"
}

Then in your /src/main.js file

fetch(process.env.BASE_URL + "config.json")
  .then((response) => response.json())
  .then((config) => {
       Vue.prototype.$config = config
       new Vue({
         router,
         store,
         render: (h) => h(App)
       }).$mount("#app")
  })

You will have your configuration loaded application-wide. You can then just use

mounted() {
  this.$config.KEY // "value"
}

in your Vue components

Update Nov 23, 2022 (Adding Vue 3 Version):

// VUE 3 Version
const app = createApp(App)

fetch(process.env.BASE_URL + "config.json")
  .then((response) => response.json())
  .then((config) => {
    // either use window.config
    window.config = config
    // or use [Vue Global Config][1]
    app.config.globalProperties.config = config
    // FINALLY, mount the app
    app.mount("#app")
  })
Sign up to request clarification or add additional context in comments.

12 Comments

Is it possibile to require the config file from webpack with require()? I tried with require(process.env.BASE_URL + 'config.json') but it's not working.
@MaurizioRicci it is not possible to use require as webpack will convert the dynamic links to inline json, which is not desired results. Key is to use fetch() here and fetch external json file
Make sure you request a new file with each request by appending a dynamic parameter to the url (eg: ?t=currentTimestamp). Otherwise browsers will cache the request. Or add the appropriate Cache-Control header
How can I access this file in a js file inside my src/ folder (e.g api.js that needs token key for requests)
@abbas Yes, definitely you just have to wrap the app.mount() in the then callback of fetch
|
4

Here's how I did it:

Create a config.js file in your public folder with the settings you want:

window.VUE_APP_API_KEY = 'blahblahblah';

Then in your public/index.html add the following lines to your head section:

  <script type="text/javascript">
    var cachebuster = Math.round(new Date().getTime() / 1000);
    document.write('<scr' + 'ipt type="text/javascript" src="<%= BASE_URL %>config.js?cb=' + cachebuster + '"></scr' + 'ipt>');
  </script>

Then in your VUE app, you just have to call window.VUE_APP_API_KEY. Simple, quick :)

3 Comments

Why do you split the script tag in 2 parts and then join them with a concatenation?
@bernie cause otherwise it cause errors. See this SO question for a full explanation and various methods to escape. stackoverflow.com/questions/236073/…
Wth vite I am getting "[vite] Internal server error: URI malformed".
3

Inspired by @Hammad, but for vue.js 3 using typescript and the component API, as well as the app.provide() mechanism.

Place your configuration keys in /public/config.json file

{
  "KEY": "value"
}

Then in your /src/main.ts file

fetch(import.meta.env.BASE_URL + 'config.json')
  .then((response) => response.json())
  .then((config) => {
    for (const key in config) {
      app.provide(key, config[key])
    }
    app.mount('#app')
  })

Finally, to read the configuration inside components:

<script setup lang="ts">
import { inject } from 'vue'

...

const config_value = inject('KEY')

2 Comments

This works for my current application
This works fine for me. AND - the solution "injected" me to sue provide/inject. Thx.
0

I have a route served by node which returns a dynamically created JS files and defines a global object where I store that config. Nothing that is Vue dependent.

In index.html:

 <script type="text/javascript" src="config.js"></script>

In node (server side):

  app.get('/config.js', (request, reply) => {
    reply.header('Content-Type', 'application/javascript');
    reply.send(`MyConfig = ${JSON.stringify(config)}`);
  });

In components (or anywhere else):

{
  data: () => ({
    someField: MyConfig.someField
  })
}

2 Comments

This solution needs an external server i.e. node.js. See my solution below which doesn't require any external server. Also, the suggested framework and code example doesn't correspond to any specific library
Yes it does. I was already using Node to serve the static files (and other things) so it fit in my case.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.