MariaDB
 sql >> Base de données >  >> RDS >> MariaDB

MariaDB JSON_TABLE() expliqué

Dans MariaDB, JSON_TABLE() est une fonction intégrée qui convertit les données JSON en une forme relationnelle.

En d'autres termes, il vous permet de renvoyer un document JSON sous forme de tableau.

Le JSON_TABLE() la fonction a été introduite dans MariaDB 10.6.0.

Syntaxe

La syntaxe ressemble à ceci :

JSON_TABLE(json_doc, 
          context_path COLUMNS (column_list)
) [AS] alias

column_list va comme ceci :

column[, column][, ...]

column va comme ceci :

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)

on_empty va comme ceci :

{NULL | DEFAULT string | ERROR} ON EMPTY

Et on_error va comme ceci :

{NULL | DEFAULT string | ERROR} ON ERROR

Exemple

Voici un exemple pour illustrer.

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;

Résultat :

+------+------+--------+
| name | type | weight |
+------+------+--------+
| Wag  | Dog  |     20 |
| Bark | Dog  |     10 |
| Meow | Cat  |      7 |
+------+------+--------+

Ici, nous nommons chaque colonne de la table, spécifions son type de données, puis spécifions le chemin du document JSON qui s'appliquera à cette colonne.

Donc, nous avons appelé notre première colonne name , puis mappé le nœud appelé name du document JSON à cette colonne.

Colonnes d'ordinanalité

Le FOR ORDINALITY l'option peut être utilisée pour compter les lignes, à partir de 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;

Résultat :

+------+---------+----------+--------+
| id   | name    | type     | weight |
+------+---------+----------+--------+
|    1 | Scratch | Cat      |      8 |
|    2 | Bruce   | Kangaroo |    100 |
|    3 | Hop     | Kangaroo |    130 |
+------+---------+----------+--------+

Vérification de l'existence d'un chemin

Vous pouvez utiliser le EXISTS clause pour vérifier l'existence d'un chemin. Si le chemin existe dans le document JSON, le résultat est 1 . S'il n'existe pas, 0 est renvoyé.

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;

Résultat :

+-------+----------+------------+
| name  | type     | has_weight |
+-------+----------+------------+
| Punch | Kangaroo |          1 |
| Snap  | Cat      |          1 |
| Ruff  | Dog      |          0 |
+-------+----------+------------+

Chemins imbriqués

Le NESTED PATH La clause vous permet de traiter des documents JSON imbriqués. Lorsque vous utilisez cette clause, elle convertit les structures JSON imbriquées en plusieurs lignes.

Exemple :

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;

Résultat :

+-------------------------+------+
| 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 |
+-------------------------+------+

Traitement des chemins vides

Le ON EMPTY La clause spécifie ce qui sera fait lorsque l'élément spécifié par le chemin de recherche est manquant dans le document JSON.

Exemple :

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;

Résultat :

+-------+----------+--------+
| name  | type     | weight |
+-------+----------+--------+
| Punch | Kangaroo |    200 |
| Snap  | Cat      |     12 |
| Ruff  | N/A      |   NULL |
+-------+----------+--------+

Dans cet exemple, Ruff n'a pas de champ de type et donc N/A est retourné. C'est parce que j'ai spécifié cela dans le ON EMPTY clause pour ce champ.

Traitement des erreurs

Le ON ERROR La clause spécifie ce qui doit être fait si une erreur de structure JSON se produit lors de la tentative d'extraction de la valeur du document.

Une erreur de structure JSON se produit uniquement lorsque vous tentez de convertir un JSON non scalaire (tableau ou objet) en une valeur scalaire. Lorsque ON ERROR la clause n'est pas présente, NULL ON ERROR est implicite.

Voici un exemple de gestion d'une erreur de structure JSON :

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;

Résultat :

+-------------------------+-------+
| product                 | sizes |
+-------------------------+-------+
| Left Handed Screwdriver | Oops! |
| Long Weight             | Oops! |
| Bottomless Coffee Cup   | None  |
+-------------------------+-------+

Ici, j'ai spécifié une chaîne (Oops! ) à utiliser chaque fois qu'une erreur de structure JSON s'est produite.

Dans ce cas, j'ai également inclus le ON EMPTY clause. Cela démontre que le ON ERROR et le ON EMPTY clause peut être utilisée dans la même instruction.

Cependant, il est important de noter qu'une erreur de conversion de type de données (par exemple, une tentative de stockage d'une valeur non entière dans un champ entier ou une colonne varchar tronquée) n'est pas considérée comme une erreur JSON et ne déclenchera donc pas le ON ERROR clause. Au lieu de cela, il produira des avertissements.

Voici un exemple pour illustrer ce que je veux dire :

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;

Résultat :

+-------+------+
| name  | type |
+-------+------+
| Punch |    0 |
| Snap  |    0 |
| Ruff  |    0 |
+-------+------+
3 rows in set, 3 warnings (0.000 sec)

Montrons les avertissements :

SHOW WARNINGS;

Résultat :

+---------+------+---------------------------------------------------------------------------------+
| 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      |
+---------+------+---------------------------------------------------------------------------------+