jOOQ记录中的错误字段

时间:2017-01-02 15:49:10

标签: java sql jooq

我有3个表ABC,它们是继承链的一部分:

  A
 / \
B   C

看起来像:

A(row_id)
B(row_id, a_row_id REFERENCES A(row_id))
C(row_id, a_row_id REFERENCES A(row_id))

请注意,列名称相同(a_row_id

现在,我通过以下方式获取RecordB的{​​{1}}:

C

我加入了ctx.select() .from( Tables.A .leftOuterJoin(Tables.B).onKey() .leftOuterJoin(Tables.C).onKey() ) .where(someCondition) .fetch() B,因为我(此时)并不知道我正在寻找哪一个。

但是,当我知道我需要获取C并执行此操作时:

B

我得到ctx.select() .from( Tables.A .leftOuterJoin(Tables.B).onKey() ) .where(someCondition) .fetch() ,如果我Record,我会record.field(Tables.B.A_ROW_ID).toString(),如果我"b.a_row_id",我会得到预期值。

但是,如果我record.getValue(Tables.B.A_ROW_ID),我会record.field(Tables.C.A_ROW_ID).toString()"b.a_row_id"会给我预期的record.getValue(Tables.C.A_ROW_ID)值。

我认为这是因为引用父表的列名是相同的。

jOOQ是否仅使用表的field_name(而不是完全限定的“table.field_name”),如果这是连接中唯一的表?

对此的任何帮助将不胜感激。

2 个答案:

答案 0 :(得分:1)

Record.field(Field)Record.field(Name)Record.field(String)的语义都遵循相同,一致的逻辑:

在SQL中,记录的列有一个名称。如果该名称源自表/视图(在模式中(在目录中)),则该名称可以是限定的,但这是可选的。不合格的列也非常好,例如当:

  • 对列进行别名
  • 创建表达式,例如col + 1
  • 如果列不合格,请使用JOIN .. USING
  • 使用派生表(可能有表名,但肯定不是架构/目录)
  • SELECT *与特定于供应商的列发布运算符一起使用,例如PIVOTMODELMATCH_RECOGNIZE

正如您所看到的,从语法角度来看,具有限定列名称是例外,而不是规则。因此,Record.field(Field)的最合理和最有用的实现是:

  • 在记录中找到完全匹配(完全限定列名称)
  • 如果失败,请在记录内找到近似匹配(不合格的列名称)
  • 如果那是"模棱两可的" (因为顶层选择允许这种歧义),那么:

因此,您观察到的行为是正确的。

答案 1 :(得分:1)

Lukas已经回答了主要问题,但我只是想告诉大家,jOOQ最终正在运行一个SQL语句。它的安全性和缓存是有限的,但它仍然是一个SQL语句。如果你开始记录,你可以看到SQL本身 如果您希望返回动态记录并希望列为X,则可以始终执行.as(" X"),以便更容易地读取数据。