Reputation: 2535
I have a page in nuxt that is divided in two parts. The first part is a normal template structure filled with dynamic content based on the url param. The second part is a component that should be loaded based on this data. I am trying to accomplish it like this:
<template>
<div>
<h1>{{myData.header}}</h1>
<p>{{myData.text}}</p>
<my-component></my-component>
</div>
</template>
<script>
export default {
components: {
'my-component': () => import('@/components' + this.myData.component)
},
async asyncData(context) {
return {
myData: context.params.myData
}
}
}
</script>
But this is not working. Is there a way to accomplish this?
I am familiar with the possibility to use <my-component :is="myData.component"></my-component>
. However, this requires me to import every component explicitly and I would like to avoid this.
Upvotes: 13
Views: 11725
Reputation: 590
I've found an easy way of doing it if you need to import an existing component. I did it because I'm using Nuxt and I need to load the component only on client side:
<template>
<my-component></my-component>
</template>
<script>
data() {
return {...}
},
mounted() {
if (process.browser) {
const component = require("~/assets/libs/component");
Vue.use("my-component", component); // or just Vue.use(component);
}
}
</script>
This method avoid the import errors related to Window instance.
Upvotes: 0
Reputation: 149
Based on Imre_G's answer, it can be simplified like this:
<template>
<div>
<h1>Hi</h1>
<p>Hello World!</p>
<Component :is="component"></Component>
</div>
</template>
<script>
export default {
computed: {
component() {
return () =>
import(`../../__relative_path__/${this.$route.params.yourParam}`)
}
}
}
</script>
Upvotes: 2
Reputation: 2535
I found a solution to this yesterday. It needs to be done like this.
<template>
<div>
<h1>{{myData.header}}</h1>
<p>{{myData.text}}</p>
<component :is="componentInstance"></component>
</div>
</template>
<script>
export default {
computed: {
componentInstance () {
const name = this.myData.component
return () => import(`./components/${name}`)
}
},
async asyncData(context) {
return {
myData: context.params.myData
}
}
}
</script>
More info in this article: https://itnext.io/vue-a-pattern-for-idiomatic-performant-component-registration-you-might-not-know-about-9f3c091846f5.
Upvotes: 19