vue-class-component and vue plugin issue

Created on 6 Dec 2018  路  12Comments  路  Source: vuejs/vue-class-component

Hello there,

I am facing a problem and for now I have not been able to find a workaround.
I am in the process of building a Vue application with typescript, this application use a plugin that I write as well.
This plugin is in fact a library of reusable components.

Let's say i use Vuetify in my application :

main.ts

import Vuetify from 'vuetify'
import MyOwnPlugin from 'my-own-plugin'
...
Vue.use(Vuetify);
Vue.use(MyOwnPlugin);
Vue.
 const vm = new Vue({
  router,
  store,
  render: h => h(App),
});

vm.$vuetify // => vuetify instance

And i would like to access it in my plugin

my-own-plugin/component/RandomComponent.Vue (this plugin has it's own repo)

<script>
import Vue from 'vue'
import Component from 'vue-class-component'

@Component
export default class RandomComponent extends Vue {

  // lifecycle hook
  created () {
    **this.$vuetify // => undefined**
  }
}
</script>

this.$vuetify is undefined , and as i understand. It is because when i declare my component I extend another Vue constructor. (by the way , when working on my plugin, i use npm link, which cause Vue to exist in two different node_modules)

The thing is : If i'm not using vue-class-component, this is working seemlessly

my-own-plugin/component/RandomComponent.Vue (without class-component)

<script>

export default  {

  // lifecycle hook
  created () {
    **this.$vuetify // => vuetify instance**
  }
}
</script>

Do you have an idea of what i can do to achieve this using vue-class-component ?

P.S. : I know it should work when installing the plugin package from npm , but it would make me add some conditions for the development phase in my plugin code for it to work when linking that i would like to avoid.

All 12 comments

Please provide a minimal / self-contained reproduction to confirm the problem.

How am i supposed to provide a self-contained reproduction with my plugin in it's own npm repo ?

You can create an example github repo which reproduce it. Also you don鈥檛 have to use npm library if you can reproduce it by local plugin.

you are right, but i stil have to create two repo, in order to be able to reproduce the issue,
As i have said, the problem occurs when you link the plugin with npm

https://github.com/Meg4mi/reproIssue

Here is a github repo to help reproduce the issue i encounter

Because you are referring different Vue constructor between app and plugin directory. They use the one under their own node_modules. You need to configure your vue.config.js to make them refer the exact same one or always use built source not including external libs for plugin by using vue-cli lib mode.

const path = require('path')

module.exports = {
  configureWebpack: config => {
    config.resolve.modules = [path.resolve(__dirname, 'node_modules')]
  }
}

Hello, thanks for the answer.
I know this is happening because i'm referring different Vue constructor, as i supposed it in my first post.
The thing is , the repo i've provided is an exemple, in the real use case, "plugin" is not in the same repo and we are already using "lib mode", same story.
I have updated the reproduction repo using lib target mode.

As I have said earlier, if I run the project like I were using it for production , I have no problem, but when I'm working on my plugin using "npm link" (even with lib mode), issue appears and i would like to find a solution that is not to test the environnement i am into.

I am not sure to be very clear ?

when I'm working on my plugin using "npm link" (even with lib mode), issue appears

That is the same case. If you refer your plugin by npm link it'll use node_modules under your linked library directory.

I found a workaround using webpack resolve alias.

I put that it here if that can help someone:

vue.config.js

const path = require('path');
module.exports = {
  configureWebpack: config => {
    if (process.env.NODE_ENV !== 'production') {
      // mutate config for production...
      config.resolve = {
        alias: {
          vue: path.resolve(__dirname, './node_modules/vue')
        }
      };
    }
  }
};

I still recommend you to set resolve.modules option rather than setting alias in this case because other dependencies also can be duplicated. For example, vue-class-component and vue-property-decorators under plugin directory would be used in your reproduction.

You are right, thanks.
I have updated the repo.

const path = require('path');
module.exports = {
  configureWebpack: config => {
    if (process.env.NODE_ENV !== 'production') {
      // mutate config for production...
      config.resolve = {
        modules: [path.resolve(__dirname, './node_modules')]
      };
    }
  }
};

I would suggest prepending the module resolve path to keep the rest as it is (e.g. the @ resolving part in vue cli). So your config could look like:
const path = require('path'); module.exports = { chainWebpack: (config) => { if (process.env.NODE_ENV !== 'production') { config.resolve.modules.prepend(path.resolve(__dirname, './node_modules')); } }, };
This works in my tests for your repository.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

micobarac picture micobarac  路  6Comments

kabaluyot picture kabaluyot  路  3Comments

dmitrykurmanov picture dmitrykurmanov  路  4Comments

asolopovas picture asolopovas  路  4Comments

hesi726 picture hesi726  路  5Comments