bastinald/ux
Bastinald/UX is a Laravel package that provides reusable Blade UI components for building clean, responsive interfaces faster. It streamlines common layout, form, and navigation patterns, helping you create polished admin screens and frontend pages with less repetitive markup.
Install the package with Composer and run its installer:
composer require bastinald/ux
php artisan ux:install
The install step is the first place to look. It publishes the package's stubs, a base layout, and wires up the Livewire/Bootstrap assets the scaffolding expects. Check config/ and resources/views/layouts/ (or wherever the installer points) for what was added, and confirm routes/web.php still contains your existing routes after publishing.
Then scaffold authentication:
php artisan ux:auth
This generates Login, Register, Forgot Password, and related Livewire components plus their views and routes. Visit /login to confirm the flow works end to end.
The first real use case is scaffolding a CRUD screen for a simple Eloquent model:
php artisan ux:crud Post
That creates a Livewire component, a Blade view, and a route. Run php artisan route:list | grep post to find the URL and open it. From there, edit the generated component to match your model's $fillable fields — this is scaffolding, not a runtime framework, so everything after generation lives in your app code.
Scaffold auth once, then scaffold CRUD per model. Do the auth pass first so the CRUD pages have a working layout and session context to sit inside. Then run ux:crud for each entity you need an admin screen for: ux:crud Post, ux:crud Category, etc.
Treat the generated component as your component. The command produces a complete Livewire class with a modal-driven create/edit flow, search, pagination, and delete handling in one place. The intended workflow is: generate, then edit the generated file directly. Add properties for your fields, adjust validation rules, and wire relationships in the mount/save methods.
Modal-based CRUD is the house style. The generated views rely on Bootstrap modals for forms rather than separate pages. Follow that pattern when extending — keep create/edit in modals and use the generated $model-style property for the currently-edited record, so validation and reset behavior stay consistent.
Customize the stubs before you scale out. If you need a house convention (extra columns, a $search field, soft-delete handling, a company_id constraint), publish and edit the stubs first, then generate. Editing stubs is far cheaper than editing every CRUD component afterward. This is the main extension point for making the scaffolding produce code that matches your app.
Layer authorization on top of the generated route. Add middleware or a policy check to the generated route (or in the component's mount) so only the right roles can reach the CRUD screen. The scaffolding generates the UI, not the access rules.
Integrate with migrations and policies you write yourself. ux:crud assumes the model and table exist; it doesn't generate migrations. Write the migration and model first, then scaffold the UI against them, and keep the field list in the component in sync with $fillable.
ux:crud Post will overwrite or collide with your edited component and route. Back up or version-control before regenerating, and prefer generating once and editing from there.App\Http\Livewire namespaces, $rules properties, emit/emitUp). On newer Laravel/Livewire 3 projects the generated components will likely need namespace and lifecycle adjustments. Check the package's composer constraints before installing on a fresh app.->withQueryString() as usual and point Livewire's pagination view at a Bootstrap view if the pager looks broken.auth. Confirm in routes/web.php and wrap them if the CRUD screen should be private.app/Models (or app/ on older Laravel) — a typo produces components that reference a class that doesn't exist.@livewireStyles/@livewireScripts in the layout? (4) is Bootstrap JS loaded? (5) does the model have the fields the view renders?mount and the sync in save, following the existing field-handling pattern in the generated file.How can I help you explore Laravel packages today?