korotovsky/csrf-validator-bundle
A Symfony bundle for CSRF protection that generates and validates anti-CSRF tokens for forms and state-changing requests, helping guard against cross-site request forgery with straightforward, framework-native configuration.
{Minimal steps, where to look first, first use case}
Read this first: it is not a Laravel package. korotovsky/csrf-validator-bundle is a Symfony bundle that validates CSRF tokens via doctrine annotations on controller actions. There is no service provider, no facade, no config/csrf.php, and no Laravel auto-discovery. A Laravel developer cannot composer require it and expect it to work in a Laravel app — the "day-to-day leverage" is therefore mostly as a reference implementation, or as a component you deliberately port.
Minimal path if you are evaluating it (30 minutes):
composer.json. Check the PHP and Symfony version constraints and whether it requires doctrine/annotations (removed from Symfony core in 7.0). If it pins Symfony 4/5-era versions or requires doctrine annotations, you already have your answer — it will not run on a modern stack.DependencyInjection extension. That listener is essentially the entire feature: it inspects the controller action for the annotation, extracts the token from the request, and throws/aborts on failure.TokenMismatchException-equivalent semantics, your client retry logic and error budgets will not match what Laravel clients expect.First use case. The realistic first use case for a Laravel developer is not installation — it is using the package as a small, readable reference for how declarative per-endpoint CSRF enforcement is shaped, and then deciding it is redundant. On Laravel, the equivalent first use case is: open app/Http/Middleware/VerifyCsrfToken.php, confirm the middleware is registered in the HTTP kernel (or via bootstrap/app.php in Laravel 11), and confirm you have no wildcard $except entries beyond api/* if you run stateless tokens there.
{Usage patterns, workflows, integration tips}
Declarative per-action enforcement is the pattern worth stealing. The package's core idea — annotate the controller action with the token requirement, let a listener validate before the controller runs — is a legitimate pattern for auditability: a reviewer can grep controller files and see exactly which actions are protected. If you have a security team demanding greppable evidence per endpoint, this is the shape to imitate.
In Laravel, the equivalent is the middleware, not an annotation. The day-to-day patterns:
VerifyCsrfToken runs on every web route. Do not reach for per-endpoint decorators; keep the default and narrow $except deliberately.$except and document why in the same commit. Never add a wildcard $except = ['*'] — that is the silent fail-open the package's unmaintained status warns against.@csrf in Blade or csrf_field(). For AJAX from your own JS, read the XSRF-TOKEN cookie and send X-XSRF-TOKEN; Axios does this automatically once the cookie is set./sanctum/csrf-cookie endpoint and let the framework's double-submit flow handle it. Do not build a parallel token mechanism._token, the X-CSRF-TOKEN header, or X-XSRF-TOKEN. If you have a custom client, prefer the header so tokens never appear in request bodies or application logs.If you are on Symfony and evaluating this bundle. The day-to-day pattern is: register the bundle, enable annotation reading, annotate the controller action, and rely on the listener to run before the controller. Test the happy path (valid token → controller runs) and the failure path (missing token → denied) with functional tests. Do not build this pattern on Laravel from a third-party dependency — implement it as a small middleware if you need it at all.
Porting pattern (only if you must). If the behavior is genuinely required and you cannot use VerifyCsrfToken, port rather than depend: a single middleware that reads a token, compares with hash_equals, and abort(419) on failure. Keep it under a hundred lines, own it, and write contract tests asserting denial on missing, malformed, and replayed tokens. That is a smaller long-term cost than tracking a 0-star, single-maintainer bundle.
Coverage audit workflow. The highest-leverage day-to-day use of the existence of this package is as a prompt: enumerate every state-changing route (POST/PUT/PATCH/DELETE), confirm each is under the web middleware group, and list any that are not. That audit gives the same evidence the package's annotations would, with no new dependency.
{Pitfalls, debugging, config quirks, extension points}
#[IsCsrfTokenValid] supersedes it.web group has the same session dependency — this is exactly why API routes use Sanctum or double-submit rather than session tokens.TokenMismatchException on CSRF failure. If a ported validator returns 403, 500, or a redirect instead, your clients' retry and re-authentication logic will not trigger correctly. Standardize on 419 and test it.X-CSRF-TOKEN header and scrub it from log context.$except is a footgun. Every entry is a permanent, invisible CSRF exemption that survives refactors. Review $except alongside any route changes, and prefer explicit HMAC/signature auth on the excluded endpoint over "no CSRF but still authenticated."$this->withoutMiddleware(VerifyCsrfToken::class) in feature tests that are not about CSRF, and write at least one test that does assert 419 on a missing token — that is the test that catches a regression in your protection.web group in app/Http/Kernel.php (or bootstrap/app.php), keep it thin, and let the framework do the rest.VerifyCsrfToken plus a route coverage audit.}How can I help you explore Laravel packages today?