I have a table with JSON array data that I would like to find.
CREATE TABLE data (id SERIAL, json JSON); INSERT INTO data (id, json) VALUES (1, '[{"name": "Value A", "value": 10}]'); INSERT INTO data (id, json) VALUES (2, '[{"name": "Value B1", "value": 5}, {"name": "Value B2", "value": 15}]');
As described in this answer , I created a function that also allows you to create an index for array data (important).
CREATE OR REPLACE FUNCTION json_val_arr(_j json, _key text) RETURNS text[] AS $$ SELECT array_agg(elem->>_key) FROM json_array_elements(_j) AS x(elem) $$ LANGUAGE sql IMMUTABLE;
This works well if I want to find an integer value (for example, βB1 Valueβ):
SELECT * FROM data WHERE '{"Value B1"}'::text[] <@ (json_val_arr(json, 'name'));
Now my questions are:
Can values ββbe found using a wildcard (for example, "Value *")? Something like the following (naive) approach:
... WHERE '{"Value%"}'::text[] <@ (json_val_arr(json, 'name'));
Is it possible to find numerical values ββwith comparison operators (e.g.> = 10)? Again, a naive and obviously wrong approach:
... WHERE '{10}'::int[] >= (json_val_arr(json, 'value'));
I tried to create a new function returning int[] , but that did not work.
I created a SQL Fiddle to illustrate my problem.
Or it would be better to use a different approach, for example, the following work queries:
SELECT * FROM data, json_array_elements(json) jsondata WHERE jsondata ->> 'name' LIKE 'Value%';
and
... WHERE cast(jsondata ->> 'value' as integer) <= 10;
However, for these queries, I was unable to create any index that was actually selected by the queries.
Also, I would like to implement all of this in Postgresql 9.4 with JSONB in ββthe end, but I think this should not be a problem for the above questions.
Many thanks!
json sql indexing postgresql
lukas
source share