vue.jswebpackvuejs3webpack-5webpack-cli

Vue 3 problem rendering child of the child components


I created a Vue 3.0.5 application using Webpack 5.21.2 and Webpack CLI 4.5.0. I build a global component my-component.js:

import SecondComponent from './second-component.vue';
app.component('global-component', {
  template: `
    <div>
      <h1>Hi!</h1>
      <second-component></second-component>
    </div>
  `,
 components: {
   SecondComponent
 }
})

The imported second-component.vue:

<template>
  <div>
    <div>{{someData}}</div>
    <third-component :name="helloWorld"></third-component>
  </div>
</template>

<script>
import ThirdComponent from './third-component.vue';
export default {
 name: 'second-component',
 components: {
   ThirdComponent 
 },
 data: function () {
   return {
     someData: 'Just some data!',
     helloWorld: 'Hello World!',
   }
  }
}
</script>

The third component third-component.vue:

<template>
  <div>
    <div>{{name}}</div>
  </div>
</template>

<script>
export default {
  name: 'third-component',
  props: {
    name: String,
  }
}
</script>

Here are the webpack configuration webpack.config.js:

const { VueLoaderPlugin } = require('vue-loader');

module.exports = {
  mode: 'production',
  entry: {
    global_component: './global-component.js',
  },
  output: {
    path: `${__dirname}`,
    filename: '[name]_bundled.js'
  },
  resolve: {
   extensions: ['*', '.js', '.vue']
  },
  module: {
    rules: [
      {
        test: /\.vue$/,
        use: 'vue-loader'
      },
      {
        test: /\.js$/,
        loader: 'babel-loader',
        exclude: /node_modules/
      },
      {
        test: /\.css$/,
        use: [
          'vue-style-loader',
          'css-loader'
        ]
      }
    ]
  },
  plugins: [
    new VueLoaderPlugin()
  ]
}

The bundle file i'm using in index.html like this:

<body>
  <script src="https://cdnjs.cloudflare.com/ajax/libs/vue/3.0.5/vue.global.js"></script>
  <script>const app = Vue.createApp({});</script>
  <script type="application/javascript" src="global_component_bundled.js"></script>
  <div id="app">
    <global-component></global-component>
  </div>
  <script>app.mount("#app");</script>
</body>

The problem I get is that the child of the child component is not rendering. In my case, this is the component third-component.vue that i'm importing into second-component.vue. However, when i use the component third-component.vue directly into my-component.js, it works. Can someone explain why and how can i solve that? Here i have an codesandbox.


Solution

  • I searched for a solution for a long time and in the end I got it. I used vue from CDN and in this case I should to say webpack to use the external Vue. Just make this configuration changes in webpack.config.js:

    const { VueLoaderPlugin } = require('vue-loader');
    
    module.exports = {
     ...
     externals: {
       // Here you tell webpack to take Vue from CDN
       vue: "Vue"
     },
     ...
    }
    

    With these changes webpack bundle the component and take Vue from CDN. I hope this answer will help other people. Here i made the changes already: codesandbox.