O SQLite
json_replace()
A função nos permite substituir um valor existente em um documento JSON por outro valor. Passamos o JSON original como o primeiro argumento quando chamamos a função, seguido do caminho do valor a ser substituído, seguido do valor a ser substituído.
Também podemos substituir vários pares de chave/valor, se necessário.
Sintaxe
Funciona assim:
json_replace(json, path1, value1, path2, value2...)
Onde
json
representa o JSON original e path1, value1, path2, value2...
são pares de caminho/valor a serem substituídos. Exemplo
Aqui está um exemplo básico para demonstrar:
SELECT json_replace('{ "name" : "Fluffy" }', '$.name', "Baldy");
Resultado:
{"name":"Baldy"}
Aqui, atualizei o valor do
name
chave de Fluffy
para Baldy
. Podemos atualizar vários pares de chave/valor como este:
SELECT json_replace('{
"name" : "Fluffy",
"age" : 10
}',
'$.name', "Baldy",
'$.age', 11
);
Resultado:
{"name":"Baldy","age":11}
Eu simplesmente adicionei mais argumentos de chave/valor quando chamei
json_replace()
. Aqui, usei quebras de linha para facilitar a leitura do código. Poderia ter sido tudo em uma linha – o resultado teria sido o mesmo.
E se a chave não existir?
Se a chave ainda não existir no JSON, nada será substituído:
SELECT json_replace('{ "name" : "Fluffy" }', '$.age', 11);
Resultado:
{"name":"Fluffy"}
Esta é a principal característica que distingue o
json_replace()
função do json_set()
e json_insert()
funções. Essas funções inserirão o valor se a chave ainda não existir. No entanto, é possível inserir efetivamente novas chaves com
json_replace()
substituindo todo o objeto/documento JSON. Exemplo abaixo. Substituir todo o documento JSON
Podemos usar
json_replace()
para substituir todo o documento JSON por outro:SELECT json_replace('{ "name" : "Fluffy" }', '$', json('{ "name" : "Baldy" }') );
Resultado:
{"name":"Baldy"}
Portanto, isso nos permite inserir efetivamente novas chaves no documento:
SELECT json_replace('{
"name" : "Fluffy"
}',
'$',
json('{
"name" : "Baldy" ,
"age" : 11
}'
)
);
Resultado:
{"name":"Baldy","age":11}
Estritamente falando, não inserimos nenhuma nova chave. Nós simplesmente substituímos todo o documento. Mas o resultado foi um documento JSON que contém chaves que o original não continha.
Substituir um objeto incorporado
Também podemos substituir objetos incorporados:
SELECT json_replace('
{
"a" : 1,
"b" : { "c" : 1 }
}',
'$.b',
json('{ "c" : 2 }')
);
Resultado:
{"a":1,"b":{"c":2}}
Quando fiz isso, usei o
json()
função para retornar meu argumento como uma string JSON. Aqui está o que acontece quando eu não faço isso:SELECT json_replace('
{
"a" : 1,
"b" : { "c" : 1 }
}',
'$.b',
'{ "c" : 2 }'
);
Resultado:
{"a":1,"b":"{ \"c\" : 2 }"}
O documento JSON é inserido como um valor de texto em vez de um objeto JSON e, portanto, suas aspas duplas são escapadas com barras invertidas.
No entanto, não podemos simplesmente remover as aspas simples, porque isso resulta em um erro:
SELECT json_replace('
{
"a" : 1,
"b" : { "c" : 1 }
}',
'$.b',
{ "c" : 2 }
);
Resultado:
Parse error: unrecognized token: "{" "b" : { "c" : 1 } }', '$.b', { "c" : 2 } ); error here ---^
Sem aspas simples ou o
json()
função, obtemos um erro assim que encontra a chave esquerda. Portanto, precisamos usar aspas simples ou o json()
função, dependendo se estamos inserindo um objeto JSON ou um valor de string/texto SQL. Outra maneira de inserir um objeto JSON é usar o
json_object()
função em vez do json()
função:SELECT json_replace('
{
"a" : 1,
"b" : { "c" : 1 }
}',
'$.b',
json_object('c', 2)
);
Resultado:
{"a":1,"b":{"c":2}}
Substituir uma matriz
O mesmo conceito se aplica aos arrays:
SELECT json_replace('{ "a" : [ 1, 2, 3 ] }', '$.a', json('[ 5, 6, 7 ]'));
Resultado:
{"a":[5,6,7]}
Se removermos o
json()
função, obtemos isso:SELECT json_replace('{ "a" : [ 1, 2, 3 ] }', '$.a', '[ 5, 6, 7 ]');
Resultado:
{"a":"[ 5, 6, 7 ]"}
E se removermos as aspas simples, obtemos um erro:
SELECT json_replace('{ "a" : [ 1, 2, 3 ] }', '$.a', [ 5, 6, 7 ]);
Resultado:
Parse error: no such column: 5, 6, 7 (17) LECT json_replace('{ "a" : [ 1, 2, 3 ] }', '$.a', [ 5, 6, 7 ]); error here ---^
Alternativamente, podemos usar o
json_array()
função em vez de json()
. Essa função permite que você crie uma matriz com base em seus argumentos:SELECT json_replace('{ "a" : [ 1, 2, 3 ] }', '$.a', json_array(5, 6, 7));
Resultado:
{"a":[5,6,7]}
Anexar valores ao final de uma matriz
Para anexar valores ao final de um array, podemos usar o
json_insert()
ou json_set()
funções. No entanto, se devemos usar
json_replace()
, podemos substituir o array inteiro por outro que tenha o(s) valor(es) extra(s) adicionado(s) ao final do array:SELECT json_replace('[ 1, 2, 3 ]', '$', json('[ 1, 2, 3, 4 ]') );
Resultado:
[1,2,3,4]
Mas como mencionado,
json_insert()
e json_set()
permitem que você realmente anexe valores ao array sem substituir o array inteiro. Substituir elementos da matriz
Aqui está um exemplo de uso de
json_replace()
para substituir um elemento dentro de um array:SELECT json_replace('[ 1, 2, 3 ]', '$[1]', 4 );
Resultado:
[1,4,3]
Arrays são baseados em zero, então
[1]
indica o segundo item da matriz. O
json_set()
A função também pode ser usada para substituir elementos existentes. No entanto, o json_insert()
função não nos permite substituir elementos existentes. Caminhos inválidos
Receberemos um erro se nosso caminho não estiver bem formado:
SELECT json_replace('{ "a" : 1 }', 'a', 2);
Resultado:
Runtime error: JSON path error near 'a'
Nesse caso, esqueci de incluir
$.
na frente do caminho. Documentos JSON inválidos
Também receberemos um erro de que o JSON não está bem formado:
SELECT json_replace('{ "a" : 1', '$.a', 2);
Resultado:
Runtime error: malformed JSON
Desta vez, o erro nos diz que nosso JSON está malformado.