{"record":{"id":"a85340492df966ef","repo":"tursodatabase/turso","slug":"unsupported-object-type-in-setobject-type","errorCode":null,"errorMessage":"Unsupported object type in setObject: {type}","messagePattern":"Unsupported object type in setObject: (.+?)","errorType":"exception","errorClass":"SQLException","httpStatus":null,"severity":"error","filePath":"bindings/java/src/main/java/tech/turso/jdbc4/JDBC4PreparedStatement.java","lineNumber":315,"sourceCode":"    } else if (x instanceof byte[]) {\n      setBytes(parameterIndex, (byte[]) x);\n    } else if (x instanceof Timestamp) {\n      setTimestamp(parameterIndex, (Timestamp) x);\n    } else if (x instanceof Date) {\n      setDate(parameterIndex, (Date) x);\n    } else if (x instanceof Time) {\n      setTime(parameterIndex, (Time) x);\n    } else if (x instanceof BigDecimal) {\n      setBigDecimal(parameterIndex, (BigDecimal) x);\n    } else if (x instanceof Blob\n        || x instanceof Clob\n        || x instanceof InputStream\n        || x instanceof Reader) {\n      throw new SQLException(\n          \"setObject does not yet support LOB or Stream types because the corresponding set methods are unimplemented. Type found: \"\n              + x.getClass().getName());\n    } else {\n      throw new SQLException(\"Unsupported object type in setObject: \" + x.getClass().getName());\n    }\n  }\n\n  @Override\n  public boolean execute() throws SQLException {\n    return execute(currentBatchParams);\n  }\n\n  /** This helper method runs the statement using the provided parameter values. */\n  private boolean execute(Object[] params) throws SQLException {\n    // TODO: check whether this is sufficient\n    requireNonNull(statement);\n    bindParams(params);\n    boolean result = statement.execute();\n    updateCount = statement.changes();\n    return result;\n  }\n","sourceCodeStart":297,"sourceCodeEnd":333,"githubUrl":"https://github.com/tursodatabase/turso/blob/bad083fafbefdeae9a42ec19bdaaad8918dcf411/bindings/java/src/main/java/tech/turso/jdbc4/JDBC4PreparedStatement.java#L297-L333","documentation":"The catch-all else of setObject(int, Object): the value's runtime class matches none of the supported types (null, String, Integer, Long, Boolean, Double, Float, Byte, Short, byte[], Timestamp, java.sql.Date, Time, BigDecimal). Common Java types that land here include java.time LocalDate/LocalDateTime/Instant, UUID, BigInteger, enums, and any custom value object. The message embeds the exact class that failed.","triggerScenarios":"ps.setObject(1, LocalDate.now()); ps.setObject(1, UUID.randomUUID()); ps.setObject(1, MyEnum.A); ps.setObject(1, BigInteger.TEN); any POJO passed as a parameter.","commonSituations":"Modern java.time code against a JDBC4-era driver that only knows java.sql date/time classes; ORMs storing UUID primary keys as objects; migrating from PostgreSQL's permissive setObject which accepts nearly anything.","solutions":["Convert before binding: LocalDate -> java.sql.Date.valueOf(ld); Instant -> Timestamp.from(i); LocalDateTime -> Timestamp.valueOf(ldt); UUID -> u.toString() (or 16-byte array); enum -> name().","Use the typed setters (setString, setLong, ...) instead of setObject where possible.","In generic layers, register a converter per domain type and fail fast on unmapped classes."],"exampleFix":"// before\nps.setObject(1, LocalDate.of(2024, 1, 31)); // throws\n\n// after\nps.setObject(1, java.sql.Date.valueOf(LocalDate.of(2024, 1, 31)));","handlingStrategy":"type-guard","validationCode":"Object v = toSupportedType(raw); // LocalDate->Date, Instant->Timestamp, UUID->String, enum->name()\nif (v != null && !isSetObjectSupported(v)) {\n    throw new IllegalArgumentException(\"Unsupported bind type: \" + v.getClass().getName());\n}\nps.setObject(i, v);","typeGuard":"static boolean isSetObjectSupported(Object x) {\n    return x == null || x instanceof String || x instanceof Boolean\n        || x instanceof Byte || x instanceof Short || x instanceof Integer\n        || x instanceof Long || x instanceof Float || x instanceof Double\n        || x instanceof byte[] || x instanceof java.sql.Timestamp\n        || x instanceof java.sql.Date || x instanceof java.sql.Time\n        || x instanceof java.math.BigDecimal;\n}","tryCatchPattern":"catch (SQLException e) {\n    if (e.getMessage() != null && e.getMessage().startsWith(\"Unsupported object type in setObject\")) {\n        // map the named class to a supported type (java.time -> java.sql, UUID -> String) and retry\n    }\n    throw e;\n}","preventionTips":["Convert java.time values to java.sql types at your persistence boundary; never rely on setObject pass-through.","Keep UUID and enum encodings (TEXT vs byte[]) explicit and consistent.","Write one exhaustive binder switch over types so new types fail in tests, not production."],"tags":["jdbc","setobject","type-conversion","java-time","uuid"],"backgroundTag":"unsupported-type-conversion","analyzedSha":"bad083fafbefdeae9a42ec19bdaaad8918dcf411","analyzedAt":"2026-08-16T23:12:11.798Z","schemaVersion":2},"datasetVersion":"2026-08-17T04:17:16.089Z"}