如何通过 JOOQ 中的复合主键 select 多行?

How to select multiple rows by their composite primary keys in JOOQ?

我有一个带有复合主键的 table。我想查找包含一组主键的行。

我的table是:

create table test_tbl
(
    id_part_1 varchar(36) not null,
    id_part_2 varchar(36) not null,
    some_data text not null,
    constraint test_tbl_pkey
        primary key (id_part_1, id_part_2)
);

我的SQL查询是:

SELECT * FROM test_tbl
    WHERE (id_part_1, id_part_2) IN (('id_part_1_1', 'id_part_2_1'), ('id_part_1_2', 'id_part_2_2'));

那么,如何借助JOOQ实现这个查询呢?我没有生成 JOOQ Dao,我只有 JOOQ tables.

如何手动执行此操作

您可以使用 DSL.row() 将 SQL 查询直接转换为 jOOQ 以构建行值表达式,然后:

row(TEST_TBL.ID_PART_1, TEST_TBL.ID_PART_2).in(
  row("id_part_1_1", "id_part_2_1"),
  row("id_part_1_2", "id_part_2_2")
);

另见 jOOQ manual section about the IN predicate, degree > 1

使用可嵌入的密钥

或者,您可以从新的 jOOQ 3.14 <embeddablePrimaryKeys/> 功能提供的额外类型安全中获益,它允许您为所有主键及其引用外键生成记录类型。您的查询将显示为:

ctx.select()
   .from(TEST_TBL)
   .where(TEST_TBL.TEST_TBL_PKEY.in(
      new TestTblPkeyRecord("id_part_1_1", "id_part_2_1"),
      new TestTblPkeyRecord("id_part_1_2", "id_part_2_2")
   ))
   .fetch();

这会生成与您原来的查询相同的查询,但这样输入是安全的,而且您再也不会忘记一个键列。不仅是查询主键的时候,加入主键的时候也是!更改密钥将导致编译错误:

ctx.select()
   .from(TEST_TBL)
   .join(OTHER_TEST_TBL)
   .on(TEST_TBL.TEST_TBL_PKEY.eq(OTHER_TEST_TBL.TEST_TBL_PKEY.TEST_TBL_FKEY))
   .fetch();

或者 implicit join 看起来像这样:

ctx.select(OTHER_TEST_TBL.testTbl().fields(), OTHER_TEST_TBL.fields())
   .from(OTHER_TEST_TBL)
   .fetch();