Module to scan and auto import components for Nuxt.js 2.13+
- Scan and auto import components
- Multiple paths with customizable prefixes and lookup/ignore patterns
- Dynamic import (aka Lazy loading) Support
- Hot reloading Support
- Transpiling Support (useful for component library authors)
- Fully tested!
Set the components option in nuxt.config:
export default {
components: true
}Note: If using nuxt 2.10...2.13, you have to also manually install and add @nuxt/components to buildModules inside nuxt.config.
Create your components:
components/
ComponentFoo.vue
ComponentBar.vueUse them whenever you want, they will be auto imported in .vue files :
<template>
<ComponentFoo />
<component-bar />
</template>No need anymore to manually import them in the script section!
See live demo.
To make a component imported dynamically (lazy loaded), all you need is adding a Lazy prefix in your templates.
If you think this prefix should be customizable, feel free to create a feature request issue!
You are now being able to easily import a component on-demand :
<template>
<LazyComponentFoo v-if="foo" />
<button @click="loadFoo">
Load Foo
</button>
</template>
<script>
export default {
data () {
return {
foo: null
}
},
methods: {
async loadFoo () {
this.foo = await this.$axios.$get('foo')
}
}
}
</script>If you have components in nested directories:
components/
foo/
Bar.vueThe component name will be based on its filename:
<Bar />We do recommend to use the directory name in the filename for clarity in order to use <FooBar />:
components/
foo/
FooBar.vueIf you want to keep the filename as Bar.vue, consider using the prefix option: (See directories section)
components: [
'~/components/',
{ path: '~/components/foo/', prefix: 'foo' }
]By setting components: true, default ~/components directory will be included.
However you can customize module behaviour by providing directories to scan:
export default {
components: [
'~/components', // shortcut to { path: '~/components' }
{ path: '~/components/awesome/', prefix: 'awesome' }
],
}Each item can be either string or object. String is shortcut to { path }.
Note: Don't worry about ordering or overlapping directories! Components module will take care of it. Each file will be only matched once with longest path.
- Required
- Type:
String
Path (absolute or relative) to the directory containing your components.
You can use nuxt aliases (~ or @) to refer to directories inside project or directly use a npm package path similar to require.
- Type:
Array<string> - Default:
- Extensions supported by nuxt builder (
builder.supportedExtensions) - Default supported extensions
['vue', 'js']or['vue', 'js', 'ts', 'tsx']depending on your environment
- Extensions supported by nuxt builder (
Example: Support multi-file component structure
If you prefer to split your SFCs into .js, .vue and .css, you can only enable .vue files to be scanned:
βββ src
β βββ components
β βββ componentC
β βββ componentC.vue
β βββ componentC.js
β βββ componentC.scss
// nuxt.config.js
export default {
components: [
{ path: '~/components', extensions: ['vue'] }
]
}- Type:
string(glob pattern) - Default:
**/*.${extensions.join(',')}
Accept Pattern that will be run against specified path.
- Type:
Array - Items:
string(glob pattern) - Default:
[]
Ignore patterns that will be run against specified path.
- Type:
String - Default:
''(no prefix)
Prefix all matched components.
Example below adds awesome-/Awesome prefix to the name of components in awesome/ directory.
// nuxt.config.js
export default {
components: [
'~/components',
{ path: '~/components/awesome/', prefix: 'awesome' }
]
}components/
awesome/
Button.vue
Button.vue<template>
<div>
<AwesomeButton>Click on me π€</AwesomeButton>
<Button>Click on me</Button>
</div>
</template>- Type:
Boolean - Default:
true
Watch specified path for changes, including file additions and file deletions.
- Type:
Boolean - Default:
'auto'
Transpile specified path using build.transpile, by default ('auto') it will set transpile: true if node_modules/ is in path.
Making Vue Component libraries with automatic tree-shaking and component registration is now damn easy β¨
This module expose a hook named components:dirs so you can easily extend the directory list without updating user configuration in your Nuxt module.
Imagine a directory structure like this:
| node_modules/
---| awesome-ui/
------| components/
---------| Alert.vue
---------| Button.vue
------| nuxt.js
| pages/
---| index.vue
| nuxt.config.jsThen in awesome-ui/nuxt.js you can use the components:dir hook:
import { join } from 'path'
export default function () {
this.nuxt.hook('components:dirs', (dirs) => {
// Add ./components dir to the list
dirs.push({
path: join(__dirname, 'components'),
prefix: 'awesome'
})
})
}That's it! Now in your project, you can import your ui library as a Nuxt module in your nuxt.config.js:
export default {
buildModules: [
'@nuxt/components',
'awesome-ui/nuxt'
]
}And directly use the module components (prefixed with awesome-), our pages/index.vue:
<template>
<div>
My <AwesomeButton>UI button</AwesomeButton>!
<awesome-alert>Here's an alert!</awesome-alert>
</div>
</template>It will automatically import the components only if used and also support HMR when updating your components in node_modules/awesome-ui/components/.
Next: publish your awesome-ui module to npm and share it with the other Nuxters β¨
