AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • Início
  • system&network
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • Início
  • system&network
    • Recentes
    • Highest score
    • tags
  • Ubuntu
    • Recentes
    • Highest score
    • tags
  • Unix
    • Recentes
    • tags
  • DBA
    • Recentes
    • tags
  • Computer
    • Recentes
    • tags
  • Coding
    • Recentes
    • tags
Início / dba / Perguntas / 315117
Accepted
Leahim
Leahim
Asked: 2022-08-02 17:21:38 +0800 CST2022-08-02 17:21:38 +0800 CST 2022-08-02 17:21:38 +0800 CST

Alterando um único elemento de um array json no PostgreSQL

  • 772

Antes de tudo, gostaria de dizer que não tenho muita experiência, mas comecei a aprender dbs depois de ter algumas matérias relacionadas a dbs na minha universidade (então, lembre-se disso enquanto estiver lendo isso).

Eu já fiz essa pergunta no stackoverflow, mas não obtive uma resposta conclusiva, então pensei que seria uma boa ideia fazer a mesma pergunta aqui, pois este site é focado apenas em bancos de dados e seus prós e contras.

Desejo alterar um único elemento de uma matriz aninhada usando os comandos UPDATE, DELETE ou INSERT. Neste caso, eu queria atualizar um único elemento de um array trocando um dos valores 'lastName' por outro usando o comando UPDATE (a sintaxe que estou usando provavelmente está errada, mas isso é o máximo que consegui descobrir do que eu já li na documentação oficial). Eu usei o dbfiddle para testar se o que estou fazendo funcionaria antes de colocar qualquer coisa no banco de dados real para não cometer erros desnecessários. Aqui está o que escrevi em dbfiddle https://dbfiddle.uk/?rdbms=postgres_10&fiddle=ecc2329efea6af28636b3537d46b6c01

Agradeceria se alguém pudesse esclarecer o que estou fazendo de errado. Se você tiver alguma sugestão sobre como esse tipo de coisa deve ser feito, ficarei mais do que feliz em receber algum feedback construtivo.

postgresql json
  • 1 1 respostas
  • 77 Views

1 respostas

  • Voted
  1. Best Answer
    a_horse_with_no_name
    2022-08-02T22:19:36+08:002022-08-02T22:19:36+08:00

    Eu não acho que isso pode ser feito usando jsonb_set().

    O segundo parâmetro para essa função requer um "caminho de destino". Como podacicontém uma matriz, você precisa incluir a posição da matriz, por exemplo jsonb_set(podaci, '{1,lastName}', '"Kirin"')- no entanto, não há uma maneira fácil (eu consigo pensar) de obter a posição do índice que você precisa.

    Portanto, você precisará percorrer os elementos, alterar o que deseja e agregar de volta. Isso pode ser feito com uma subconsulta na atribuição da instrução UPDATE:

    update test_tablica1
       set podaci = (select jsonb_agg(case 
                                       when element @> '{"firstName": "Maria"}' 
                                         then element||'{"lastName": "Kirin"}' 
                                       else element
                                      end)
                     from jsonb_array_elements(podaci) as x(element))
    where podaci @> '[{"firstName": "Maria"}]';                 
    

    jsonb_agg()agrega os elementos que são retornados de jsonb_array_elements()volta em uma matriz. A expressão CASE irá então verificar cada elemento e se contiver o nome Maria, o sobrenome será substituído (anexar um valor JSONB a um valor JSONB, substitui as chaves existentes)

    A cláusula WHERE impede a atualização de linhas que não precisam de atualização

    Exemplo on-line


    No entanto, seu modelo realmente parece um uso indevido de JSON no banco de dados. Seria mais eficiente armazenar os nomes em uma tabela relacional adequada com um relacionamento um para muitos com a tabela base ( test_tablica1no seu exemplo)

    Algo como:

    create table test_tablica1 
    (
      id int primary key generated always as identity, 
      ... other columns ...,
      datum_upisa timestamp
    );
    
    create table names
    (
      id int not null, 
      tablica1_id int not null references test_tablica1,
      firstname text, 
      lastname text
    );
    
    insert into test_tablica1 (id) values (1);
    insert into names (id, tablica1_id, firstname, lastname)
    values
    (1, 'Tom', 'Cruise'),
    (2, 'Maria', 'Sharapova'),
    (3, 'James', 'Bond')
    ;
    

    Então a atualização se torna tão simples quanto:

    update names
       set lastname = 'Kirin'
    where firstname = 'Maria'
      and tablica1_id = 1 
    ;
    

    A condição tablica1_id = 1é apenas um exemplo. Adicione qualquer condição necessária para restringir a alteração do nome às linhas vinculadas a uma linha específica na tabela pai.

    • 0

relate perguntas

  • Posso ativar o PITR depois que o banco de dados foi usado

  • Práticas recomendadas para executar a replicação atrasada do deslocamento de tempo

  • Os procedimentos armazenados impedem a injeção de SQL?

  • Sequências Biológicas do UniProt no PostgreSQL

  • Qual é a diferença entre a replicação do PostgreSQL 9.0 e o Slony-I?

Sidebar

Stats

  • Perguntas 205573
  • respostas 270741
  • best respostas 135370
  • utilizador 68524
  • Highest score
  • respostas
  • Marko Smith

    conectar ao servidor PostgreSQL: FATAL: nenhuma entrada pg_hba.conf para o host

    • 12 respostas
  • Marko Smith

    Como fazer a saída do sqlplus aparecer em uma linha?

    • 3 respostas
  • Marko Smith

    Selecione qual tem data máxima ou data mais recente

    • 3 respostas
  • Marko Smith

    Como faço para listar todos os esquemas no PostgreSQL?

    • 4 respostas
  • Marko Smith

    Listar todas as colunas de uma tabela especificada

    • 5 respostas
  • Marko Smith

    Como usar o sqlplus para se conectar a um banco de dados Oracle localizado em outro host sem modificar meu próprio tnsnames.ora

    • 4 respostas
  • Marko Smith

    Como você mysqldump tabela (s) específica (s)?

    • 4 respostas
  • Marko Smith

    Listar os privilégios do banco de dados usando o psql

    • 10 respostas
  • Marko Smith

    Como inserir valores em uma tabela de uma consulta de seleção no PostgreSQL?

    • 4 respostas
  • Marko Smith

    Como faço para listar todos os bancos de dados e tabelas usando o psql?

    • 7 respostas
  • Martin Hope
    Jin conectar ao servidor PostgreSQL: FATAL: nenhuma entrada pg_hba.conf para o host 2014-12-02 02:54:58 +0800 CST
  • Martin Hope
    Stéphane Como faço para listar todos os esquemas no PostgreSQL? 2013-04-16 11:19:16 +0800 CST
  • Martin Hope
    Mike Walsh Por que o log de transações continua crescendo ou fica sem espaço? 2012-12-05 18:11:22 +0800 CST
  • Martin Hope
    Stephane Rolland Listar todas as colunas de uma tabela especificada 2012-08-14 04:44:44 +0800 CST
  • Martin Hope
    haxney O MySQL pode realizar consultas razoavelmente em bilhões de linhas? 2012-07-03 11:36:13 +0800 CST
  • Martin Hope
    qazwsx Como posso monitorar o andamento de uma importação de um arquivo .sql grande? 2012-05-03 08:54:41 +0800 CST
  • Martin Hope
    markdorison Como você mysqldump tabela (s) específica (s)? 2011-12-17 12:39:37 +0800 CST
  • Martin Hope
    Jonas Como posso cronometrar consultas SQL usando psql? 2011-06-04 02:22:54 +0800 CST
  • Martin Hope
    Jonas Como inserir valores em uma tabela de uma consulta de seleção no PostgreSQL? 2011-05-28 00:33:05 +0800 CST
  • Martin Hope
    Jonas Como faço para listar todos os bancos de dados e tabelas usando o psql? 2011-02-18 00:45:49 +0800 CST

Hot tag

sql-server mysql postgresql sql-server-2014 sql-server-2016 oracle sql-server-2008 database-design query-performance sql-server-2017

Explore

  • Início
  • Perguntas
    • Recentes
    • Highest score
  • tag
  • help

Footer

AskOverflow.Dev

About Us

  • About Us
  • Contact Us

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve