JDBI是否接受UUID参数?

时间:2012-08-18 21:39:30

标签: java jdbc jdbi

使用SQL Object参数绑定时,JDBI是否可以与UUID参数一起使用?

我有一个这样的方法:

@SqlQuery("EXECUTE [MyProcedure] :myField")
MyDto myMethod(@Bind("myField") UUID myField);

绑定到接收如下参数的SQL Server存储过程:

@myField uniqueidentifier

执行时,抛出此异常:

! com.microsoft.sqlserver.jdbc.SQLServerException: The conversion from UNKNOWN to UNKNOWN is unsupported.
! at com.microsoft.sqlserver.jdbc.SQLServerException.makeFromDriverError(SQLServerException.java:190)
! at com.microsoft.sqlserver.jdbc.DataTypes.throwConversionError(DataTypes.java:1117)
! at com.microsoft.sqlserver.jdbc.SQLServerPreparedStatement.setObject(SQLServerPreparedStatement.java:991)

如果我将JDBI上的参数类型更改为String,并使用UUID对象中的toString()方法调用它,它可以工作:

@SqlQuery("EXECUTE [MyProcedure] :myField")
MyDto trash(@Bind("myField") String myField);

有没有办法编写我的DAO方法接受UUID参数并在绑定之前将它们转换为字符串?

1 个答案:

答案 0 :(得分:16)

JDBI仅为JDBC公开它们的类型公开基于显式类型的绑定。 JDBC不公开用于绑定的UUID类型,因此默认将其设置为Object。不幸的是,JDBC没有提供明确的UUID绑定机制,因此通过String可能是最便携的方式: - (

如果要在Java中将其绑定为UUID并在内部将其转换为String,则有两个路径。第一个,如果始终想要将UUID绑定为字符串,则使用ArgumentFactory,请参阅https://github.com/brianm/jdbi/blob/master/src/test/java/org/skife/jdbi/v2/sqlobject/TestRegisterArgumentFactory.java以获取示例。

第二种是,如果您只想在特定情况下执行此操作,请创建自定义活页夹,例如使用http://jdbi.org/sql_object_api_argument_binding/

使用ArgumentFactory实现从UUID到字符串的全局绑定的示例:

UUIDArgumentFactory.java:

public class UUIDArgumentFactory implements ArgumentFactory<UUID> {

    @Override
    public boolean accepts(Class<?> expectedType, Object value, StatementContext ctx) {
        return value instanceof UUID;
    }

    @Override
    public Argument build(Class<?> expectedType, UUID value, StatementContext ctx) {
        return new UUIDArgument(value);
    }
}

UUIDArgument.java:

public class UUIDArgument implements Argument {
    private final UUID value;

    public UUIDArgument(UUID value) {
        this.value = value;
    }

    @Override
    public void apply(int position, PreparedStatement statement, StatementContext ctx) throws SQLException {
        statement.setString(position, value.toString());
    }    
}

寄存器:

final DatabaseFactory factory = new DatabaseFactory(environment);
final Database db = factory.build(configuration.getDatabaseConfiguration(), "sqlserver");
db.registerArgumentFactory(new UUIDArgumentFactory());