How to use npm packages in Laravel with Vite frontend build tool
Vite is a Next Generation Frontend Tooling and Vite is now the default Laravel module bundler.
this method will help you to configure any npm package. just import the package in /resources/js/app.js and add <script type="module"></script>
where you want to use that npm package.
Checkout Laracast threads on this topic for more in-depth details with my comment [link]
https://laracasts.com/discuss/channels/vite/laravel-vite-jquery?page=1&replyId=825471
How to use any NPM Package in Laravel with Vite
- install npm package (like jquery, dropzone, select2, etc…)
- import that package in `/resources/js/app.js`
- import $ from ‘jquery’
- import select2 from “select2”
- import dropzone from “dropzone”
- window.jQuery = window.$ = $
- add attribute type=”module” in <script> tag where you want to use that npm package.
How to use any NPM Package in Laravel with Vite
2 2 minutes
install npm package
install npm package (like jquery, dropzone, select2, etc…)
import that package in /resources/js/app.js
import $ from ‘jquery’
import select2 from “select2”
import dropzone from “dropzone”
window.jQuery = window.$ = $
add attribute type=”module” in </p>
<script type=”module”></script>
Usage
<script type=”module”> $(“button”).click(function() { $(“p”).hide(); }); $(“.select2”).select2(); </script>
How to fix Uncaught ReferenceError: $ is not defined issue with vitejs
- First your route URL request load
- then app.css
- then app.js
- then all other imports (like fonts, svg, css, js)
- (means jquery, select2, dropzone etc will load after app.js)
-- and due to this you got the Uncaught ReferenceError: $ is not defined
Goto: (check the sequence of your project)
-- Inspect element
-- Network
-- and you can see the request sequence
Suppose you import jQuery, select2, dropzonejs, and other packages in resources/js/app.js like
-------------------------------
import $ from 'jquery'
import select2 from "select2"
import dropzone from "dropzone"
window.jQuery = window.$ = $
-------------------------------
/**
then above all imports didn't work properly reason you need to add module in <script> attribute.
Using module on your inline <script> tag solves this issue by loading the JavaScript in the correct order, making app.js load in before your inline <script> tags and populating the window object with jQuery.
**/
Example:
<script type="module">
$("button").click(function() {
$("p").hide();
});
$(".select2").select2();
</script>
and maybe you use @stack, @push then the code will be
@push('js_after')
<script type="module">
$("button").click(function() {
$("p").hide();
});
$(".select2").select2();
</script>
@endpush
Below is the complete details step by step.
Complete details step by step.
install npm the package you want.
npm i jquery
npm i select2 // maybe
npm install --save dropzone // maybe
2nd: add Jquery alias in vite.config.js
[you can skip this step, if you don’t want alias and jump to 3rd-step]
import { defineConfig } from 'vite';
import laravel from 'laravel-vite-plugin';
export default defineConfig({
plugins: [
laravel({
input: [
'resources/css/app.css',
'resources/js/app.js',
],
refresh: true,
}),
],
resolve: {
alias: {
'$': 'jQuery',
},
},
});
3rd: add the below code at end of the resources/js/app.js
import $ from 'jquery'
import select2 from "select2"
import dropzone from "dropzone"
window.jQuery = window.$ = $
4th: make sure you added @vite([‘resources/css/app.css’, ‘resources/js/app.js’]) in <head>
<head>
<meta charset="utf-8">
<title>Dashboard</title>
@vite(['resources/css/app.css', 'resources/js/app.js'])
</head>
<body>
@yield('content')
@stack('js_after')
</body>
5th: try to add type=”module” in </p>
<script type="module">
$("button").click(function() {
$("p").hide();
});
$(".select2").select2();
</script>
// with child blade
@extends('layouts.dashboard')
@section('content')
<!-- your blade code -->
@push('js_after')
<script type="module">
$("button").click(function() {
$("p").hide();
});
$(".select2").select2();
</script>
@endpush
@endsection
Also read: