5
votes

PHP: regex dans JSON pose un problème pour json_decode?

J'ai des expressions régulières dans mon JSON, ce qui ne semble pas poser de problème lorsque je teste mon JSON sur un validateur JSON en ligne. Cependant, lorsque je prends cette chaîne JSON et que j'essaye de json_decode () en PHP, j'obtiens un JSON_ERROR_SYNTAX .

Des idées pourquoi? Et comment résoudre ce problème?

Exemple de code:

<?php

$json = <<<EOD
{
  "regex": [
    "Hello\s+World"
  ]
}
EOD;

json_decode($json);

switch (json_last_error()) {
    case JSON_ERROR_NONE:
        echo ' - No errors';
    break;
    case JSON_ERROR_DEPTH:
        echo ' - Maximum stack depth exceeded';
    break;
    case JSON_ERROR_STATE_MISMATCH:
        echo ' - Underflow or the modes mismatch';
    break;
    case JSON_ERROR_CTRL_CHAR:
        echo ' - Unexpected control character found';
    break;
    case JSON_ERROR_SYNTAX:
        echo ' - Syntax error, malformed JSON';
    break;
    case JSON_ERROR_UTF8:
        echo ' - Malformed UTF-8 characters, possibly incorrectly encoded';
    break;
    default:
        echo ' - Unknown error';
    break;
}

Le problème est dans le \ s . Le changer en \\ s n'aide pas.


2 commentaires

Quel validateur JSON en ligne valide celui de cette question?


Jetez un œil à ce package . Vous pouvez facilement convertir un tableau en chaîne JSON en l'utilisant.


3 Réponses :


7
votes

Lorsque vous écrivez "\ s" en PHP, la chaîne littérale est \ s car \ s n'est pas une séquence d'échappement valide.

p> Lorsque vous écrivez "\\ s" en PHP, la chaîne littérale est \ s car \\ est une séquence d'échappement valide.

JSON, d'autre part, générera une erreur pour les séquences d'échappement non valides, ce qui est votre problème.

La solution: N'écrivez pas JSON à la main.

$json = json_encode(['regex'=> ['Hello\s+World']]);

Sortie: {"regex": ["Hello \\ s + World"]} [note: chaîne littérale, JSON valide]

La mauvaise solution qui pose plus de problèmes qu'elle n'en vaut la peine et causera probablement des problèmes sur toute la ligne: "Bonjour \\\ s + World " Bienvenue à fuir l'enfer.


2 commentaires

Quand je json_decode comme tableau JSON, j'attends un tableau PHP en retour. Je reçois une chaîne. Avez-vous une idée de ce qui passe?


Votre tableau a probablement été encodé plusieurs fois. Montrez votre JSON de départ.



2
votes

Votre chaîne "Hello \ s + World" doit être échappée comme "Hello \\\ s + World" . Le premier échappement \ est pour échapper le deuxième échappement \ qui échappe \ s .

Et puis si vous voulez avoir un tableau dans sortie, vous devez définir assoc = true comme deuxième paramètre pour la fonction json_decode () .

En savoir plus sur json_decode () code> dans la documentation .

Solution

Consultez la DEMO de mon code.

<?php
$json = '{"regex":["Hello\\\s+World"]}';

$obj1 = json_decode($json);
echo $obj1->regex[0]."<br>";

$obj2 = json_decode($json, true); //When assoc == TRUE, returned objects will be converted into associative arrays.
echo $obj2["regex"][0];
?>

Comment échapper à tous les caractères de contrôle JSON:


0 commentaires

1
votes

En raison d'un problème de regex potentiellement complexe et de double échappement, vous n'obtenez pas le littéral de chaîne que vous attendez.

Cela devrait fonctionner pour n'importe quelle expression régulière:

string(13) "Hello\s+World"

sortie

$regex1 = <<<EOD
Hello\s+World
EOD;

$obj = new stdClass();
$obj->regex = array();
$obj->regex[] = $regex1;

$json = json_encode($obj);

$decoded = json_decode($json);

var_dump($decoded->regex[0]);


0 commentaires