quarkusio/quarkus · error · java.lang.RuntimeException
Found @PermissionChecker annotation instances that authorize
Error message
Found @PermissionChecker annotation instances that authorize the '%s' permissions, however
no @PermissionsAllowed annotation instance requires these permissions
What it means
One or more @PermissionChecker methods were registered, but no method in the application requires the permissions they authorize via @PermissionsAllowed. Unused permission checkers indicate a wiring mistake (or dead code) and are rejected at build time; this variant fires when more than one checker is unmatched.
Source
Thrown at extensions/security/deployment/src/main/java/io/quarkus/security/deployment/PermissionSecurityChecks.java:416
var constructor = clazz.constructors().get(0);
// first constructor parameter must be permission name
if (constructor.parametersCount() == 0 || !STRING.equals(constructor.parameterType(0).name())) {
throw new RuntimeException(
String.format("Permission constructor '%s' first argument must be '%s'",
clazz.name().toString(), String.class.getName()));
}
// rest of validation needs to be done for computed classes only and per each secured method
// therefore we do it later
// cache validation result
classSignatureToConstructor.put(key.classSignature(), constructor);
}
}
}
}
if (!permissionCheckers.isEmpty()) {
if (permissionCheckers.size() > 1) {
throw new RuntimeException("""
Found @PermissionChecker annotation instances that authorize the '%s' permissions, however
no @PermissionsAllowed annotation instance requires these permissions
""".formatted(String.join(",", permissionCheckers.values())));
} else {
throw new RuntimeException("""
Found @PermissionChecker annotation instance that authorize the '%s' permission, however
no @PermissionsAllowed annotation instance requires this permission
""".formatted(permissionCheckers.values().iterator().next()));
}
}
return this;
}
PermissionSecurityChecksBuilder gatherPermissionsAllowedAnnotations(
Map<MethodInfo, AnnotationInstance> alreadyCheckedMethods,
Map<ClassInfo, AnnotationInstance> alreadyCheckedClasses,
List<AnnotationInstance> additionalClassInstances,
Predicate<MethodInfo> hasAdditionalSecurityAnnotations) {View on GitHub (pinned to e1c734241f)
Solutions
- Add @PermissionsAllowed("<name>") on the resource methods that should require each checker's permission
- Fix typos so the permission name matches exactly between checker and requirement
- Remove the now-unused @PermissionChecker methods
Example fix
// before
@PermissionChecker("book:read") boolean canRead(...) {...}
// (no @PermissionsAllowed anywhere)
// after
@PermissionChecker("book:read") boolean canRead(...) {...}
// in the resource:
@PermissionsAllowed("book:read")
public Book get(Long id) {...} Defensive patterns
Strategy: validation
Validate before calling
// every checker value must appear in some @PermissionsAllowed
Set<String> required = scanForPermissionsAllowedValues();
Set<String> provided = scanForPermissionCheckerValues();
Set<String> unmatched = new HashSet<>(provided); unmatched.removeAll(required);
if (unmatched.size() > 1) throw new IllegalStateException("Unmatched checkers: " + unmatched); Prevention
- Add @PermissionsAllowed in the same commit as new @PermissionChecker methods
- Keep checkers and their secured endpoints in the same module
- Grep for permission-name typos in CI
When it happens
Trigger: Declaring two or more @PermissionChecker methods whose permission values never appear in any @PermissionsAllowed annotation on endpoints/methods — detected in validatePermissionClasses after gathering all required permission keys.
Common situations: Removing/refactoring the secured endpoints (or their @PermissionsAllowed) while leaving the checkers; typos in permission names so the sets don't intersect; checkers in a library module whose consumers never use them.
Related errors
- Found @PermissionChecker annotation instance that authorize
- @PermissionChecker annotation placed on the '%s' attribute '
- @PermissionChecker annotation instance placed on the '%s' re
- Detected two @PermissionChecker annotations with same value
- @PermissionChecker method '%s' declares checked exceptions w
AI-assisted analysis of quarkusio/quarkus@e1c734241f (2026-09-05).
Data as JSON: /api/errors/89fee9afba7ff904.
Report an issue: GitHub.