quarkusio/quarkus · error · IllegalStateException

CSRFFilter should have set the attribute {csrfFormFieldName}

Error message

CSRFFilter should have set the attribute {csrfFormFieldName}, but it is null

What it means

CsrfTokenParameterProvider.getToken() reads the CSRF token from the RoutingContext, where the CSRFFilter was expected to have stored it before form parameter resolution. If the attribute is absent (null), the framework cannot bind the CSRF form field, so an IllegalStateException is thrown at request time.

Source

Thrown at extensions/resteasy-reactive/rest-csrf/runtime/src/main/java/io/quarkus/csrf/reactive/runtime/CsrfTokenParameterProvider.java:43

    private final String csrfHeaderName;

    public CsrfTokenParameterProvider(RestCsrfConfigHolder configHolder) {
        RestCsrfConfig config = configHolder.getConfig();
        this.csrfFormFieldName = config.formFieldName();
        this.csrfCookieName = config.cookieName();
        this.csrfHeaderName = config.tokenHeaderName();
    }

    /**
     * Gets the CSRF token value.
     *
     * @throws IllegalStateException if the {@link RoutingContext} does not contain a CSRF token value.
     */
    public String getToken() {
        String token = (String) context.get(CSRF_TOKEN_KEY);

        if (token == null) {
            throw new IllegalStateException(
                    "CSRFFilter should have set the attribute " + csrfFormFieldName + ", but it is null");
        }

        return token;
    }

    /**
     * Gets the name of the form parameter that is to contain the value returned by {@link #getToken()}.
     */
    public String getParameterName() {
        return csrfFormFieldName;
    }

    /**
     * Gets the CSRF cookie name.
     */
    public String getCookieName() {
        return csrfCookieName;

View on GitHub (pinned to e1c734241f)

Solutions

  1. Ensure `quarkus-rest-csrf` is present and CSRF protection enabled (default) so CsrfReactiveFilter runs on the request path
  2. Verify the request actually passes through the CSRF filter (check `quarkus.rest-csrf.cookie-name`/create-token-path config and route ordering)
  3. Include a valid CSRF token field in the form post; fetch it from the CsrfController/token endpoint rendered with the form
  4. If you don't need CSRF binding, remove the CsrfTokenParameterProvider usage / @RestForm CSRF field from that endpoint

Example fix

// before
<form method="post">
  <input name="field1">
</form>
// after
<form method="post">
  <input type="hidden" name="csrf-token" th:value="{csrfToken}">
  <input name="field1">
</form>
Defensive patterns

Strategy: try-catch

Validate before calling

String token = routingContext.get(CSRF_TOKEN_KEY); if (token == null) { LOG.warn("CSRF token not set by filter — ensure CsrfReactiveFilter ran on this route"); }

Try / catch

try { String csrfToken = csrfTokenParameterProvider.getToken(); renderForm(csrfToken); } catch (IllegalStateException e) { LOG.error("CSRF filter did not populate token — check quarkus-rest-csrf setup/route ordering", e); throw e; }

Prevention

When it happens

Trigger: Injecting/using `CsrfTokenParameterProvider` (e.g. via @RestForm CSRF binding) on a request that never passed through CsrfReactiveFilter — e.g. the route is outside the CSRF filter's protection, or CSRF protection is disabled/misconfigured while form binding still expects the token.

Common situations: Calling an endpoint with `@RestForm` CSRF token binding without including the filter (quarkus-rest-csrf config or path exclusion mistakes); a GET/other route pattern that bypasses CsrfReactiveFilter; custom routing registered before the CSRF filter.

Related errors


AI-assisted analysis of quarkusio/quarkus@e1c734241f (2026-09-05). Data as JSON: /api/errors/6f20a41a024211b4. Report an issue: GitHub.