json_decode($json, true) trasforma una stringa JSON in valori PHP, con ogni oggetto JSON come array associativo. Ometti true e gli oggetti JSON diventano invece oggetti stdClass, letti con ->. Un JSON non valido dà null.
Output:
Ada
js
Ada
php
Array
(
[name] => Ada
[age] => 36
[langs] => Array
(
[0] => php
[1] => js
)
[admin] => 1
)
Gli array JSON diventano sempre liste PHP, qualunque modalità tu scelga. Per la direzione opposta, da PHP a JSON, c'è json_encode().
Array associativo o oggetto: true vs false
Entrambe le modalità contengono gli stessi dati; scegli quella che si legge meglio nel tuo codice. Gli array funzionano con ogni funzione per array (array_column, array_map, isset($data['key'])), quindi la maggior parte del codice passa true. Gli oggetti richiedono la sintassi con le graffe per le chiavi che non sono nomi di proprietà validi, come chiavi con un trattino o un numero:
Output:
Ada zero London
Ada zero London
object(stdClass)#2 (1) {
["city"]=>
string(6) "London"
}
Il quarto parametro accetta dei flag. Anche JSON_OBJECT_AS_ARRAY dà array, ma solo finché il secondo argomento è null (il suo default): json_decode($json, flags: JSON_OBJECT_AS_ARRAY) restituisce array, mentre json_decode($json, false, 512, JSON_OBJECT_AS_ARRAY) restituisce ancora oggetti.
Scorrere un JSON annidato
Le risposte delle API sono di solito una lista di oggetti dentro un oggetto. Decodifica una volta, poi percorrila con foreach, e usa ?? per i campi che potrebbero mancare:
Output:
#1 Ada <ada@example.com> roles: admin, editor
#2 Linus <no email> roles: none
#3 Grace <grace@example.com> roles: editor
Array
(
[1] => Ada
[2] => Linus
[3] => Grace
)
Gestire un JSON non valido
json_decode() restituisce null per un JSON non valido, ma null è anche il risultato corretto per il testo JSON null, quindi null da solo non ti dice se è fallito. json_last_error_msg() dà il motivo dell'ultima chiamata. Il modo più pulito è JSON_THROW_ON_ERROR, che lancia una JsonException:
Output:
NULL
Syntax error
NULL
No error
Invalid JSON: Syntax error
Il terzo argomento, 512, è la profondità massima di annidamento (il default). Con gli argomenti con nome puoi saltarlo: json_decode($json, true, flags: JSON_THROW_ON_ERROR).
Verificare se una stringa è un JSON valido con json_validate()
PHP 8.3 ha aggiunto json_validate(). Risponde true o false senza costruire gli array decodificati, quindi usa meno memoria della decodifica quando ti serve solo un sì o un no, per esempio per rifiutare subito il corpo di una richiesta:
Output:
'{"a": 1}' valid
'[1, 2, 3]' valid
'"text"' valid
'{a: 1}' invalid: Syntax error
'{\'a\': 1}' invalid: Syntax error
'' invalid: Syntax error
Se userai comunque i dati, salta json_validate() e decodifica con JSON_THROW_ON_ERROR: validare prima analizza la stringa due volte.
Leggere un file JSON
Leggi il file con file_get_contents() e decodifica la stringa. Questo blocco scrive prima settings.json così c'è un file da leggere:
Output:
Theme: dark
Plugins: 2
{
"theme": "dark",
"fontSize": 16,
"plugins": [
"git",
"lint"
]
}
Perché json_decode restituisce null: le cause abituali
Il JSON è più rigoroso della sintassi degli array di JavaScript e PHP. Ogni stringa qui sotto sembra ragionevole e ognuna restituisce null. Eseguilo per vedere il motivo di ciascuna, poi correggine una ed eseguilo di nuovo:
Output:
single quotes Syntax error
unquoted key Syntax error
trailing comma Syntax error
comment Syntax error
byte order mark Syntax error
too deep Maximum stack depth exceeded
float(1.2345678901234567E+19)
string(20) "12345678901234567890"
Un byte order mark è invisibile nella maggior parte degli editor ed è il motivo classico per cui un file JSON "sembra a posto" ma non si decodifica. Toglilo con $text = preg_replace('/^\xEF\xBB\xBF/', '', $text); prima di decodificare.
Domande frequenti
Come converto un JSON in un array in PHP?
Passa true come secondo argomento: json_decode('{"name":"Ada"}', true) restituisce ['name' => 'Ada'], quindi leggi i valori con $data['name']. Senza true, gli oggetti JSON diventano oggetti stdClass e scrivi $data->name.
Perché json_decode restituisce null?
Il JSON non è valido (apici singoli, una virgola finale, chiavi senza virgolette, un byte order mark), è annidato oltre il limite di profondità, oppure il JSON è davvero null. Controlla json_last_error_msg(), oppure decodifica con JSON_THROW_ON_ERROR per ottenere una JsonException con il motivo.
Come verifico se una stringa è un JSON valido in PHP?
Da PHP 8.3, json_validate($string) restituisce true o false senza costruire il valore decodificato. Nelle versioni precedenti, decodificala e verifica json_last_error() === JSON_ERROR_NONE.
Come leggo un file JSON in PHP?
Leggi il file, poi decodificalo: $data = json_decode(file_get_contents('data.json'), true, flags: JSON_THROW_ON_ERROR);. file_get_contents() restituisce false se il file manca, quindi verificalo prima.
Come accedo a una chiave JSON con un trattino in PHP?
Decodifica in un array e usa $data['first-name'], oppure con gli oggetti usa le graffe: $obj->{'first-name'}. La stessa sintassi con le graffe funziona per le chiavi che sono numeri, come $obj->{'0'}.