{"record":{"id":"1adadb83605c4d6d","repo":"quarkusio/quarkus","slug":"build-item-class-must-be-leaf-final-types-s","errorCode":null,"errorMessage":"Build item class must be leaf (final) types: %s","messagePattern":"Build item class must be leaf \\(final\\) types: (.+?)","errorType":"exception","errorClass":"IllegalArgumentException","httpStatus":null,"severity":"error","filePath":"core/builder/src/main/java/io/quarkus/builder/item/BuildItem.java","lineNumber":22,"sourceCode":"\n/**\n * A build item which can be produced or consumed. Any item\n * which implements {@link AutoCloseable} will be automatically closed when the build\n * is completed, unless it is explicitly marked as a final build result in which case closure is\n * the responsibility of whomever invoked the build execution.\n * <p>\n * Resources should be fine-grained as possible, ideally describing only one aspect of the build process.\n */\npublic abstract class BuildItem {\n    BuildItem() {\n        final Class<? extends BuildItem> clazz = getClass();\n        if (clazz.getTypeParameters().length != 0) {\n            throw new IllegalArgumentException(\n                    \"A generic type is not allowed here; try creating a subclass with concrete type arguments instead: \"\n                            + getClass());\n        }\n        if (!Modifier.isFinal(clazz.getModifiers())) {\n            throw new IllegalArgumentException(\"Build item class must be leaf (final) types: \" + getClass());\n        }\n    }\n}\n","sourceCodeStart":4,"sourceCodeEnd":26,"githubUrl":"https://github.com/quarkusio/quarkus/blob/e1c734241f34c7919086ceb4c9262b4a58f6de44/core/builder/src/main/java/io/quarkus/builder/item/BuildItem.java#L4-L26","documentation":"BuildItem's constructor also requires every concrete build item class to be final (a leaf type). If getClass() reports a non-final class, it throws this IllegalArgumentException. Quarkus keys build steps on exact build item classes; subclassing an item would let one production be consumed as multiple item types, so the framework forbids it.","triggerScenarios":"Declaring `class MyBaseItem extends BuildItem` (non-final) and instantiating it or a subclass; extending an existing concrete build item to add fields instead of composing; instantiating an abstract-ish intermediate class that is not marked final.","commonSituations":"Inheritance-based reuse of build items when refactoring; attempts to specialize a framework-provided build item by subclassing; copy-pasted item classes missing the final modifier.","solutions":["Mark the build item class final; if you need shared fields, extract them into a plain value object the item holds.","Stop extending other BuildItems — define a new standalone final build item class instead.","If you need polymorphic consumption, use a shared payload type or multiple distinct build items rather than a subclass hierarchy.","Check any dynamically generated or proxied build item classes for the final modifier."],"exampleFix":"// before\npublic class MyItem extends BuildItem { ... }\n\n// after\npublic final class MyItem extends BuildItem { ... }","handlingStrategy":"type-guard","validationCode":"static void assertFinalBuildItems(String packageName) {\n    // e.g. via ClassGraph/Reflections scan in a unit test\n    // for each Class<?> c in package: assert Modifier.isFinal(c.getModifiers())\n}","typeGuard":"static boolean isLeafBuildItem(Class<?> clazz) {\n    return BuildItem.class.isAssignableFrom(clazz)\n        && Modifier.isFinal(clazz.getModifiers());\n}","tryCatchPattern":"try {\n    BuildItem item = createMyItem();\n} catch (IllegalArgumentException e) {\n    if (e.getMessage().startsWith(\"Build item class must be leaf\")) {\n        throw new IllegalStateException(\"Mark the build item final; do not subclass existing items\", e);\n    }\n    throw e;\n}","preventionTips":["Always declare BuildItem subclasses with the final modifier","Do not extend other BuildItems; compose payload objects instead","Add a unit test scanning the package for non-final BuildItem subclasses"],"tags":["quarkus","build-item","inheritance","api-misuse"],"backgroundTag":"build-item-must-be-final","analyzedSha":"e1c734241f34c7919086ceb4c9262b4a58f6de44","analyzedAt":"2026-09-05T17:01:29.979Z","contentChangedAt":"2026-09-05T17:01:29.979Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}