Postgres: Jak przekonwertować ciąg json na tekst?

93

Wartość Json może składać się z wartości ciągu. na przykład.:

postgres=# SELECT to_json('Some "text"'::TEXT);
     to_json
-----------------
 "Some \"text\""

Jak mogę wyodrębnić ten ciąg jako wartość tekstową postgres?

::TEXTnie działa. Zwraca json w cudzysłowie, a nie oryginalny ciąg:

postgres=# SELECT to_json('Some "text"'::TEXT)::TEXT;
     to_json
-----------------
 "Some \"text\""

Dzięki.

PS Używam PostgreSQL 9.3

e79ene
źródło
stackoverflow.com/q/19414361/562459 może pomóc. Może nie.
Mike Sherrill „Cat Recall”
Podobny problem z tablicą ciągów, stackoverflow.com/q/45243186/287948
Peter Krauss

Odpowiedzi:

58

W PostgreSQL nie ma sposobu na dekonstrukcję skalarnego obiektu JSON. Tak więc, jak wskazałeś,

select  length(to_json('Some "text"'::TEXT) ::TEXT);

15 lat,

Sztuczka polega na przekonwertowaniu JSON na tablicę jednego elementu JSON, a następnie wyodrębnieniu tego elementu za pomocą ->>.

select length( array_to_json(array[to_json('Some "text"'::TEXT)])->>0 );

zwróci 11.

Robert M. Lefkowitz
źródło
8
Szkoda, że json_extract_path_text()nie może odwoływać się do elementu głównego (AFAIK).
Erwin Brandstetter
3
Co ciekawe, nie było dyskusji mózgów najwyraźniej z powrotem na etapie projektowania API w 2012 roku, w którym funkcja from_jsondostałem proponowanych, ale nie realizowane wiki.postgresql.org/wiki/JSON_API_Brainstorm
Nikola
147

W 9.4.4 korzystanie z #>>operatora działa dla mnie:

select to_json('test'::text) #>> '{}';

Aby użyć z kolumną tabeli:

select jsoncol #>> '{}' from mytable;
Ian Timothy
źródło
2
Wydaje się, że jest to najprostsze rozwiązanie w Postgres 9.4. Jednak nie działa w wersji 9.3.
e79ene
2
@hasen OP stwierdza, że ​​próbuje wyodrębnić tekst z wartości JSON i to_json(...)jest to po prostu łatwy sposób na utworzenie wartości JSON do pracy jako przykład w krótkiej jednowierszowej instrukcji. Z pewnością zastąpiłbyś ją nazwą kolumny JSON, gdybyś odpytywał tabelę zgodnie z opisem. Ponadto, aby wyjaśnić potencjalny błąd, rzutowanie (...)::textjest zbędne, ponieważ #>>operator z definicji zwraca tekst (i jest powodem używania operatora w pierwszej kolejności). Możesz zachować nawiasy, ale porzucić obsadę ::text.
Ian Timothy
1
Czy ktoś mógłby przeliterować, co #>>i '{}'robi? Nie do końca rozumiem, a żaden termin nie jest przyjazny dla Google. Ta odpowiedź rozwiązała mój problem, chcę tylko wiedzieć, dlaczego.
valadil
1
@valadil Dokumentacja dla #>>operatora jest tutaj .
Ian Timothy,
1
@valadil W tym przypadku istnieje obiekt JSON najwyższego poziomu lub root text. Może wyglądać jak ciąg znaków, ale jest to obiekt JSON. Aby przekonwertować ten obiekt z formatu JSON na tekst, użyj #>>operatora. Ale ten operator wymaga, abyś określił ścieżkę. Ścieżka do tego obiektu głównego to {}. Więc SELECT '"test"'::jsonb #>> '{}'oznacza „uzyskać obiekt na ścieżce root i przekonwertować go do tekstu”.
Ian Timothy,
3

Pan Ciekawski też był tego zaciekawiony. Oprócz #>> '{}'operatora, w 9.6+ można uzyskać wartość łańcucha jsonb za pomocą ->>operatora:

select to_jsonb('Some "text"'::TEXT)->>0;
  ?column?
-------------
 Some "text"
(1 row)

Jeśli ktoś ma wartość json, rozwiązaniem jest najpierw rzutowanie na jsonb:

select to_json('Some "text"'::TEXT)::jsonb->>0;
  ?column?
-------------
 Some "text"
(1 row)
Pan Ciekawy
źródło
0

Prosty sposób na zrobienie tego:

SELECT  ('[' || to_json('Some "text"'::TEXT) || ']')::json ->> 0;

Po prostu przekonwertuj ciąg json na listę json

Zhemin Zhou
źródło
0

- >> działa na mnie.

wersja postgres:

<postgres.version>11.6</postgres.version>

Pytanie:

select object_details->'valuationDate' as asofJson, object_details->>'valuationDate' as asofText from MyJsonbTable;

Wynik:

  asofJson       asofText
"2020-06-26"    2020-06-26
"2020-06-25"    2020-06-25
"2020-06-25"    2020-06-25
"2020-06-25"    2020-06-25
Surinder
źródło
Dzięki za zwrócenie uwagi, poprawiłem powyższą wersję
Surinder
Pierwotne pytanie brzmi, jak uzyskać wartość ciągu JSON jako tekst z (bez klucza obiektu). Ta odpowiedź jest po prostu różnicą między ->i ->>podczas korzystania z klucza. Zobacz tę odpowiedź lub tę odpowiedź .
Ian Timothy