我们如何在 sqlx 中为 postgres 实现批量 upsert?

所以我一直在尝试批量更新。Postgres开箱即用地支持它。示例查询

INSERT INTO table(col1, col2, col3, eligible ,created_at, updated_at)                    VALUES (:col1, :col2, :col3 :eligible ,now(), now()) 
                    ON CONFLICT (col1, col2)
                    DO UPDATE SET col2 = excluded.col2,eligible = excluded.eligible, updated_at = now() RETURNING *

我希望能够做的是使用jmoiron/sqlx库使用命名功能创建批量更新插入。

正如这里提到的Github问题,我无法这样做。


慕少森
浏览 138回答 2
2回答

翻阅古今

我想自己回答这个问题,作为一个开发人员,我的第一个本能是查看堆栈溢出并将其传达给人们我相信sqlx中的批量upsert是最近在1.3.0中引入的。它在README中有详细说明,但作为一个ORM,它是一堆PR已经转发并还原了更改以支持多种SQL风格。识别查询是否是批量查询的当前正则表达式期望查询以空格或括号结尾,基本上是占位符。请在此处查看提交。为了解决这个问题,我能够使用内部函数和一些旁路来使postgres提供的批量upsert工作。这是相同的代码。为方便起见,请在此处重新注册: sliceOfStructs := []model.Gamer{        {        UserID:   "123",        Name: "aarengee",        Address: "xd",        Eligible: true,        },        {            UserID:   "1234",            Name: "aarengeeAgain",            Address: "xd",            Eligible: false,        },    }    upsertQuery := "INSERT INTO gamer_details (user_id, name, address, eligible,updated_at) VALUES (:user_id,:name,:address,:eligible,now())"    onConflictStatement := " ON CONFLICT (user_id, name) DO UPDATE SET address = excluded.address,eligible = excluded.eligible, updated_at = now() RETURNING *"    query, queryArgs, _ := db.BindNamed(upsertQuery, sliceOfStructs)    query = db.Rebind(query)    query = query + onConflictStatement    rows, err := db.Queryx(query, queryArgs...)

慕哥9229398

在使用ON CONFLICT进行批量插入时,我仍然遇到错误,因此在朋友的帮助下找到了一个对我有用的解决方案。这很难找到,但你可以在这里看到更多信息。https://www.prisma.io/dataguide/postgresql/inserting-and-modifying-data/insert-on-conflict#using-the-do-update-action...DO UPDATE SET (var1, var2, var3, var4) = (excluded.var1, excluded.var2, excluded.var3, excluded.var4)那么你应该能够做到这一点_, err := db.NamedExecContext(ctx, query, sliceObj)当然,如果您不想,则不需要使用上下文
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Go