With 9.19
version, Laravel offer a new bundle for assets, vite
. If you use a Laravel version under 9.19
, check this guide.
Node.js packages
pnpm i
pnpm remove axios lodash
pnpm add typescript -D
Views
<?phpnamespace App\Providers;use Illuminate\Support\Facades\View;use Illuminate\Support\ServiceProvider;class AppServiceProvider extends ServiceProvider{ /** * Register any application services. */ public function register() { // } /** * Bootstrap any application services. */ public function boot() { View::addNamespace('front', resource_path('front')); }}
mkdir resources/frontmkdir resources/front/componentsmkdir resources/front/layoutsmkdir resources/front/pagestouch resources/front/global.d.tsmv resources/css resources/front/cssmv resources/js resources/tsmv resources/ts resources/front/tsmv resources/front/ts/app.js resources/front/ts/app.tsrm resources/front/ts/bootstrap.js
tsconfig.json
touch tsconfig.json
{ "compilerOptions": { "target": "esnext", "module": "esnext", "moduleResolution": "node", "strict": true, "jsx": "preserve", "sourceMap": true, "resolveJsonModule": true, "esModuleInterop": true, "skipLibCheck": true, "noImplicitAny": false, "lib": [ "esnext", "dom" ], "types": [ "vite/client" ], "typeRoots": [ "./node_modules/@types", "resources/**/*.d.ts" ], "paths": { "~": [ "./resources" ], "~/*": [ "./resources/*" ] } }, "include": [ "resources/**/*.ts", "resources/**/*.d.ts", "resources/**/*.tsx", "resources/**/*.vue" ], "exclude": [ "resources/views/stubs", "resources/webreader/scripts/library", "resources/admin/auto-imports.d.ts" ]}
Vite
mv vite.config.js vite.config.ts
import { defineConfig } from 'vite'import laravel from 'laravel-vite-plugin'export default defineConfig({ plugins: [ laravel({ input: ['resources/front/css/app.css', 'resources/front/ts/app.ts'], refresh: ['resources/**'], }), ],})
Blade
mkdir resources/views/componentstouch resources/views/components/app.blade.php
<!DOCTYPE html><html lang="{{ str_replace('_', '-', app()->getLocale()) }}"><head> <meta charset="UTF-8"> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta name="csrf-token" content="{{ csrf_token() }}"> <title>@yield('title', app_name())</title> {{-- {!! SEO::generate() !!} --}} <link rel="icon" type="image/x+ico" href="/favicon.ico"> <link rel="apple-touch-icon" sizes="180x180" href="/apple-touch-icon.png"> <link rel="icon" type="image/png" sizes="32x32" href="/favicon-32x32.png"> <link rel="icon" type="image/png" sizes="16x16" href="/favicon-16x16.png"> <link rel="manifest" href="/site.webmanifest"> {{-- <script src="{{ asset('/color-mode.js') }}"></script> --}} @stack('head') @stack('styles') {{-- @livewireStyles --}}</head><body class="{{ config('app.env') === 'local' ? 'debug-screens' : '' }} color-mode"> {{ $slot }} @stack('modals') @stack('scripts') {{-- @livewireScripts --}}</body></html>
Layout
touch resources/front/layouts/app.blade.php
<x-app> @push('head') @vite(['resources/front/css/app.css', 'resources/front/ts/app.ts']) @endpush @yield('default')</x-app>
Page
touch resources/front/pages/index.blade.php
@extends('front::layouts.app')@section('default') Content@endsection
Controller
php artisan make:controller Front/FrontController
<?phpnamespace App\Http\Controllers\Front;use App\Http\Controllers\Controller;class FrontController extends Controller{ public function index() { return view('front::pages.index'); }}
Routes
Route::get('/', [FrontController::class, 'index'])->name('front.index');
spatie/laravel-route-attributes
composer require spatie/laravel-route-attributes
php artisan vendor:publish --provider="Spatie\RouteAttributes\RouteAttributesServiceProvider" --tag="config"
<?phpreturn [ // ... 'directories' => [ // app_path('Http/Controllers'), ], // ...];
<?phpnamespace App\Providers;use Illuminate\Cache\RateLimiting\Limit;use Illuminate\Foundation\Support\Providers\RouteServiceProvider as ServiceProvider;use Illuminate\Http\Request;use Illuminate\Routing\Router;use Illuminate\Support\Facades\RateLimiter;use Illuminate\Support\Facades\Route;use Spatie\RouteAttributes\RouteRegistrar;class RouteServiceProvider extends ServiceProvider{ public const HOME = '/home'; public function boot() { $this->configureRateLimiting(); $this->routes(function () { Route::middleware('api') ->prefix('api') ->group(base_path('routes/api.php')) ; Route::middleware('web') ->group(base_path('routes/web.php')) ; }); Route::name('front.') ->group( fn () => (new RouteRegistrar(app(Router::class))) ->useRootNamespace(app()->getNamespace()) ->useMiddleware(['web']) ->registerDirectory(app_path('Http/Controllers/Front')) ) ; // Route::prefix('api') // ->name('api.') // ->group( // fn () => (new RouteRegistrar(app(Router::class))) // ->useRootNamespace(app()->getNamespace()) // ->useMiddleware(['api']) // ->registerDirectory(app_path('Http/Controllers/Api')) // ) // ; } // ...}
<?phpnamespace App\Http\Controllers\Front;use App\Http\Controllers\Controller;use Spatie\RouteAttributes\Attributes\Get;class FrontController extends Controller{ #[Get('/', name: 'front.index')] public function index() { return view('front::pages.index'); }}
<?php- Route::get('/', [FrontController::class, 'index'])->name('front.index');