json_decode($json, true) macht aus einem JSON-String PHP-Werte, mit jedem JSON-Objekt als assoziativem Array. Lass true weg, dann werden JSON-Objekte stattdessen zu stdClass-Objekten, die du mit -> liest. Ungültiges JSON ergibt null.
Ausgabe:
Ada
js
Ada
php
Array
(
[name] => Ada
[age] => 36
[langs] => Array
(
[0] => php
[1] => js
)
[admin] => 1
)
JSON-Arrays werden immer zu PHP-Listen, egal welchen Modus du wählst. Die andere Richtung, von PHP zu JSON, ist json_encode().
Assoziatives Array oder Objekt: true vs false
Beide Modi enthalten dieselben Daten; wähl den, der sich in deinem Code besser liest. Arrays funktionieren mit jeder Array-Funktion (array_column, array_map, isset($data['key'])), deshalb übergeben die meisten true. Objekte brauchen die Klammersyntax für Schlüssel, die keine gültigen Eigenschaftsnamen sind, etwa Schlüssel mit Bindestrich oder Zahlen:
Ausgabe:
Ada zero London
Ada zero London
object(stdClass)#2 (1) {
["city"]=>
string(6) "London"
}
Der vierte Parameter nimmt Flags. JSON_OBJECT_AS_ARRAY liefert ebenfalls Arrays, aber nur, solange das zweite Argument null ist (sein Standardwert): json_decode($json, flags: JSON_OBJECT_AS_ARRAY) liefert Arrays, während json_decode($json, false, 512, JSON_OBJECT_AS_ARRAY) weiterhin Objekte liefert.
Über verschachteltes JSON iterieren
API-Antworten sind meist eine Liste von Objekten in einem Objekt. Dekodiere einmal, lauf dann mit foreach durch und verwende ?? für Felder, die fehlen könnten:
Ausgabe:
#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
)
Ungültiges JSON behandeln
json_decode() liefert null für ungültiges JSON, aber null ist auch das korrekte Ergebnis für den JSON-Text null, also verrät null allein nicht, ob es gescheitert ist. json_last_error_msg() nennt den Grund des letzten Aufrufs. Der sauberere Weg ist JSON_THROW_ON_ERROR, das eine JsonException wirft:
Ausgabe:
NULL
Syntax error
NULL
No error
Invalid JSON: Syntax error
Das dritte Argument, 512, ist die maximale Verschachtelungstiefe (der Standard). Mit benannten Argumenten kannst du es überspringen: json_decode($json, true, flags: JSON_THROW_ON_ERROR).
Mit json_validate() prüfen, ob ein String gültiges JSON ist
PHP 8.3 brachte json_validate(). Es antwortet mit true oder false, ohne die dekodierten Arrays aufzubauen, und braucht deshalb weniger Speicher als das Dekodieren, wenn du nur ein Ja oder Nein brauchst, etwa um einen Request-Body früh abzulehnen:
Ausgabe:
'{"a": 1}' valid
'[1, 2, 3]' valid
'"text"' valid
'{a: 1}' invalid: Syntax error
'{\'a\': 1}' invalid: Syntax error
'' invalid: Syntax error
Wenn du die Daten sowieso verwendest, lass json_validate() weg und dekodiere mit JSON_THROW_ON_ERROR: Vorher zu validieren parst den String zweimal.
Eine JSON-Datei lesen
Lies die Datei mit file_get_contents() und dekodiere den String. Dieser Block schreibt zuerst settings.json, damit es eine Datei zum Lesen gibt:
Ausgabe:
Theme: dark
Plugins: 2
{
"theme": "dark",
"fontSize": 16,
"plugins": [
"git",
"lint"
]
}
Warum json_decode null liefert: die üblichen Ursachen
JSON ist strenger als JavaScript und als die Array-Syntax von PHP. Jeder String unten sieht vernünftig aus, und jeder liefert null. Führe es aus, um den Grund für jeden zu sehen, korrigiere dann einen und führe es erneut aus:
Ausgabe:
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"
Eine Byte Order Mark ist in den meisten Editoren unsichtbar und der klassische Grund, warum eine JSON-Datei „gut aussieht“, sich aber nicht dekodieren lässt. Entferne sie vor dem Dekodieren mit $text = preg_replace('/^\xEF\xBB\xBF/', '', $text);.
Häufig gestellte Fragen
Wie wandle ich in PHP JSON in ein Array um?
Übergib true als zweites Argument: json_decode('{"name":"Ada"}', true) liefert ['name' => 'Ada'], also liest du Werte mit $data['name']. Ohne true werden JSON-Objekte zu stdClass-Objekten, und du schreibst $data->name.
Warum liefert json_decode null?
Das JSON ist ungültig (einfache Anführungszeichen, ein Komma am Ende, Schlüssel ohne Anführungszeichen, eine Byte Order Mark), es ist tiefer verschachtelt als das Tiefenlimit, oder das JSON ist wirklich null. Prüfe json_last_error_msg() oder dekodiere mit JSON_THROW_ON_ERROR, um eine JsonException mit dem Grund zu bekommen.
Wie prüfe ich in PHP, ob ein String gültiges JSON ist?
Seit PHP 8.3 liefert json_validate($string) true oder false, ohne den dekodierten Wert aufzubauen. In älteren Versionen dekodierst du und prüfst json_last_error() === JSON_ERROR_NONE.
Wie lese ich in PHP eine JSON-Datei?
Lies die Datei und dekodiere sie dann: $data = json_decode(file_get_contents('data.json'), true, flags: JSON_THROW_ON_ERROR);. file_get_contents() liefert false, wenn die Datei fehlt, also prüfst du das zuerst.
Wie greife ich in PHP auf einen JSON-Schlüssel mit Bindestrich zu?
Dekodiere in ein Array und verwende $data['first-name'], oder bei Objekten geschweifte Klammern: $obj->{'first-name'}. Dieselbe Klammersyntax funktioniert für Schlüssel, die Zahlen sind, etwa $obj->{'0'}.