In MariaDB, JSON_TABLE()
is een ingebouwde functie die JSON-gegevens omzet in een relationele vorm.
Met andere woorden, het laat je een JSON-document als een tabel retourneren.
De JSON_TABLE()
functie is geïntroduceerd in MariaDB 10.6.0.
Syntaxis
De syntaxis gaat als volgt:
JSON_TABLE(json_doc,
context_path COLUMNS (column_list)
) [AS] alias
Waar column_list
gaat als volgt:
column[, column][, ...]
Waar kolom
gaat als volgt:
name FOR ORDINALITY
| name type PATH value_path path [on_empty] [on_error]
| name type EXISTS PATH value_path
| NESTED [PATH] path COLUMNS (column_list)
Waar on_empty
gaat als volgt:
{NULL | DEFAULT string | ERROR} ON EMPTY
En on_error
gaat als volgt:
{NULL | DEFAULT string | ERROR} ON ERROR
Voorbeeld
Hier is een voorbeeld om te demonstreren.
SET @json_document = '
[
{ "name": "Wag", "type": "Dog", "weight": 20 },
{ "name": "Bark", "type": "Dog", "weight": 10 },
{ "name": "Meow", "type": "Cat", "weight": 7 }
]
';
SELECT * FROM JSON_TABLE(@json_document, '$[*]'
COLUMNS (
name VARCHAR(255) PATH '$.name',
type VARCHAR(50) PATH '$.type',
weight INT PATH '$.weight'
)
) AS json_table;
Resultaat:
+------+------+--------+ | name | type | weight | +------+------+--------+ | Wag | Dog | 20 | | Bark | Dog | 10 | | Meow | Cat | 7 | +------+------+--------+
Hier noemen we elke kolom voor de tabel, specificeren het gegevenstype en specificeren vervolgens het pad van het JSON-document dat van toepassing is op die kolom.
Dus noemden we onze eerste kolom naam
, en vervolgens het knooppunt met de naam name
in kaart gebracht van het JSON-document naar die kolom.
Ordinaliteitskolommen
De VOOR ORDINALITEIT
optie kan worden gebruikt om de rijen te tellen, beginnend bij 1
.
SET @json_document = '
[
{ "name": "Scratch", "type": "Cat", "weight": 8 },
{ "name": "Bruce", "type": "Kangaroo", "weight": 100 },
{ "name": "Hop", "type": "Kangaroo", "weight": 130 }
]
';
SELECT * FROM JSON_TABLE(@json_document, '$[*]'
COLUMNS (
id FOR ORDINALITY,
name VARCHAR(255) PATH '$.name',
type VARCHAR(50) PATH '$.type',
weight INT PATH '$.weight'
)
) AS json_table;
Resultaat:
+------+---------+----------+--------+ | id | name | type | weight | +------+---------+----------+--------+ | 1 | Scratch | Cat | 8 | | 2 | Bruce | Kangaroo | 100 | | 3 | Hop | Kangaroo | 130 | +------+---------+----------+--------+
Het bestaan van een pad controleren
U kunt de EXISTS
. gebruiken clausule om te controleren op het bestaan van een pad. Als het pad in het JSON-document bestaat, is het resultaat 1
. Als het niet bestaat, 0
wordt geretourneerd.
SET @json_document = '
[
{ "name": "Punch", "type": "Kangaroo", "weight": 200 },
{ "name": "Snap", "type": "Cat", "weight": 12 },
{ "name": "Ruff", "type": "Dog" }
]
';
SELECT * FROM JSON_TABLE(@json_document, '$[*]'
COLUMNS (
name VARCHAR(255) PATH '$.name',
type VARCHAR(50) PATH '$.type',
has_weight INT EXISTS PATH '$.weight'
)
) AS json_table;
Resultaat:
+-------+----------+------------+ | name | type | has_weight | +-------+----------+------------+ | Punch | Kangaroo | 1 | | Snap | Cat | 1 | | Ruff | Dog | 0 | +-------+----------+------------+
Geneste paden
Het GENEST PAD
clausule kunt u omgaan met geneste JSON-documenten. Wanneer u deze clausule gebruikt, worden geneste JSON-structuren geconverteerd naar meerdere rijen.
Voorbeeld:
SET @json_document = '
[
{ "product": "Left Handed Screwdriver", "sizes": [ "S", "M", "L" ] },
{ "product": "Long Weight", "sizes": [ "S", "L", "XL" ] },
{ "product": "Bottomless Coffee Cup" }
]
';
SELECT * FROM JSON_TABLE(@json_document, '$[*]'
COLUMNS (
product VARCHAR(255) PATH '$.product',
NESTED PATH '$.sizes[*]' columns (
size VARCHAR(2) PATH '$'
)
)
) AS json_table;
Resultaat:
+-------------------------+------+ | product | size | +-------------------------+------+ | Left Handed Screwdriver | S | | Left Handed Screwdriver | M | | Left Handed Screwdriver | L | | Long Weight | S | | Long Weight | L | | Long Weight | XL | | Bottomless Coffee Cup | NULL | +-------------------------+------+
Omgaan met lege paden
De ON LEEG
clausule specificeert wat er zal gebeuren als het element gespecificeerd door het zoekpad ontbreekt in het JSON-document.
Voorbeeld:
SET @json_document = '
[
{ "name": "Punch", "type": "Kangaroo", "weight": 200 },
{ "name": "Snap", "type": "Cat", "weight": 12 },
{ "name": "Ruff"}
]
';
SELECT * FROM JSON_TABLE(@json_document, '$[*]'
COLUMNS (
name VARCHAR(255) PATH '$.name',
type VARCHAR(50) PATH '$.type' DEFAULT "N/A" ON EMPTY,
weight INT PATH '$.weight'
)
) AS json_table;
Resultaat:
+-------+----------+--------+ | name | type | weight | +-------+----------+--------+ | Punch | Kangaroo | 200 | | Snap | Cat | 12 | | Ruff | N/A | NULL | +-------+----------+--------+
In dit voorbeeld, Kemmel
heeft geen typeveld en daarom N/A
wordt teruggestuurd. Dit komt omdat ik heb opgegeven dat in de ON EMPTY
clausule voor dat veld.
Omgaan met fouten
De ON ERROR
clausule specificeert wat er moet gebeuren als er een JSON-structuurfout optreedt bij het extraheren van de waarde uit het document.
Een JSON-structuurfout treedt alleen op wanneer u probeert een niet-scalaire JSON (array of object) om te zetten in een scalaire waarde. Wanneer de ON ERROR
clausule is niet aanwezig, NULL ON ERROR
wordt geïmpliceerd.
Hier is een voorbeeld van het afhandelen van een JSON-structuurfout:
SET @json_document = '
[
{ "product": "Left Handed Screwdriver", "sizes": [ "S", "M", "L" ] },
{ "product": "Long Weight", "sizes": [ "S", "L", "XL" ] },
{ "product": "Bottomless Coffee Cup" }
]
';
SELECT * FROM JSON_TABLE(@json_document, '$[*]'
COLUMNS (
product VARCHAR(255) PATH '$.product',
sizes VARCHAR(5) PATH '$.sizes'
DEFAULT 'Oops!' ON ERROR
DEFAULT 'None' ON EMPTY
)
) AS json_table;
Resultaat:
+-------------------------+-------+ | product | sizes | +-------------------------+-------+ | Left Handed Screwdriver | Oops! | | Long Weight | Oops! | | Bottomless Coffee Cup | None | +-------------------------+-------+
Hier heb ik een string gespecificeerd (Oeps!
) om te gebruiken wanneer er een JSON-structuurfout is opgetreden.
In dit geval heb ik ook de ON LEEG
clausule. Dit toont aan dat zowel de ON ERROR
en de ON LEEG
clausule kan in dezelfde verklaring worden gebruikt.
Het is echter belangrijk op te merken dat een conversiefout van het datatype (bijvoorbeeld een poging om een niet-gehele waarde op te slaan in een integer veld of een varchar-kolom die wordt afgekapt) niet wordt beschouwd als een JSON-fout en dus niet de OP FOUT
clausule. In plaats daarvan zal het waarschuwingen produceren.
Hier is een voorbeeld om te illustreren wat ik bedoel:
SET @json_document = '
[
{ "name": "Punch", "type": "Kangaroo" },
{ "name": "Snap", "type": "Cat" },
{ "name": "Ruff", "type": "Dog" }
]
';
SELECT * FROM JSON_TABLE(@json_document, '$[*]'
COLUMNS (
name VARCHAR(255) PATH '$.name',
type INT PATH '$.type' DEFAULT 'Oops!' ON ERROR
)
) AS json_table;
Resultaat:
+-------+------+ | name | type | +-------+------+ | Punch | 0 | | Snap | 0 | | Ruff | 0 | +-------+------+ 3 rows in set, 3 warnings (0.000 sec)
Laten we de waarschuwingen tonen:
SHOW WARNINGS;
Resultaat:
+---------+------+---------------------------------------------------------------------------------+ | Level | Code | Message | +---------+------+---------------------------------------------------------------------------------+ | Warning | 1366 | Incorrect integer value: 'Kangaroo' for column ``.`(temporary)`.`type` at row 1 | | Warning | 1366 | Incorrect integer value: 'Cat' for column ``.`(temporary)`.`type` at row 2 | | Warning | 1366 | Incorrect integer value: 'Dog' for column ``.`(temporary)`.`type` at row 3 | +---------+------+---------------------------------------------------------------------------------+