{"record":{"id":"484b4cbcc19c46f6","repo":"hibernate/hibernate-orm","slug":"enum-literal-cannot-be-cast-to-bigdecimal","errorCode":null,"errorMessage":"Enum literal cannot be cast to BigDecimal","messagePattern":"Enum literal cannot be cast to BigDecimal","errorType":"exception","errorClass":"UnsupportedOperationException","httpStatus":null,"severity":"error","filePath":"hibernate-core/src/main/java/org/hibernate/query/sqm/tree/spi/expression/SqmEnumLiteral.java","lineNumber":166,"sourceCode":"\t\treturn nodeBuilder().literal( ordinalValue() );\n\t}\n\n\t@Nonnull\n\t@Override\n\tpublic SqmExpression<Float> asFloat() {\n\t\treturn nodeBuilder().literal( ordinalValue().floatValue() );\n\t}\n\n\t@Nonnull\n\t@Override\n\tpublic SqmExpression<Double> asDouble() {\n\t\treturn nodeBuilder().literal( ordinalValue().doubleValue() );\n\t}\n\n\t@Nonnull\n\t@Override\n\tpublic SqmExpression<BigDecimal> asBigDecimal() {\n\t\tthrow new UnsupportedOperationException( \"Enum literal cannot be cast to BigDecimal\" );\n\t}\n\n\t@Nonnull\n\t@Override\n\tpublic SqmExpression<BigInteger> asBigInteger() {\n\t\tthrow new UnsupportedOperationException( \"Enum literal cannot be cast to BigInteger\" );\n\t}\n\n\t@Nonnull\n\t@Override\n\tpublic SqmExpression<String> asString() {\n\t\treturn nodeBuilder().literal( getExpressibleJavaType().toName( getEnumValue() ) );\n\t}\n\n\t@Override\n\tpublic <X> X accept(SemanticQueryWalker<X> walker) {\n\t\treturn walker.visitEnumLiteral( this );\n\t}","sourceCodeStart":148,"sourceCodeEnd":184,"githubUrl":"https://github.com/hibernate/hibernate-orm/blob/fad1729dce015f908198d57a8d80274a30f905a5/hibernate-core/src/main/java/org/hibernate/query/sqm/tree/spi/expression/SqmEnumLiteral.java#L148-L184","documentation":"Thrown by SqmEnumLiteral.asBigDecimal(). In Hibernate's SQM (semantic query model) tree, an enum literal can be converted to Integer/Long/Float/Double (through the enum's ordinal) or to String (through its name), but conversion to BigDecimal is deliberately not implemented because an enum constant has no decimal value, so the override always throws UnsupportedOperationException.","triggerScenarios":"Calling asBigDecimal() on an expression Hibernate resolved to an SqmEnumLiteral: criteria code like builder.literal(MyEnum.ACTIVE).asBigDecimal(), generic numeric-coercion helpers that call asBigDecimal()/asBigInteger() on every SqmExpression, or queries that force an enum literal into a BigDecimal-typed position (comparing or casting it against a BigDecimal operand).","commonSituations":"Dynamic query builders that apply numeric coercion uniformly to all operands; arithmetic between an enum attribute and BigDecimal values; refactors where a formerly numeric column became an enum; porting queries from a dialect where implicit enum-to-number casts worked.","solutions":["Convert through a supported type first: call asInteger() (ordinal) or asString() (name), then cast - e.g. asInteger().cast(BigDecimal.class).","Compare against the enum's ordinal or name instead of coercing the enum literal to BigDecimal.","If the enum encodes a decimal magnitude, map the attribute with an AttributeConverter to BigDecimal and query that representation instead of the enum literal.","In generic coercion code, skip asBigDecimal() when the expression is an SqmEnumLiteral (instanceof check)."],"exampleFix":"// before\nSqmExpression<BigDecimal> v = enumLiteralExpr.asBigDecimal(); // UnsupportedOperationException\n\n// after - go via the ordinal, then cast\nSqmExpression<BigDecimal> v = enumLiteralExpr.asInteger().cast( BigDecimal.class );","handlingStrategy":"type-guard","validationCode":null,"typeGuard":"static boolean isEnumLiteral(SqmExpression<?> e) {\n    return e instanceof org.hibernate.query.sqm.tree.spi.expression.SqmEnumLiteral;\n}","tryCatchPattern":"try {\n    return expr.asBigDecimal();\n} catch (UnsupportedOperationException e) {\n    // enum literal: fall back to an ordinal-based cast\n    return expr.asInteger().cast( BigDecimal.class );\n}","preventionTips":["Never call asBigDecimal()/asBigInteger() on enum-typed expressions; route through asInteger() (ordinal) or asString() (name) first.","In generic numeric-coercion helpers, branch on SqmEnumLiteral before choosing a conversion.","Prefer numeric attributes over enum literals when the query needs decimal arithmetic."],"tags":["hibernate","sqm","enum","bigdecimal","cast","criteria-api"],"backgroundTag":"unsupported-cast-operation","analyzedSha":"fad1729dce015f908198d57a8d80274a30f905a5","analyzedAt":"2026-08-22T04:13:57.527Z","schemaVersion":2},"datasetVersion":"2026-08-22T09:17:25.309Z"}