quarkusio/quarkus · error · IllegalArgumentException

The use of interfaces as the generic type of Lists fields /

Error message

The use of interfaces as the generic type of Lists fields / methods is not allowed. Offending field is ' + member.name() + ' of class ' + member.declaringClass().name().toString() + '

What it means

YamlListObjectHandler resolves the concrete element class of a List<...> field/method so it can instantiate elements when binding YAML config. Interfaces cannot be instantiated, so validation rejects them outright with IllegalArgumentException.

Source

Thrown at extensions/spring-boot-properties/deployment/src/main/java/io/quarkus/spring/boot/properties/deployment/YamlListObjectHandler.java:201

                    mc.public_();
                    mc.body(b -> {
                        LocalVar resultHandle = b.localVar("resultHandle", b.new_(ConstructorDesc.of(HashMap.class)));
                        for (Map.Entry<String, String> entry : fieldNameMap.entrySet().stream()
                                .sorted(Map.Entry.comparingByKey()).toList()) {
                            b.invokeVirtual(
                                    MethodDesc.of(HashMap.class, "put", Object.class, Object.class, Object.class),
                                    resultHandle, Const.of(entry.getKey()), Const.of(entry.getValue()));
                        }
                        b.return_(resultHandle);
                    });
                });
            }
        });
    }

    private void validateClass(ClassInfo classInfo, Member member) {
        if (Modifier.isInterface(classInfo.flags())) {
            throw new IllegalArgumentException(
                    "The use of interfaces as the generic type of Lists fields / methods is not allowed. Offending field is '"
                            + member.name() + "' of class '" + member.declaringClass().name().toString() + "'");
        }
        if (!classInfo.hasNoArgsConstructor()) {
            throw new IllegalArgumentException(
                    String.format("Class '%s' which is used as %s in class '%s' must have a no-args constructor", classInfo,
                            member.phraseUsage(), member.declaringClass().name().toString()));
        }
        if (!Modifier.isPublic(classInfo.flags())) {
            throw new IllegalArgumentException(
                    String.format("Class '%s' which is used as %s in class '%s' must be a public class", classInfo,
                            member.phraseUsage(), member.declaringClass().name().toString()));
        }
    }

    private ClassInfo validateType(Type type) {
        if (type.kind() != Type.Kind.PARAMETERIZED_TYPE) {
            throw new IllegalArgumentException(ILLEGAL_ARGUMENT_MESSAGE);

View on GitHub (pinned to e1c734241f)

Solutions

  1. Change the list element type from the interface to a concrete class with a public no-args constructor
  2. Introduce a concrete base/default implementation class and use List<Impl> in the config
  3. Move polymorphism out of the config binding (bind concrete class, expose interface separately)

Example fix

// before
List<Handler> handlers();
// after
List<DefaultHandler> handlers();
Defensive patterns

Strategy: type-guard

Validate before calling

static <T> void checkListElementType(List<T> listField, Class<?> cfg) {
    // element type must be a concrete class
}

Type guard

boolean isConcreteListElement(Type t) {
    return t instanceof Class<?> c && !c.isInterface() && !c.isAnnotation();
}

Try / catch

catch (IllegalArgumentException e) { if (e.getMessage().contains("not allowed")) { /* use concrete element class */ } throw e; }

Prevention

When it happens

Trigger: A @ConfigProperties class/interface (processed via quarkus-config-yaml list-of-object support) declares a field or method of type List<SomeInterface> where SomeInterface is an interface, not a class.

Common situations: Modeling config lists against an abstraction (List<Handler> where Handler is an interface) carried over from Spring Boot style configuration.

Related errors


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