Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/firebase/6.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 基于JSON中的值向上插入到表中_Javascript_Postgresql_Meteor_Knex.js - Fatal编程技术网

Javascript 基于JSON中的值向上插入到表中

Javascript 基于JSON中的值向上插入到表中,javascript,postgresql,meteor,knex.js,Javascript,Postgresql,Meteor,Knex.js,我正在使用passport bnet通过战网对用户进行身份验证(他们可以拥有多种服务)。我有一个用户对象,其格式如下: { "id": 1, "name": "Meow", "battlenet": { "id": 5, "tag": "obviously-not-a-real-battletag#1234" } } 当我对一个用户进行身份验证时,我会在响应中获得战网用户的id。我试图做的是从这个json字段中选择id,如果它不存在,就创建它 passport.

我正在使用
passport bnet
通过战网对用户进行身份验证(他们可以拥有多种服务)。我有一个用户对象,其格式如下:

{
  "id": 1,
  "name": "Meow",
  "battlenet": {
    "id": 5,
    "tag": "obviously-not-a-real-battletag#1234"
  }
}
当我对一个用户进行身份验证时,我会在响应中获得战网用户的id。我试图做的是从这个json字段中选择id,如果它不存在,就创建它

passport.use(new Battlenet({/**...*/}, function (accessToken, refreshToken, profile, done) {
  database
    .select('*')
    .where('battlenet->id', '=', profile.id)
    .then(user => done(null, user))
    .catch(done);
});
然而,我有点麻烦。如何插入此用户文档以包含一些默认值?本质上,我想要一些类似于mongo中这种修饰语的东西

{
  $setOnInsert: { name: profile.tag.replace(/\W/, '') },
  $set: { battlenet: profile }
}

如何通过knex和postgres实现这一点?

我很难理解您的模式,以及当同一查询运行两次时,您希望发生什么。请随时更新问题,我可能会给出更完整的答案

一般来说,对于knex,在中已经讨论了upsert

讨论的结论是仍然应该使用原始SQL(
knex.raw
)fr upsert

对于问题的SQL部分,我认为关键在于需要为
battlenet->id
属性创建
UNIQUE
约束。在这之后,可以在JSONB属性中执行与重复ID冲突的
INSERT
s

大概是这样的:

CREATE UNIQUE INDEX t_id ON t((json->>'id'));
在这之后,编写upsert应该很容易,它实际上只是在
JSONB\u set
函数的帮助下更新一些JSONB属性