Overview Inertia v3 represents a significant evolution in how developers bridge the gap between Laravel and modern frontend frameworks like React and Vue.js. Traditionally, building a Single-Page Application (SPA) required maintaining a complex API layer, managing state across two repositories, and handling authentication twice. Inertia.js solved this by acting as the glue, allowing you to build SPAs using standard server-side routing and controllers. Version 3 takes this developer experience further by stripping away boilerplate and introducing features that were previously left to manual implementation. This update focuses on three core pillars: reducing the footprint of the client-side library, improving the feedback loop during development (especially for Server-Side Rendering), and providing first-class utilities for the modern UI patterns users expect, such as optimistic updates and background HTTP requests. Prerequisites To follow this guide and implement these features, you should be comfortable with the following: * **PHP & Laravel:** Understanding of routes, controllers, and middleware. * **Modern JavaScript:** Familiarity with ES6 syntax and a frontend framework (Vue 3 or React). * **Vite:** Basic knowledge of how Vite handles asset bundling in a Laravel context. * **Inertia Fundamentals:** A baseline understanding of how Inertia.js pages receive data as props from the server. Key Libraries & Tools * Inertia.js v3: The core library and its framework-specific adapters. * Laravel: The recommended backend framework for the Inertia protocol. * Vite: The build tool used to compile assets and run the new Inertia plugin. * Laravel Wayfinder: A tool that provides type-safe routing and form integration between the backend and frontend. * Pest: Used for browser testing, now with better SSR error reporting. Section 1: The New Vite Plugin and SSR Development One of the most immediate changes in v3 is the move toward a cleaner, plugin-driven architecture. In previous versions, your `app.js` entry point was often cluttered with boilerplate code required to resolve components and set up the application. Pascal Baljet explains that the new Vite plugin handles this automatically. Cleaning up app.js Previously, you had to manually define a `resolve` callback to tell Inertia where your page components lived. In v3, the Vite configuration handles this, allowing your entry point to look like this: ```javascript import { createInertiaApp } from '@inertiajs/vue3' import { resolvePageComponent } from 'laravel-vite-plugin/inertia-helpers' import { createApp, h } from 'vue' createInertiaApp({ setup({ el, App, props, plugin }) { createApp({ render: () => h(App, props) }) .use(plugin) .mount(el) }, }) ``` By including the `@inertiajs/vite-plugin` in your `vite.config.js`, you no longer need a separate `ssr.js` entry point. The plugin detects the environment and serves the correct bundle, drastically reducing file noise in your `resources/js` directory. Real-Time SSR Debugging Server-Side Rendering (SSR) is vital for SEO and initial load performance, but it was notoriously difficult to debug locally. In v3, running `npm run dev` now spins up an SSR development endpoint. When a component fails to render on the server—for example, if you accidentally reference the `window` object in a server-side context—the error is caught and displayed with a full stack trace directly in your terminal and browser. ```javascript // This will now throw a clean SSR error in the console instead of silently crashing export default { setup() { if (typeof window !== 'undefined') { // Browser only code } // If you call window.alert() here, v3 provides a source-mapped error trace } } ``` Section 2: Replacing Axios with useHTTP In a move to make the library leaner, Inertia.js v3 has dropped Axios as a hard dependency. While Axios is powerful, it is often overkill for the specific needs of an Inertia application. By replacing it with a custom XHR implementation, the library shed approximately 100KB from its bundle size. The useHTTP Hook To fill the gap for non-navigational requests (like checking a username's availability or toggling a status without changing pages), v3 introduces the `useHTTP` hook. It mirrors the familiar `useForm` API, making it intuitive for long-time users. ```javascript import { useHTTP } from '@inertiajs/vue3' const http = useHTTP({ username: '', }) const checkAvailability = () => { http.post('/check-username', { onSuccess: (response) => { console.log('Available:', response.data.available) }, }) } ``` Unlike the standard `router.post` or `useForm.post`, this does not trigger a page visit. It returns raw JSON from your controller, allowing for highly interactive UI elements that don't reload the entire page state. Section 3: Native Optimistic Updates Perhaps the most requested feature in the v3 release is built-in support for optimistic updates. In modern web apps, users expect instant feedback. If they click a "favorite" button, the icon should turn red immediately, even if the server takes 200ms to process the request. Implementing Instant Feedback In v3, you can prepend any request with the `.optimistic()` method. This method takes a callback where you define what the props *should* look like assuming the request succeeds. ```javascript import { router } from '@inertiajs/vue3' const toggleFavorite = (id) => { router.optimistic((props) => ({ contacts: props.contacts.map(c => c.id === id ? { ...c, is_favorite: !c.is_favorite } : c ) })).post(`/contacts/${id}/favorite`) } ``` If the server returns an error, Inertia automatically rolls back the state to the previous snapshot. This eliminates the need for developers to manually track "loading" or "pending" states for every single toggle switch in their application. Section 4: Instant Visits and Shared Props Traditional Inertia visits wait for the server to respond with the new page data before performing the navigation. Instant visits change this by navigating to the target component immediately and filling in the data as it arrives. How Instant Visits Work When you use an instant visit, you specify which component to render. Inertia will carry over "shared props"—like the authenticated user or the site name—so the layout renders correctly while the specific page content remains in a loading state. ```javascript router.visit('/profile', { component: 'Profile/Show', // Optionally define specific props to carry over pageProps: (currentProps) => ({ user: currentProps.auth.user }) }) ``` This is perfect for pages where the data fetching is slow but the UI structure is known, giving the user the feeling of a lightning-fast application. Syntax Notes * **Generics for Forms:** The `useForm` hook now supports generics, providing full type-hinting for your form data. This is especially powerful when combined with Laravel Wayfinder. * **Event Renaming:** Several events have been renamed for clarity. `onInvalid` is now `onHTTPException`, and the generic `exception` event is now `onNetworkError` (specific to client-side connectivity issues). * **Layout Prop Access:** A new `useLayoutProps` hook allows page components to pass data directly up to their parent layouts without needing a complex state management library or nested event emitting. Practical Examples 1. **Travel Booking Dashboards:** Use optimistic updates for seat selection or filter toggles where server-side latency is high due to third-party API calls. 2. **Live Search:** Use `useHTTP` to fetch search suggestions in real-time as the user types, without interrupting their scroll position or page state. 3. **Complex Error Pages:** Leverage the new `handleExceptionsUsing` callback in your Laravel AppServiceProvider to render custom 404 or 500 pages that still have access to your shared layout data and authenticated user info. Tips & Gotchas * **The Server Always Wins:** Remember that in optimistic updates, once the real server response arrives, it overwrites the optimistic state. Ensure your frontend logic and backend logic are perfectly synced. * **SSR Awareness:** When using the improved SSR, be careful with third-party libraries that assume a `window` object exists. Use the `onMounted` lifecycle hook to run browser-only code. * **Upgrading:** If your project relies heavily on Axios interceptors for global headers, you must either migrate that logic to Inertia's middleware or manually reinstall Axios and pass it to the `createInertiaApp` configuration as an adapter.
Laravel Wayfinder
Products
TL;DR
The Laravel channel (5 mentions) drives positive sentiment through technical showcases like 'Laravel Wayfinder: End-to-End Type Safety' and the 'Laracon Keynote 2025' and defines the tool as an automated bridge.
- Mar 19, 2026
- Jan 10, 2026
- Sep 8, 2025
- Jul 30, 2025
- Apr 9, 2025