如何在PostgreSQL中更新jsonb列的字段?

Ran*_*dra 5 postgresql jsonb postgresql-9.4

所以我想试试jsonbPostgreSQL.在我的表,我有一个名为列extrasjsonb类型.

示例数据extras看起来像{"param1": 10, "param2": 15}

我想仅使用sql语句修改JSON.我想做这样的事情:

更新param1extras通过,如果添加10到其值字段param2extras超过12.

我该如何编写这样的SQL语句?我知道我可以很容易地在应用程序层中执行此操作,但我想在SQL层本身中执行此操作,因为我可能会处理的行数会很大而且我不想在db-application中浪费时间 - db往返

Mik*_*stö 6

这应该与PostgreSQL 9.5一起使用:

create table t (extras jsonb);
insert into t values
    ('{"param1": 10, "param2": 15}'),
    ('{"param1": 10, "param2": 5}');

UPDATE t 
  SET extras = jsonb_set(extras, '{param1}', ((extras->>'param1')::real + 10)::text::jsonb) 
  WHERE (extras#>>'{param2}')::real > 12;

select * from t;
            extras            
------------------------------
 {"param1": 10, "param2": 5}
 {"param1": 20, "param2": 15}
(2 rows)
Run Code Online (Sandbox Code Playgroud)


And*_*mar 0

jsonb类型旨在存储整个文档。如果更改文档的任何部分,则需要为该列分配新值。因为 Postgres 会将旧版本保留一段时间,这是一项昂贵的操作。

考虑到这一点,以下是如何不更新jsonb列的示例:

create table t1 (doc jsonb);

insert into t1 values 
    ('{"param1": 10, "param2": 15}'),
    ('{"param1": 10, "param2": 5}');

update  t1
set     doc = ('{"param1": ' ||
        ((doc->'param1')::text::int + 10)::text ||
        ', "param2": ' ||
        (doc->'param2')::text ||
        '}')::jsonb
where   (doc->'param2')::text::int > 12;

select * from t1;
Run Code Online (Sandbox Code Playgroud)

这打印:

            doc
------------------------------
 {"param1": 10, "param2": 5}
 {"param1": 20, "param2": 15}
(2 rows)
Run Code Online (Sandbox Code Playgroud)