jOOQ:如何使用MySQL“BINARY”运算符创建选择查询?

时间:2014-05-05 15:18:58

标签: java mysql jooq

问题

如何使用jOOQ创建以下两个(等效的)MySQL语句中的任何一个?

SELECT * FROM `tbl` WHERE `col` = BINARY 'foobar   ';
SELECT * FROM `tbl` WHERE `col` = CAST('foobar   ' AS BINARY);

背景

我想比较任意字符串,可能包括(重要的)尾随空格。不幸的是,MySQL与=进行比较时默认忽略尾随空格。据我所见this question,只能使用the BINARY operator in MySQL进行此类比较。

我已经尝试过了

我尝试使用DSL.cast() method in jOOQ

myDb.selectFrom(TBL)
  .where(TBL.COL
     .eq(DSL.cast("foobar   ", MySQLDataType.BINARY)))
  .fetchOne();
// → compiler error: “The method eq(String) in the type Field<String> is not
//   applicable for the arguments (Field<byte[]>)”

myDb.selectFrom(TBL)
  .where(DSL.cast(TBL.COL, MySQLDataType.BINARY)
     .eq("foobar   "))
  .fetchOne();
// → compiler error: “The method eq(byte[]) in the type Field<byte[]> is not
//   applicable for the arguments”

myDb.selectFrom(TBL)
  .where(DSL.cast(TBL.COL, MySQLDataType.BINARY)
     .eq(DSL.cast("foobar   ", MySQLDataType.BINARY)))
  .fetchOne();
// → runtime error: “org.jooq.exception.DataTypeException: Cannot convert from
//   foobar    (class java.lang.String) to class [B”

解决方法

我的最后一招是将我的查询更改为使用LIKE而不是=。不过,那将是一个黑客,因为我必须首先在我的字符串中引用任何通配符,我也会面临性能损失: - |

1 个答案:

答案 0 :(得分:4)

你的第三个例子应该有用,可能是一个bug,我注册为Issue #3255

myDb.selectFrom(TBL)
  .where(DSL.cast(TBL.COL, MySQLDataType.BINARY)
     .eq(DSL.cast("foobar   ", MySQLDataType.BINARY)))
  .fetchOne();

与往常一样,如果您在jOOQ中缺少某个功能,或者您遇到了错误,则可以使用此处记录的纯SQL:

解决问题的一个例子在你的案例中:

myDb.selectFrom(TBL)
  .where(TBL.COL
     .eq(DSL.field("BINARY ?", String.class, "foobar   ")))
  .fetchOne();

或者:

myDb.selectFrom(TBL)
  .where("{0} = BINARY {1}", TBL.COL, DSL.val("foobar   "))
  .fetchOne();