SonarSource/sonarqube · error · IllegalStateException
Constructor annotations missing in:
Error message
Constructor annotations missing in:
What it means
PriorityBeanFactory overrides Spring's instantiateBean to fail fast when a bean class has more than one constructor but no explicit constructor annotation (@Autowired/@Inject) or XML-specified constructor resolution. With multiple constructors and no annotations, Spring would silently pick the no-arg constructor, so SonarQube refuses to guess and throws IllegalStateException naming the offending class.
Source
Thrown at sonar-core/src/main/java/org/sonar/core/platform/PriorityBeanFactory.java:109
while (factory != null) {
if (factory.containsBeanDefinition(beanName)) {
return i;
}
factory = (DefaultListableBeanFactory) factory.getParentBeanFactory();
i++;
}
return null;
}
/**
* A common mistake when migrating from Pico Container to Spring is to forget to add @Inject or @Autowire annotations to classes that have multiple constructors.
* Spring will fail if there is no default no-arg constructor, but it will silently use the no-arg constructor if there is one, never calling the other constructors.
* We override this method to fail fast if a class has multiple constructors.
*/
@Override
protected BeanWrapper instantiateBean(String beanName, RootBeanDefinition mbd) {
if (mbd.hasBeanClass() && mbd.getBeanClass().getConstructors().length > 1) {
throw new IllegalStateException("Constructor annotations missing in: " + mbd.getBeanClass());
}
return super.instantiateBean(beanName, mbd);
}
private static class Bean {
private final String name;
private final Object instance;
public Bean(String name, Object instance) {
this.name = name;
this.instance = instance;
}
public String getName() {
return name;
}
public Object getInstance() {View on GitHub (pinned to 184c821202)
Solutions
- Annotate the intended constructor with @org.springframework.beans.factory.annotation.Autowired (or @Inject).
- Delete the extra constructor so the class has exactly one constructor.
- Register the bean with an explicit constructor-arg definition so instantiateBean's multi-constructor check is not hit.
Example fix
// before
class MyService {
MyService(Database db) { ... }
MyService() { ... } // second ctor -> IllegalStateException
}
// after
class MyService {
@Autowired
MyService(Database db) { ... }
} Defensive patterns
Strategy: type-guard
Validate before calling
static boolean isContainerSafe(Class<?> beanClass) {
return beanClass.getConstructors().length <= 1
|| Arrays.stream(beanClass.getConstructors())
.anyMatch(c -> c.isAnnotationPresent(Autowired.class) || c.isAnnotationPresent(Inject.class));
} Type guard
boolean hasSingleOrAnnotatedConstructor(Class<?> c) {
java.lang.reflect.Constructor<?>[] ctors = c.getConstructors();
return ctors.length == 1 || Arrays.stream(ctors).anyMatch(k -> k.isAnnotationPresent(Autowired.class));
} Try / catch
try {
container.add(MyService.class);
} catch (IllegalStateException e) {
// e.getMessage() names the offending class: add @Autowired or remove extra constructor
} Prevention
- Give Spring components exactly one constructor (use final fields + constructor injection).
- Never keep old constructors around 'for tests' — instantiate test fixtures directly.
- Lint for multi-constructor components registered in SonarQube containers.
When it happens
Trigger: Registering a class with 2+ constructors (and no @Autowired on any constructor, no no-arg-only case handled as intended) into a SonarQube Spring container; the bean is instantiated without an explicit constructor definition.
Common situations: Adding a second constructor (e.g. for tests) to a component without adding @Autowired to the intended one; refactoring a component's constructor while keeping the old one for compatibility.
Understand the failure class
Background: "Invalid state transition" errors: "status must be X, actually Y", "already rejected/charging/uninstalled", "cannot ... while running" — what they mean when a library rejects your call — this error's family across 31 libraries.
Related errors
AI-assisted analysis of SonarSource/sonarqube@184c821202 (2026-09-09).
Data as JSON: /api/errors/9b39d56843a53e90.
Report an issue: GitHub.