Sequelize:如何排除字段被`upsert`方法更新

时间:2019-07-04 06:06:12

标签: sequelize.js

情况

  • 我正在使用Sequelize(v5.8.9)upsert方法来插入/更新记录 在具有唯一索引的表中。
  • 我正在使用Postgres 11,每个表都有字段createdAtcreatedByupdatedAtupdatedBy

问题

当我在表中添加一条记录时,Sequelize会生成如下的SQL:

CREATE OR REPLACE FUNCTION pg_temp.sequelize_upsert
(OUT created boolean, OUT primary_key text)  AS $func$ 
BEGIN INSERT INTO "table1" ("name","created_by","updated_by","created_at","updated_at") 
VALUES (...) RETURNING "id" INTO primary_key; created := true; 
EXCEPTION WHEN unique_violation THEN 
UPDATE "table1" SET ...,"created_by"='user1',"updated_by"='user1',"updated_at"='2019-07-03 23:45:05.872 +00:00' 
WHERE ("id" IS NULL OR "name" = '...') 
RETURNING "tag_id" INTO primary_key; created := false; 
END; $func$ LANGUAGE plpgsql; 
SELECT * FROM pg_temp.sequelize_upsert();

我们可以看到,当记录已经存在时(unique_violation),Sequelize正在更新created_by字段。

我找不到解决方案或解决方法,因此created_by可以从更新中排除。我还喜欢坚持使用upsert,因为它比通过选择然后再插入或更新来检查其存在效率更高。任何建议表示赞赏。

我知道我可以指定fields参数,但是按照doc来指定:

The fields to insert / update. Defaults to all changed fields

但是,在我的情况下,如果成功插入upsert,我确实需要插入created_by字段。

我也正在考虑在Sequelize中提出功能请求,以便在模型定义中我可以注册一个应从所有更新(实例保存,Model.update,upsert等)中排除的字段列表,而不仅仅是{{ 1}}。

1 个答案:

答案 0 :(得分:0)

在upsert方法中,您可以使用 fields 键将对象作为第二个参数传递,以提供要插入或更新的字段列表。

检查此文档:

http://docs.sequelizejs.com/class/lib/model.js~Model.html#static-method-upsert

db.model.upsert({
  ...yourData
},{
  fields: [...NameOfFieldsToBeUpdated]
}).then(function(test){})