I have JSON documents stored in Postgres under the JSON data type (Postgres 9.3) and I need to recursively collect the key names down the tree.
For example, given th
I wrote a function to do this:
CREATE OR REPLACE FUNCTION public.jsonb_keys_recursive(_value jsonb)
RETURNS TABLE(key text)
LANGUAGE sql
AS $function$
WITH RECURSIVE _tree (key, value) AS (
SELECT
NULL AS key,
_value AS value
UNION ALL
(WITH typed_values AS (SELECT jsonb_typeof(value) as typeof, value FROM _tree)
SELECT v.*
FROM typed_values, LATERAL jsonb_each(value) v
WHERE typeof = 'object'
UNION ALL
SELECT NULL, element
FROM typed_values, LATERAL jsonb_array_elements(value) element
WHERE typeof = 'array'
)
)
SELECT DISTINCT key
FROM _tree
WHERE key IS NOT NULL
$function$;
For an example, try:
SELECT jsonb_keys_recursive('{"A":[[[{"C":"B"}]]],"X":"Y"}');
Note that the other two answers don't find keys within objects inside arrays, my solution does. (The question didn't give any examples of arrays at all, so finding keys inside arrays may not have been what the original asker needed, but it was what I needed.)