quarkusio/quarkus · error · java.lang.IllegalArgumentException

@PermissionChecker annotation placed on the '%s' attribute '

Error message

@PermissionChecker annotation placed on the '%s' attribute 'value' must not be blank

What it means

Quarkus's security deployment step scans methods annotated with @PermissionChecker. Each such method must carry a non-blank permission name in the annotation's 'value' attribute, since this name is used both as the map key linking checkers to @PermissionsAllowed requirements and as the generated Permission class name. An empty or whitespace-only value is rejected at build time with this IllegalArgumentException.

Source

Thrown at extensions/security/deployment/src/main/java/io/quarkus/security/deployment/PermissionSecurityChecks.java:150

                    // so the checker method must be either public or package-private
                    throw new RuntimeException("Private method '" + toString(checkerMethod)
                            + "' cannot be annotated with the @PermissionChecker annotation");
                }
                if (Modifier.isStatic(checkerMethod.flags())) {
                    // checkers must be CDI bean member methods for now, so the checker method must not be static
                    throw new RuntimeException("Static method '" + toString(checkerMethod)
                            + "' cannot be annotated with the @PermissionChecker annotation");
                }
                boolean isReactive = isUniBoolean(checkerMethod);
                if (!isReactive && !isPrimitiveBoolean(checkerMethod)) {
                    throw new RuntimeException(("@PermissionChecker method '%s' has return type '%s', but only " +
                            "supported return types are 'boolean' and 'Uni<Boolean>'. ")
                            .formatted(toString(checkerMethod), checkerMethod.returnType().name()));
                }

                var permissionName = annotationInstance.value().asString();
                if (permissionName.isBlank()) {
                    throw new IllegalArgumentException(
                            "@PermissionChecker annotation placed on the '%s' attribute 'value' must not be blank"
                                    .formatted(toString(checkerMethod)));
                }
                boolean isBlocking = checkerMethod.hasDeclaredAnnotation(BLOCKING);
                if (isBlocking && isReactive) {
                    throw new IllegalArgumentException("""
                            @PermissionChecker annotation instance placed on the '%s' returns 'Uni<Boolean>' and is
                            annotated with the @Blocking annotation; if you need to block, please return 'boolean'
                            """.formatted(toString(checkerMethod)));
                }

                var generatedPermissionClassName = getGeneratedPermissionName(checkerMethod, permissionCheckerIndex++);
                var methodParamMappers = new MethodParameterMapper[checkerMethod.parametersCount()];
                var generatedPermissionConstructor = getGeneratedPermissionConstructor(checkerMethod, methodParamMappers);
                var checkerMetadata = new PermissionCheckerMetadata(checkerMethod, generatedPermissionClassName,
                        isReactive, generatedPermissionConstructor, methodParamMappers, isBlocking);

                if (permissionCheckers.containsKey(permissionName)) {

View on GitHub (pinned to e1c734241f)

Solutions

  1. Set a non-blank value on the @PermissionChecker annotation, e.g. @PermissionChecker(value="can-read")
  2. Ensure the constant/enum feeding the value is initialized to a real name, not an empty string
  3. If you intended no permission name, remove the @PermissionChecker annotation entirely

Example fix

// before
@PermissionChecker("")
boolean canRead(Book book) { return true; }

// after
@PermissionChecker("book:read")
boolean canRead(Book book) { return true; }
Defensive patterns

Strategy: validation

Validate before calling

// check before build
PermissionChecker pc = MyBean.class.getMethod("canRead", Book.class).getAnnotation(PermissionChecker.class);
if (pc == null || pc.value().isBlank()) throw new IllegalStateException("@PermissionChecker value must not be blank");

Prevention

When it happens

Trigger: Annotating a method with @PermissionChecker(value="") or @PermissionChecker(value=" ") (blank string) on a CDI bean method during application build.

Common situations: Copy-pasting @PermissionChecker from examples and forgetting to fill in the value; building the name dynamically and accidentally leaving an empty constant; refactoring that empties the string.

Related errors


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