Version 8 rebuilds the package around a fluent, Laravel-native builder. The v7 API was one 700-line Toaster class; v8 is three purpose-built builders, five composable concerns, three enums, and a test suite that covers behaviour rather than the shape of the code.
Your existing code keeps working. alert()->success(), toast() and confirmDelete() display immediately the way they always did. A survey of five real applications using this package found Alert::success() in 52 files and none of the changed signatures anywhere.
Highlights
AlertBuilder,ToastBuilderandInputBuilder, each with its own defaults- Full SweetAlert2 coverage — deny buttons, progress steps, every input type, pre-confirm and pre-deny routes, per-alert themes, animations
- PHP 8.3 enums (
AlertType,InputType,Position) with IDE completion when()/unless()andmacro()on every builder@sweetAlertBlade directive, replacing@include('sweetalert::alert')- Livewire v4 trait and Inertia middleware
- Laravel Boost guideline and skill, so AI assistants write v8 rather than v7
- VitePress documentation, Pest suite with architecture tests, Pint, PHPStan level 5
Guarded actions
A dialog that can only ask a question is half a feature. v8 acts on the answer with no JavaScript on your side:
<a href="{{ route('posts.destroy', $post) }}" data-confirm-delete>Delete</a>
<a href="{{ route('posts.publish', $post) }}" data-confirm data-confirm-method="PUT">Publish</a>
<form method="POST" action="{{ route('orders.refund', $order) }}" data-confirm>
@csrf
<button type="submit">Refund</button>
</form>Override the copy per element with data-confirm-title, -text, -icon, -button and -cancel. On confirm the package builds a form with the CSRF token and the right method and submits it.
data-confirm-delete worked this way before, but only on the request where confirmDelete() had been flashed — on any other render the link was an ordinary link and the browser opened the destroy URL with a GET. The listener is always present now. Closes #174 and #183.
SweetAlert2 is fetched on the first click, so a page carrying only a guarded link ships no JavaScript until someone uses it. If it cannot be fetched, the browser's own confirm() is used — a guarded delete never goes through unasked because a CDN was down.
submitTo()
The answer reaches your server instead of vanishing when the dialog closes:
Alert::input('What should we call you?')
->submitTo(route('profile.name'), 'POST', 'name')
->flash();Closes #147.
topLayer()
Puts a popup in the browser's top layer, above any z-index — the answer to a toast rendering behind a navbar. Closes #158.
Upgrading
php artisan alert:upgrade --dry-runThe command rewrites the two methods whose signatures changed, the container binding, the moved SessionStore, the Blade include, and the config keys that break theming. It reads your code with PHP's own tokeniser rather than searching for text, so a ->html() call on an unrelated object, or the old binding name inside a comment, is reported rather than edited. Nothing is written without confirmation and vendor/ is never touched.
Run against five real third-party applications it scanned 1,065 files and rewrote 16, with no false positives and no broken syntax.
It exists because of html() specifically. v7's signature was html($title, $code, $icon); v8's is html($html). PHP ignores surplus arguments, so an un-migrated call does not error — it just stops working.
Two config keys to check if you published the config under v7: background, width and padding are now null by default. SweetAlert2 applies each as an inline style that beats every stylesheet, so a background value means no theme can ever change the popup colour. alert:upgrade fixes this for you.
Requirements
PHP 8.3+ and Laravel 11, 12 or 13.
Full upgrade path: https://realrashid.github.io/sweet-alert/guide/upgrade-guide