Unable to use swiper/vue dependencies not found - vue.js

"vue": "^2.6.14"
"swiper": "^7.0.5",
import { Swiper, SwiperSlide } from 'swiper/vue';
import 'swiper/css';
i try default import as per example but:
These dependencies were not found:
#/swiper/css in ./node_modules/cache-loader/dist/cjs.js??ref--12-0!./node_modules/babel-loader/lib!./node_modules/cache-loader/dist/cjs.js??ref--0-0!./node_modules/vue-loader/lib??vue-loader-options!./src/components/Swiper.vue?vue&type=script&lang=js&
swiper/vue in ./node_modules/cache-loader/dist/cjs.js??ref--12-0!./node_modules/babel-loader/lib!./node_modules/cache-loader/dist/cjs.js??ref--0-0!./node_modules/vue-loader/lib??vue-loader-options!./src/components/Swiper.vue?vue&type=script&lang=js&
To install them, you can run: npm install --save #/swiper/css swiper/vue
i try to install:
npm install --save #/swiper/css swiper/vue
but the following error appears:
npm ERR! code ENOLOCAL
npm ERR! Could not install from "#\swiper\css" as it does not contain a package.json file.
npm ERR! A complete log of this run can be found in:
npm ERR! C:\Users\A262556\AppData\Roaming\npm-cache_logs\2021-09-14T13_57_46_048Z-debug.log

There seems to be an ongoing issue with the latest version of Swiper regarding module import.
At the moment, I would advise you to use Swiper v6 as a quick fix but you should try to see what is causing this issue (might be related to your bundler).
npm i swiper#^6.8.4
Edit: If you want to use Swiper 7 (from Swiper 6), the solution to your issue might be in the migration guide from Swiper.

Use direct style imports as shown in this example for React:
import 'swiper/swiper.scss'; // core Swiper
import 'swiper/modules/navigation/navigation.scss'; // Navigation module
import 'swiper/modules/pagination/pagination.scss'; // Pagination module

The easy solution for Swiper 7.4.1 on Vue 3 + Vite and compile with Webpack
is using alias.
All this files is located on base structure:
vite.config.js
import path from "path";

export default defineConfig({
resolve: {
alias: [
{
find: "#",
replacement: path.resolve(__dirname, "src"),
},
{
find: "#SwiperBundleCss",
replacement: path.resolve(__dirname, "./node_modules/swiper/swiper-bundle.min.css"),
},
{
find: "#SwiperBundle",
replacement: path.resolve(__dirname, "./node_modules/swiper/swiper-bundle.esm.js"),
},
{
find: "#Swiper",
replacement: path.resolve(__dirname, "./node_modules/swiper/swiper.esm.js"),
},
{
find: "#SwiperVue",
replacement: path.resolve(__dirname, "./node_modules/swiper/vue/swiper-vue.js"),
},
],
},
plugins: [ViteRequireContext(), vue()],
});
jsconfig.json
{
"include": [
"./src/**/*"
],
"compilerOptions": {
"baseUrl": ".",
"target": "esnext",
"module": "es2015",
"paths": {
"#SwiperBundleCss": ["./node_modules/swiper/swiper-bundle.min.css"],
"#SwiperBundle": ["./node_modules/swiper/swiper-bundle.esm.js"],
"#Swiper": ["./node_modules/swiper/swiper.esm.js"],
"#SwiperVue": ["./node_modules/swiper/vue/swiper-vue.js"],
}
}
}
vue.config.js
const path = require("path");
module.exports = {
publicPath: "/",
…
configureWebpack: {
resolve: {
alias: {
"#SwiperBundle": path.resolve(__dirname, "./node_modules/swiper/swiper-bundle.esm.js"),
"#SwiperBundleCss": path.resolve(__dirname, "./node_modules/swiper/swiper-bundle.min.css"),
"#Swiper": path.resolve(__dirname, "./node_modules/swiper/swiper.esm.js"),
"#SwiperVue": path.resolve(__dirname, "./node_modules/swiper/vue/swiper-vue.js"),
},
},
},
};
webpack.config.js
const path = require("path");
…
mode: "production",
stats: "errors-only",
resolve: {
alias: {
"#SwiperBundle": path.resolve(__dirname, "./node_modules/swiper/swiper-bundle.esm.js"),
"#SwiperBundleCss": path.resolve(__dirname, "./node_modules/swiper/swiper-bundle.min.css"),
"#Swiper": path.resolve(__dirname, "./node_modules/swiper/swiper.esm.js"),
"#SwiperVue": path.resolve(__dirname, "./node_modules/swiper/vue/swiper-vue.js"),
},
},
…
And finally how to declare in your project
main.js
…
import "#SwiperBundleCss"; //import css
import { Swiper, SwiperSlide } from "#SwiperVue"; //import component
import SwiperCore, { Pagination, Scrollbar } from "swiper"; //import swiper core and plugins
SwiperCore.use([Pagination, Scrollbar]); //declare two plugins
const app = createApp(App)
.use(router)
…
.component("swiper", Swiper) //declare vue component
.component("swiper-slide", SwiperSlide) //declare vue component
…
.use(devtools);
router.isReady().then(() => app.mount("#app"));
Usage in your .vue files
some_view.vue
<template>
<div>
<!—// … //—>
<swiper
:scrollbar="{
hide: false,
}"
:slides-per-view="isMobileScreen"
:space-between="10"
:grabCursor="true"
:loop="true"
>
<swiper-slide>
<img src=“some_image.jpg" alt="" />
</swiper-slide>
<swiper-slide>
<img src=“some_image.jpg" alt="" />
</swiper-slide>
<swiper-slide>
<img src=“some_image.jpg" alt="" />
</swiper-slide>
</swiper>
<!—// … //—>
</div>
</template>
You can read more info about aliases right there:
https://webpack.js.org/configuration/resolve/
https://github.com/vuejs/vue-cli/issues/2398
https://dev.to/alansolitar/webpack-aliases-in-vue-js-41hp
Regards

Related

Nuxt 3 with TailwindCSS -> heroicons

Can someone help with setting up Heroicons in combination with Nuxt 3?
I ran the following command:
yarn add #heroicons/vue
I also added #heroicons/vue as following to my nuxt.config.js:
build: {
transpile: ["#headlessui/vue", "#heroicons/vue"],
postcss: {
plugins: {
tailwindcss: {},
autoprefixer: {},
},
},
},
But I can't seem to make it work at all.
Could you tell me what I have to do?
Tailwindcss and Nuxt
first you should ,install tailwind package:
npm install -D tailwindcss postcss autoprefixer
then generate tailwind cona fig file:
npx tailwindcss init
Add Tailwind to your PostCSS configuration
// https://v3.nuxtjs.org/api/configuration/nuxt.config
export default defineNuxtConfig({
postcss: {
plugins: {
tailwindcss: {},
autoprefixer: {},
},
},
})
then inside your tailwind.config.js Configure your template paths:
/** #type {import('tailwindcss').Config} */
module.exports = {
content: [
"./components/**/*.{js,vue,ts}",
"./layouts/**/*.vue",
"./pages/**/*.vue",
"./pages/index.vue",
"./plugins/**/*.{js,ts}",
"./nuxt.config.{js,ts}",
"./app.vue",
],
theme: {
extend: {},
},
plugins: [],
}
! if you set srcDir correct the paths
then add the Tailwind directives to your CSS:
add main.css file to your assets with this content:
Add main.css the CSS file globally
main.css file:
#tailwind base;
#tailwind components;
#tailwind utilities;
nuxt.config.js
css: ['~/assets/css/main.css'],
finally you can use tailwind.
final nuxt.config.js file :
export default defineNuxtConfig({
css: ["#/assets/styles/main.scss"],
postcss: {
plugins: {
"postcss-import": {},
"tailwindcss/nesting": {},
tailwindcss: {},
autoprefixer: {},
},
},
})
Heroicons and Nuxt
First, you should install Heroicons package:
npm install #heroicons/vue
then you can use it like this:
<template>
<BeakerIcon class="h-6 w-6 text-blue-500" />
</template>
<script lang="ts" setup>
import { BeakerIcon } from "#heroicons/vue/24/solid";
</script>
The 24x24 outline icons can be imported from #heroicons/vue/24/outline, the 24x24 solid icons can be imported from #heroicons/vue/24/solid, and the 20x20 solid icons can be imported from #heroicons/vue/20/solid.
learn more here: https://github.com/tailwindlabs/heroicons#vue
but try nuxt-icon library :)
Here is how you should set up a nuxt.config.js file together with tailwindcss and nuxt-icon library:
export default defineNuxtConfig({
modules: ['nuxt-icon'],
css: ['~/assets/css/main.css'], // css file with #tailwind base etc.
postcss: {
plugins: {
tailwindcss: {},
autoprefixer: {}
}
}
})
Like I wrote in comment, nuxt-icon contains all Heroicons together with 100k + more.
Here is the way you can use this icon library: https://stackoverflow.com/a/73810640/6310260

taildwindcss config not applied in nuxt3 app

I am still very much at the start of a new project using nuxt3. I installed tailwindcss for quick themeing and prototyping. I followed the basic setup on the documentation for the tailwindcss plugin for nuxt 3.
The problem is, that the background color for the welcome message is not applied (the CSS property also does not show up on the rendered HTML). When I change the CSS to something like this: class="bg-green-200", then it works.
I could not find any similar issues, however I'm sure I can't be the first/only one stumbling over this. I appreciate any hints.
**Edit: ** The issue was the import syntax in the tailwind configuration file. Changing the import to the require syntax solved the issue.
My code is as follows:
nuxt.config.js
export default defineNuxtConfig({
modules: [
'#nuxtjs/robots',
'#nuxtjs/color-mode',
'#nuxtjs/tailwindcss',
'#nuxtjs/i18n',
],
i18n: {
locales: [
{
code: 'de', name: 'Deutsch', iso: 'en-US', file: 'de.js'
},
{
code: 'en', name: 'English', iso: 'de-CH', file: 'en.js'
},
],
defaultLocale: 'de',
strategy: 'prefix_except_default',
langDir: 'languages',
detectBrowserLanguage: {
useCookie: true,
cookieKey: 'i18n_redirected',
redirectOn: 'root', // recommended
},
},
buildModules: [],
robots: {},
tailwindcss: {
configPath: 'tailwind.config.js',
exposeConfig: false,
injectPosition: 0,
}
})
tailwind.config.js
import defaultTheme from 'tailwindcss/defaultTheme'
export default {
theme: {
extend: {
colors: {
primary: defaultTheme.colors.green
}
}
}
}
app.vue
<template>
<NuxtLayout>
<NuxtPage />
</NuxtLayout>
</template>
layouts/default.vue
<template>
<div>
<LayoutHeader/>
<slot />
<LayoutFooter/>
</div>
</template>
pages/index.vue
<template>
<div>
<div class="bg-primary">Welcome to the homepage</div>
</div>
</template>
The main issue being that tailwind.config.css is not a valid configuration file because we're using JS here, hence why npx tailwindcss init is the recommended way to safely generate the configuration file (the config itself is a JS file, not a CSS one).
I have successfully installed it with the following tailwind.config.js file
const colors = require('tailwindcss/colors')
/** #type {import('tailwindcss').Config} */
module.exports = {
content: [
"./components/**/*.{js,vue,ts}",
"./layouts/**/*.vue",
"./pages/**/*.vue",
"./plugins/**/*.{js,ts}",
"./nuxt.config.{js,ts}",
],
theme: {
extend: {
colors: {
primary: colors.green
}
},
},
}
Here is a reference to the documentation: https://tailwindcss.com/docs/customizing-colors#naming-your-colors
Here is a working github repo.

Vite vuetify plugin doesn't load components listed in external libraries

I am creating a library that wraps Vuetify 3 components. But when I try to use the library it gives the following error:
[Vue warn]: Failed to resolve component: v-btn If this is a native custom element, make sure to exclude it from component resolution via compilerOptions.isCustomElement.
Library vite.config.ts :
import { fileURLToPath, URL } from 'node:url';
import { resolve } from 'node:path';
import { defineConfig } from 'vite';
import vue from '#vitejs/plugin-vue';
import vueJsx from '#vitejs/plugin-vue-jsx';
import vuetify from 'vite-plugin-vuetify';
export default defineConfig({
plugins: [
vue(),
vueJsx(),
// vuetify({ autoImport: true, styles: 'none' }), // Don't export vuetify
],
resolve: {
alias: {
'#': fileURLToPath(new URL('./src', import.meta.url)),
},
},
build: {
lib: {
entry: resolve(__dirname, 'src/main.ts'),
name: '#my/ui',
// the proper extensions will be added
fileName: 'my-ui',
},
rollupOptions: {
// make sure to externalize deps that shouldn't be bundled
// into your library
external: ['vue', 'vuetify'],
output: {
// Provide global variables to use in the UMD build
// for externalized deps
globals: {
vue: 'Vue',
vuetify: 'Vuetify',
},
},
},
},
});
Nuxt project nuxt.config.ts:
import { defineNuxtConfig } from 'nuxt';
import vuetify from 'vite-plugin-vuetify';
export default defineNuxtConfig({
css: ['#/assets/css/main.css'],
modules: [
async (options, nuxt) => {
nuxt.hooks.hook('vite:extendConfig', (config) =>
config.plugins.push(vuetify({ autoImport: true }))
);
},
],
build: {
transpile: ['#my/ui', 'vuetify'],
},
});
Nuxt project app.vue:
<template>
<v-app>
<v-main>
<HelloWorld label="Test" primary />
</v-main>
</v-app>
</template>
<script lang="ts" setup>
import { HelloWorld } from '#my/ui';
</script>
Nuxt project plugin vuetify.ts:
import 'vuetify/styles';
import { createVuetify } from 'vuetify';
import * as components from 'vuetify/components';
import * as directives from 'vuetify/directives';
export default defineNuxtPlugin((nuxtApp) => {
const vuetify = createVuetify({
// components, if imported components getting resolved but treeshaking doesn't work.
// directives
});
nuxtApp.vueApp.use(vuetify);
});
Expected Behavior
Vuetify components from the Library project should be auto imported.
Current workaround:
If the vuetify components are imported in the parent project then the components are resolved. But this causes issue as the library users has to know what to import or import on global which is creating larger bundle size.
Is there an alternative way to implement and meet the following criteria:
Wrapping module doesn't depend on vuetify (Peer dep only)
Consuming app can auto import and get all of the benefits of tree shaking
Consuming app doesn't need to import any of the peer dependencies of the wrapping module.
Thank you so much in advance.
Just to create an answer for the workaround Sasank described:
If you just want to get rid of the error, import the components into the parent project as described in this link: https://next.vuetifyjs.com/en/features/treeshaking/#manual-imports

TypeError: Cannot read properties of null (reading 'isCE') - Custom Component Library

I am having trouble building a custom component library for Vue 3 using ViteJS and NPM. I have included a basic illustration of my issue below, can someone please tell me what I am doing wrong or point me in the right direction, I have been stuck on this for 2 days :(.
My folder structure:
dist
node_modules
src
components
Paragraph.vue
paragraph.js
.gitignore
package.json
README.md
vite.config.js
package.json
{
"name": "paragraph",
"private": true,
"version": "0.0.0",
"description": "The paragraph test component.",
"main": "./dist/paragraph.umd.js",
"module": "./dist/paragraph.es.js",
"exports": {
".": {
"import": "./dist/paragraph.es.js",
"require": "./dist/paragraph.umd.js"
},
"./dist/style.css": "./dist/style.css"
},
"scripts": {
"dev": "vite",
"build": "vite build",
"preview": "vite preview"
},
"dependencies": {
"vue": "^3.2.25"
},
"devDependencies": {
"#vitejs/plugin-vue": "^2.3.1",
"vite": "^2.9.5"
}
}
vite.config.js
import { fileURLToPath, URL } from 'url'
import { defineConfig } from 'vite'
import vue from '#vitejs/plugin-vue'
// https://vitejs.dev/config/
export default defineConfig({
build: {
lib: {
entry: fileURLToPath(new URL('./src/paragraph.js', import.meta.url)),
name: 'Paragraph',
fileName: (format) => `paragraph.${format}.js`,
},
rollupOptions: {
external: ['vue'],
output: {
globals: {
vue: 'Vue'
},
},
},
},
plugins: [vue()],
resolve: {
alias: {
'#': fileURLToPath(new URL('./src', import.meta.url))
},
},
})
paragraph.js
import Paragraph from './components/Paragraph.vue';
export default {
install: (app) => {
app.component('Paragraph', Paragraph);
},
};
Paragraph.vue
<script setup>
console.log('Test');
</script>
<template>
<p class="paragraph">
<slot />
</p>
</template>
<style>
.paragraph
{
color: black;
}
</style>
When I run npm run build it works successfully and creates the correct files, I then include the es file into my test Vue project as a plugin.
import { createApp } from 'vue'
import App from './App.vue'
import Paragraph from '../../paragraph/dist/paragraph.es.js'
createApp(App).use(Paragraph).mount('#app')
The component doesn't work when used liked this.
<Paragraph>Hello World 2!</Paragraph>
The following error is reported back in the console.
TypeError: Cannot read properties of null (reading 'isCE')
I have looked into the issue and it seems a lot of people have had the same issue, although I cannot find a fix for myself.
I have tried the solutions mentioned in the following links:
https://github.com/vuejs/core/issues/4344
When Importing Self Made Vue 3 Library Into Vue 3 Project: "Uncaught TypeError: Cannot read properties of null (reading 'isCE')"
Neither of the solutions mentioned here are working.
Can someone please help!!!
I have noticed if I exclude the <slot /> it works fine, but slots are vital to components.
I know it is bundling the Vue code into the build file, but how do I stop it doing so.
Thanks in advance.
I've also encountered this very frustrating issue. According to this answer, it is caused by having Vue imported from multiple packages instead of using just one singleton, as you do suspect.
Presumably, you are building your consumer application using Vite. In that case, setting the dedupe option in its vite.confg.js should solve it.
resolve: {
dedupe: [
'vue'
]
},
I've also encountered this issue :) the problem is you have two distinct copies of the Vue package being used
just read this and you will find your answer. for me, changing the workspace to yarn was the solution.
https://github.com/vuejs/core/issues/4344
Try to remove node_modules + yarn.lock
And then reinstall packages (yarn)

Vue3, Typescript and Eslint raise: "Parsing error: '}' expected"

I am writing code by Vue3 and Typescript, and this is the code of App.vue, which is the root component:
<template>
<router-view v-if="inited" />
<div v-else>
Initing...
</div>
</template>
<script lang="ts">
import router from './router';
import { defineComponent } from 'vue';
import { useStore } from 'vuex';
import { key } from './store';
const store = useStore(key);
export default defineComponent({
data() {
return { inited: store.state.inited };
},
});
</script>
But the eslint tell me:
/home/peter/proj/skogkatt-next/src/App.vue
17:9 error Parsing error: '}' expected
I use many time on Google and so on, but still cannot find a useful solution. This is the config of eslint in package.json:
{
// ...
"eslintConfig": {
"root": true,
"env": {
"node": true
},
"parser": "#typescript-eslint/parser",
"plugins": [
"#typescript-eslint"
],
"extends": [
"plugin:vue/vue3-essential",
"eslint:recommended",
"#vue/typescript",
"plugin:#typescript-eslint/eslint-recommended",
"plugin:#typescript-eslint/recommended"
],
"parserOptions": {
"parser": "#typescript-eslint/parser"
},
"rules": {
"#typescript-eslint/camelcase": "off"
}
},
// ...
}
I am not sure which config is useful or not, so I post those out. Thanks.
The error is caused by "plugin:#typescript-eslint/recommended", which sets the top-level parser, which collides with Vue's vue-eslint-parser. In addition, your own config duplicates the top-level parser setting already set in the plugin, and should also be removed.
Vue's ESLint config for TypeScript projects addresses this problem, so consider copying it:
module.exports = {
plugins: ['#typescript-eslint'],
// Prerequisite `eslint-plugin-vue`, being extended, sets
// root property `parser` to `'vue-eslint-parser'`, which, for code parsing,
// in turn delegates to the parser, specified in `parserOptions.parser`:
// https://github.com/vuejs/eslint-plugin-vue#what-is-the-use-the-latest-vue-eslint-parser-error
parserOptions: {
parser: require.resolve('#typescript-eslint/parser'),
extraFileExtensions: ['.vue'],
ecmaFeatures: {
jsx: true
}
},
extends: [
'plugin:#typescript-eslint/eslint-recommended'
],
overrides: [{
files: ['*.ts', '*.tsx'],
rules: {
// The core 'no-unused-vars' rules (in the eslint:recommeded ruleset)
// does not work with type definitions
'no-unused-vars': 'off',
}
}]
}
Another option is to generate a TypeScript project with Vue CLI, and copying the resulting ESLint config.
I think it should be:
import { router } from './router';
Check if you have eslintConfig specified in both package.json and separate eslint config file. Both of these conflict and give this inconsistent state.
Its best to remove eslintConfig from package.json and move those to eslint config file.