How do we modify an json array object regardless of its position? - mysql

The problem
Each entity owns an id and a json field. That json field simply stores a json list of objects.
Entity{ id, json }
"1, '[{"tag": "Player"}, {"position": {"x": 20, "y": 20}}]'"
The order of those json objects is not always the same and i want to update the json object inside the array where "tag" :"Player". I basically wanna change the tag.
I tried to use json_replace, but it didnt worked because it seems like that function does not accept the $** wildcard. But i cant use $[0] because that json object is not always at the first position. Thats what i tried.
UPDATE entity
SET jsonComponents = JSON_REPLACE(
jsonComponents ,
'$**.tag' ,
'NewTag'
)
WHERE
entity.id = 1
The Question
How are we supposed to modify/remove an json object inside an pure json list, if we dont know where its located at ? How can we modify/remove a json object inside a list regardless of its position inside the list ?
Im actually very glad for any help on this topic, couldnt find anything about it...

The solution
If we dont know the path of the json object we seek to modify... we simply query for the path using json_search
update entity
set jsonComponents = JSON_REPLACE(
jsonComponents,
JSON_UNQUOTE(json_search(jsonComponents, 'one', 'Player')),
'NewTag'
)
where entity.id = 0

Related

Redshift JSON Parsing

I have some JSON data in Redshift table of type character varying. An example entry is:
[{"value":["*"], "key":"testData"}, {"value":"["GGG"], key: "differentData"}]
I want to return vales based on keys, how can i do this? I'm attempting to do something like
json_extract_path_text(column, 'value') but unfortunately it errors out. Any ideas?
So the first issue is that your string isn't valid JSON. There are mismatched and missing quotes. I think you mean:
[{"value":["*"], "key":"testData"}, {"value":["GGG"], "key": "differentData"}]
I don't know if this is a data issue or a transcription error but these functions won't work unless the json text is valid.
The next thing to consider is that at the top level this json is an array so you will need to use json_extract_array_element_text() function to pick up an element of the array. For example:
json_extract_array_element_text('json string', 0)
So putting this together we can extract the first "value" with (untested):
json_extract_path_text(
json_extract_array_element_text(
'[{"value":["*"], "key":"testData"}, {"value":["GGG"], "key": "differentData"}]', 0
), 'value'
)
Should return the string ["*"].

Parse JSON data in T-SQL [duplicate]

This is driving me nuts, and I don't understand what's wrong with my approach.
I generate a JSON object in SQL like this:
select #output = (
select distinct lngEmpNo, txtFullName
from tblSecret
for json path, root('result'), include_null_values
)
I get a result like this:
{"result":[{"lngEmpNo":696969,"txtFullName":"Clinton, Bill"}]}
ISJSON() confirms that it's valid JSON, and JSON_QUERY(#OUTPUT, '$.result') will return the array [] portion of the JSON object... cool!
BUT, I'm trying to use JSON_QUERY to extract a specific value:
This gets me a NULL value. Why??????? I've tried it with the [0], without the [0], and of course, txtFullName[0]
SELECT JSON_QUERY(#jsonResponse, '$.result[0].txtFullName');
I prefixed with strict, SELECT JSON_QUERY(#jsonResponse, 'strict $.result[0].txtFullName');, and it tells me this:
Msg 13607, Level 16, State 4, Line 29
JSON path is not properly formatted. Unexpected character 't' is found at
position 18.
What am I doing wrong? What is wrong with my structure?
JSON_QUERY will only extract an object or an array. You are trying to extract a single value so, you need to use JSON_VALUE. For example:
SELECT JSON_VALUE(#jsonResponse, '$.result[0].txtFullName');

JSON_REMOVE object in MySQL

I am trying to delete objects from my JSON array in MySQL.
I have a table called cart with two fields quote_id type int and items type json with the following row stored inside MySQL
quote_id: 0
items:
[
{
"a":42,
"b":"test4"
},
{
"a":32,
"b":"test3"
}
]
I am trying to create a query which would delete json objects from the json array. For example every
{
"a":32,
"b":"test3"
}
I have tried many queries. First I ended up with this:
UPDATE cart
SET items = IFNULL(JSON_REMOVE(items, JSON_UNQUOTE(JSON_SEARCH(items, 'one', 'test3'))), items)
WHERE quote_id = 13392;
However it just deletes "b":"test3" from the second object and left the "a":32 in it and I need a query that would find the whole object and would delete it.
This is my second query:
UPDATE cart
SET items = IFNULL(JSON_REMOVE(items, JSON_SEARCH(items, 'one', CAST('{"a": 32, "b": "test3"}' AS JSON))), items)
WHERE quote_id = 13392;
However I don't think the search on it works. I tried it without using the CAST()AS JSON, however it still did not work.
As I said I am pretty sure the problem is with the JSON_SEARCH, but maybe someone has the solution?
Thank you!
The JSON_SEARCH returns the path of the property, not the path to the object itself.
So you can use the following solution to get the object path with SUBSTR:
SELECT JSON_REMOVE(items,
SUBSTR(JSON_UNQUOTE(JSON_SEARCH(items, 'one', 'test3')), 1, LOCATE('.', JSON_UNQUOTE(JSON_SEARCH(items, 'one', 'test3')))-1)
) FROM cart
You can also use REGEXP_SUBSTR to get the object path:
SELECT JSON_REMOVE(items, REGEXP_SUBSTR(JSON_UNQUOTE(JSON_SEARCH(items, 'one', 'test3')), '^\\$\\[[0-9]+\\]'))
FROM cart
demo on dbfiddle.uk

What's the correct JsonPath expression to search a JSON root object using Newtonsoft.Json.NET?

Most examples deal with the book store example from Stefan Gössner, however I'm struggling to define the correct JsonPath expression for a simple object (no array):
{ "Id": 1, "Name": "Test" }
To check if this json contains Id = 1.
I tried the following expression: $..?[(#.Id == 1]), but this does find any matches using Json.NET?
Also tried Manatee.Json for parsing, and there it seems the jsonpath expression could be like $[?($.Id == 1)] ?
The path that you posted is not valid. I think you meant $..[?(#.Id == 1)] (some characters were out of order). My answer assumes this.
The JSON Path that you're using indicates that the item you're looking for should be in an array.
$ start
.. recursive search (1)
[ array item specification
?( item-based query
#.Id == 1 where the item is an object with an "Id" with value == 1 at the root
) end item-based query
] end array item specification
(1) the conditions following this could match a value no matter how deep in the hierarchy it exists
You want to just navigate the object directly. Using $.Id will return 1, which you can validate in your application.
All of that said...
It sounds to me like you want to validate that the Id property is 1 rather than to search an array for an object where the Id property is 1. To do this, you want JSON Schema, not JSON Path.
JSON Path is a query language for searching for values which meet certain conditions (e.g. an object where Id == 1.
JSON Schema is for validating that the JSON meet certain requirements (your data's in the right shape). A JSON Schema to validate that your object has a value of 1 could be something like
{
"properties": {
"Id": {"const":1}
}
}
Granted this isn't very useful because it'll only validate that the Id property is 1, which ideally should only be true for one object.

Use variable as key in JSON data object to get value

I have a given JSON object .
var item = {VENUE_ID: "146", Cost: 0, Impressions: 0, Position: 0, id: 6} ;
I can extract value by item.VENUE_ID ,item.Cost.
How can i use variable to extract value .I want something like it
var keys="VENUE_ID";
item.keys or item[keys];
Solved it we can use following code to set key dynamic and get value item["" + keys+ ""]
For me
item[keys]
works perfectly where keys = "VENUE_ID"
Anyone facing this requirement, try and access the value the aforesaid way, even the OP posted the correct method in his question. I'm not sure why it didn't work for him in the first place.