【问题标题】:jOOQ - how to use .whereNotExists() properly?jOOQ - 如何正确使用 .whereNotExists()?
【发布时间】:2018-07-11 20:03:30
【问题描述】:

我想坚持每日收盘实体,代表股票的收盘价。

public class DailyData {
    private Long       id;
    private String     ticker;
    private BigDecimal open;
    private BigDecimal high;
    private BigDecimal low;
    private BigDecimal close;
    private Timestamp  date;
    //getters, setters
}

由于数据提供者的 API 有限,我可能会在某些日期得到重复的条目(例如,如果我只需要两天,我仍然需要请求一个月的数据)。显然,我只想每个日期有一条记录,因此不应保留数据库中已经存在的任何日期。

这可能已经回答了here,但我在实践中遇到了麻烦。特别是,我不明白如何传递要持久的实际值。这改编自链接中的示例:

Param<Integer> myId = param("date", Timestamp.class);
create.insertInto(DATA, DATA.TICKER, DATA.OPEN, DATA.HIGH, DATA.LOW, DATA.CLOSE, DATA.DATE)
            .select(
                    select(
                            date,
                            param("ticker", DATA.TICKER.getType()),
                            param("open", DATA.OPEN.getType()),
                            param("high", DATA.HIGH.getType()),
                            param("low", DATA.LOW.getType()),
                            param("close", DATA.CLOSE.getType()),
                            param("date", DATA.DATE.getType())
                    )
                            .whereNotExists(
                                    selectOne()
                                            .from(DATA)
                                            .where(DATA.DATE.eq(date))
                            )
            );
  1. 示例中传递的实际值在哪里?没有调用 .values() DSL 命令,该命令通常出现在 jOOQ 文档中,告诉它要插入哪些值。
  2. 最后不需要 .execute 吗?
  3. 有一个 batchInsert() 命令可以一次保存许多实体/行。上面提到的例子有很多批次吗?还是我只需要遍历所有实体并分别对每个实体执行唯一性检查?

【问题讨论】:

    标签: postgresql jooq


    【解决方案1】:
    1. 示例中传递的实际值在哪里?没有调用 .values() DSL 命令,该命令通常出现在 jOOQ 文档中,告诉它要插入哪些值。

    为什么要通过DSL.param() 使用命名参数API?只需通过DSL.val() 就可以了。例如

    select(
        date,
        val(ticker),
        val(open),
        val(high),
        val(low),
        val(close),
        val(date)
    )
    

    其实还有一个DSL.param(String, T)方法,可以用来传递实际值。

    可能应该有更多的重载。我为此创建了一个功能请求:https://github.com/jOOQ/jOOQ/issues/7136

    但是,在 PostgreSQL 中使用 INSERT .. ON CONFLICT 可能会更好地实现此查询。 See also my answer to this question here.

    1. 最后不需要 .execute 吗?

    是的。

    1. 有一个 batchInsert() 命令可以一次保存许多实体/行。上面提到的例子有很多批次吗?还是我只需要遍历所有实体并分别对每个实体执行唯一性检查?

    您可以批处理任何语句。相关文档在这里: https://www.jooq.org/doc/latest/manual/sql-execution/batch-execution

    【讨论】:

    • 我可能误解了您的原始答案,但这澄清了它。另外,我只是从 jOOQ 开始。但是现在可以了,谢谢。我现在有一个后续问题。是否可以针对不应根据列插入或更新行的情况扩展上述查询?类似于:如果“日期”不存在,则插入该行。如果存在且“实时关闭”列为真,则更新关闭,否则不执行任何操作。第一部分已经包含在现有查询中,但是带有 if...update.. 的第二部分没有,我不确定是否可以这样做。
    • @JozefMorvay。很高兴它奏效了。你介意在 Stack Overflow 上问一个新问题吗?他们不会很快用完问题 ID :)(cmets 功能不太适合问答)
    • 一个人永远都不够小心 :) 我已经创建了问题here
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-10-27
    • 2021-10-23
    • 1970-01-01
    • 2015-12-27
    • 2016-11-29
    • 2020-01-30
    • 1970-01-01
    相关资源
    最近更新 更多