PostgreSQL-JSON-Abfrage-Array für mehrere Werte

14

Ich möchte eine Abfrage gegen jsonbTyp in Postgres schreiben , die bei einem Array von Kunden-IDs entsprechende Gruppen findet.

Angesichts dieser Beispieltabelle:

CREATE TABLE grp(d JSONB NOT NULL);

INSERT INTO grp VALUES
   ('{"name":"First","arr":["foo"], "customers":[{"id":"1", "name":"one"},{"id":"2", "name":"two"}]}')
 , ('{"name":"Second","arr":["foo","bar"], "customers":[{"id":"3", "name":"three"},{"id":"4", "name":"four"}]}')
 , ('{"name":"Third","arr":["bar","baz"], "customers":[{"id":"5", "name":"five"},{"id":"6", "name":"seven"}]}');

Ich fand ähnliche Frage ( PostgreSql JSONB SELECT gegen mehrere Werte ) und schaffte es, mit dieser Abfrage zu erreichen, was ich auf einem einfachen Array will:

SELECT d FROM grp WHERE d->'arr' ?| ARRAY['foo', 'bar'];

Ich kann es jedoch nicht zum Laufen bringen, wenn das Array JSON- Objekte enthält :

SELECT d FROM grp WHERE d->'customers' ?| ARRAY['{"id":"1"}', '{"id":"5"}'];

Folgendes erwarte ich von meiner Anfrage:

Gruppe "First" -> Kunde "1"

Gruppe "Dritter" -> Kunde "5"

BartZ
quelle

Antworten:

15

Es gibt einen Weg: Kombiniere den Containment-Operator@> mit dem ANYKonstrukt :

SELECT d
FROM   grp
WHERE  d->'customers' @> ANY (ARRAY ['[{"id":"1"}]', '[{"id":"5"}]']::jsonb[]);

Oder:

...
WHERE d->'customers' @> ANY ('{"[{\"id\": \"1\"}]","[{\"id\": \"5\"}]"}'::jsonb[]);

Es ist wichtig, das Array jsonb[]explizit auf zu setzen. Beachten Sie, dass jedes Element ein JSON- Array ist, wie es der Operator @>erfordert. Es handelt sich also um ein Array von JSON-Arrays.

Sie können dafür einen Index verwenden:

Das Handbuch gibt ausdrücklich an, dass der Operator ?|nur für Zeichenfolgen ist .

Erwin Brandstetter
quelle