Java JBDI 如何通过查询重复键更新 mysql 获取受影响的行和生成的 id

Java JBDI how to get the affected rows and generated id with a query on duplicate key update mysql

提问人:Robbie 提问时间:11/13/2023 最后编辑:Robbie 更新时间:11/14/2023 访问量:63

问:

我正在尝试了解如何在插入时返回受影响的行,并从同一查询中获取生成的键;id

我有这个查询

@SqlUpdate("""
            INSERT INTO table_name (
                account, 
                state,
                lock,
                external_id
)
            VALUES (
                :account,
                :state,
                :lock,
                :external_id)
            """)
    @GetGeneratedKeys("id")
    Long insert(@BindBean ExampleBean exampleBean);

我想更新到这样的东西,所以当我发现一个重复的条目时,我想把它更新成这样的东西

  @SqlUpdate("""
            INSERT INTO table_name (
                account, 
                state,
                lock,
                external_id
)
            VALUES (
                :account,
                :state,
                :lock,
                :external_id)
                ON DUPLICATE KEY
                UPDATE
                external_id = :external_id
                lock = :lock
            """)
    @GetGeneratedKeys("id")
    idRows insert(@BindBean ExampleBean exampleBean);  

 public record idRows(Long id, int rowsAffected) {}

边做边叫

try (Handle handle = jdbi.open()) {
        return handle.attach(ExampleBean.class).upsert(exampleBean));
        } catch (Exception e) {
            log(example);
            return null;
        }

在我的 Hikari 数据源上,我设置了"useAffectedRows", true

我可以同时将受影响的行和生成的 ID 映射到我的记录,任何想法将不胜感激!

java mysql jdbi

评论

0赞 queeg 11/13/2023
upsert是 Couchbase 引入的一个术语。在关系数据库上,您需要区分插入和更新。因此,我相信您的两个 SqlUpdate 语句都错误地显示“插入......”
0赞 Robbie 11/13/2023
嘿,@queeg,查询 1 是我想变成查询 2 的样式,这就是为什么我使用重复键更新来反映更新插入器的行为,但也许我把问题写错了?

答:

0赞 4EACH 11/14/2023 #1
@SqlUpdate("""
    INSERT INTO table_name (
        account, 
        state,
        lock,
        external_id
    )
    VALUES (
        :account,
        :state,
        :lock,
        :external_id)
    ON DUPLICATE KEY UPDATE
        external_id = :external_id,
        lock = :lock
""")
@GetGeneratedKeys({"id", "rowsAffected"})
idRows upsert(@BindBean ExampleBean exampleBean);
idRows 记录应如下所示:
public record idRows(Long id, int rowsAffected) {}

这样,当您调用 upsert 方法时,它应该返回一个 idRows 实例,其中包含生成的 ID 和受影响的行数。

评论

0赞 Robbie 11/14/2023
我似乎无法让它工作,我的第一个问题是它需要一个行映射器,所以我添加了一个只返回一个,在该列名称中,我唯一能看到的是它为我提供了生成的键,而不是我也在寻找的受影响的行class idRowsMapper implements RowMapper<idRows> { @Override public idRows map(ResultSet rs, StatementContext ctx) throws SQLException { return new idRows(rs.getLong("id"), rs.getInt("rowsAffected")); } } rs.getMetaData().getColumnCount()GENERATED_KEY