Interested how Laravel works under the hood? → Check my Laravel Core Adventures Course

Moving A Laravel Webpack Project To Vite

#javascript #performance #laravel

Vite is the new front-end tooling for Laravel. Let's see how we can move a given Laravel project to Vite together.

Vite is the Next Generation Frontend Tooling, which is Laravel's default from now on.

The Laravel documentation contains an entire section explaining how it works and how to use it. But most of us are more interested in using it in an existing project. So that's what this post is for.

Note: This article concentrates on migrating a basic Laravel application. There will be differences if you use different tools like React or Vue.

Why Vite

Before switching to a new tool, it is a good idea to think about why you want to do that. It is already enough for me to be Laravel's new default front-end bundling, but let's also talk about some details.

The main benefit is the overall improved performance. Vite is faster in starting a new dev server, bundling assets, and updating them than other tools like webpack.

Vite is leveraging new advancements in the ecosystem, like the availability of native ES modules in the browser and the rise of JavaScript tools written in compile-to-native languages. There is a detailed explanation in the Why Vite section of the official docs.

Dependencies

Make sure to have the latest version of Laravel, which today is 9.19, to use the new Vite tooling. Then we need to install two new dependencies:

npm install --save-dev vite laravel-vite-plugin

Also, the scripts section of our package.json file will change due to the new Vite scripts.

"scripts": {
    "dev": "vite",
    "build": "vite build"
},

That's all we need for the scripts.

Since Vite is a replacement for webpack, we can remove the laravel-mix dependency and delete the webpack.mix.js file from our application.

npm remove laravel-mix && rm webpack.mix.js

Your package.json file will now look something like this:

    "private": true,
    "scripts": {
        "dev": "vite",
        "build": "vite build"
    },
    "devDependencies": {
        "axios": "^0.25",
        "laravel-vite-plugin": "^0.2.1",
        "lodash": "^4.17.19",
        "postcss": "^8.4.14",
        "postcss-import": "^14.0.1",
        "vite": "^2.9.11",
    }
}

Vite Configuration

Now we need to set up Vite. Therefore create a new vite.config.js file in the root of your Laravel application.

import laravel from 'laravel-vite-plugin'
import {defineConfig} from 'vite'

export default defineConfig({
    plugins: [
        laravel([
            'resources/css/app.css',
            'resources/js/app.js',
        ]),
    ],
});

This is where we use the vite and laravel-vite-plugin packages, and we also define our asset paths.

Using Vite In Your Templates

In the head of your template files, we have to load the assets through the new @vite blade directive.

@vite(['resources/css/app.css', 'resources/js/app.js'])

You don't need to use mix or load them manually anymore.

Running Vite

To run Vite, you use the npm script npm run dev, which we have defined, which is just an alias for npm run vite.

It will compile your assets lighting fast! To make your assets production-ready, you can use the new npm run build script to version and bundle your assets.

In the background, Vite is using the new assets compiled to the public/build directory. This means we can delete the old asset folders, public/css and public/js, in my case.

Importing JS Modules Might Change For You

Vite only supports ES modules, so require doesn't work anymore, and you need to import modules now in your scripts.

Example - not working with Vite anymore:

require('my-package');

Example - working with Vite:

import myPackage from 'my-package';

Using Tailwind CSS

If you use Tailwind CSS in your Laravel project, your styles won't work. That's because we need Post CSS for Tailwind CSS.

Create a postcss.config.js file, if you haven't already, and define two plugins there:

module.exports = {
    plugins: {
        tailwindcss: {},
        autoprefixer: {},
    },
};

You also need to have those packages installed, but if you already use Tailwind CSS, you should have them already.

Vite will look for the PostCSS configuration and automatically apply it if given. That's already it. Your Tailwind CSS styles should now work too.

Environment Variables

You can inject environment variables to JavaScript through your .env file, by prefixing them with VITE_.

For example, the given Laravel Pusher variables are no longer of use to you.

MIX_PUSHER_APP_KEY="${PUSHER_APP_KEY}"
MIX_PUSHER_APP_CLUSTER="${PUSHER_APP_CLUSTER}"

If you like to use them in JavaScript, rename them.

VITE_PUSHER_APP_KEY="${PUSHER_APP_KEY}"
VITE_PUSHER_APP_CLUSTER="${PUSHER_APP_CLUSTER}"

Automatically Migrate to Vite

Laravel Shift is an excellent service known for migrating your Laravel apps to a newer version with just one click.

Today was also a new shift released that migrates Laravel Mix to Vite.

Auto-Refresh Templates On Change

One of Vite's most prominent features is Hot Module Replacement for Vue.js and React.

But it's also great for refreshing a browser after file changes. By default, this is not working with Blade files, but Freek and Spatie got a working solution.

Just update your Vite configuration with a custom plugin named blade here:

import laravel from 'laravel-vite-plugin'
import {defineConfig} from 'vite'

export default defineConfig({
    plugins: [
        laravel([
            'resources/css/app.css',
            'resources/js/app.js',
        ]),
        {
            name: 'blade',
            handleHotUpdate({ file, server }) {
                if (file.endsWith('.blade.php')) {
                    server.ws.send({
                        type: 'full-reload',
                        path: '*',
                    });
                }
            },
        }
    ],
});

This is enough to refresh your browser after a blade file is changing. And again, this happens lightning fast!

Troubleshooting

Browser Blocking

Some browsers, like Brave, block Vite's request by default. You will see those errors in your browser console. This can prevent Vite from compiling your assets. So make sure to check your browser if you see blocking-request errors.

HTTPS and Valet

You may also run into an issue if you are running Laravel Valet locally with HTTPS secured sites. But, again, Freek already found a solution.

Successful Public Pull Requests

It may help you to see how others have already successfully moved their Laravel projects to Vite:

Conclusion

I like Vite a lot, and I hope this guide can help you switch from an existing Laravel project faster. Did I miss something? Please reach out to me on Twitter.

Do you like to learn more about Vite? Here are some excellent resources:

Do you enjoy my posts?

Sign up for my newsletter to receive updates on my latest content.

You will receive monthly updates on my latest articles and products. I do care about the protection of your data. Read my Privacy Policy.