PHP: полный мануал с примерами, функциями и ООП
Практический мануал PHP: от переменных и читаемого кода до безопасных форм, интеграций, базы данных и ООП на примере магазина. Учебный маршрут, поиск функций, подробные примеры, разбор ошибок и исходники для скачивания.

Дерево руководства
Глава 149 · С нуля → справочник
JSON: функции, флаги, ошибки и формат обмена
Полная категория JSON: кодирование и разбор, проверка синтаксиса, все флаги и коды ошибок, JsonException и публичное представление объектов.
JSON — общий текстовый формат для разных программ
Из числа 0 в JSON-текст и обратно
Первый опыт не требует ни массива, ни сети. Он показывает смену представления одного и того же остатка товара.
- 1$stock = 0↓
PHP хранит int: целое число.
- 2json_encode($stock)↓
Возвращает string "0" — текст из одного байта.
- 3$text = …↓
Строка сохранена; транспорт или файл могут передать её другой программе.
- 4json_decode($text)↓
Разбирает текст и возвращает PHP int 0.
- 5$restored = …
var_dump показывает int(0), а не строку.
JSON-кодирование и декодирование не выполняют HTTP-запросы. Правильный синтаксис не доказывает, что пришёл допустимый заказ или показание датчика.
PHP-массив живёт внутри PHP. Мобильное приложение, Node.js и контроллер на объекте не умеют читать его внутреннее устройство. Они договариваются передавать текст в известном формате — например JSON. json_encode создаёт такой текст из PHP-значения; json_decode читает текст и создаёт PHP-значение. Ни одна из этих функций сама не отправляет HTTP-запрос.
- PHP: $stock = 0 — целое число.
- json_encode($stock) → PHP-строка "0", содержащая JSON-число.
- Передача/хранение — отдельный шаг, которого в первом опыте нет.
- json_decode($text) → снова PHP int 0.
<?php
$stock = 0;
$text = json_encode($stock);
var_dump($text);
$restored = json_decode($text);
var_dump($restored);
Ожидаемый результат
string(1) "0"
int(0)
Вызов справа от = вычисляется первым, затем результат сохраняется в переменной слева. Кодирование вернуло строку; декодирование прочитало её и вернуло число. var_dump показывает типы, которые обычный echo визуально не различил бы. Здесь маленький заранее известный вход; работу с ошибками добавим отдельно.
Если вы ещё не работали с вложенными структурами, сначала пройдите JSON-текст → массив → чтение полей. Далее этот справочник раскрывает весь договор расширения, а не заменяет начальный урок сложным примером.
Какие значения можно передавать
| В JSON | После json_decode | Прикладной смысл |
|---|---|---|
| null | null | Значение явно неизвестно или отсутствует по договору поля. |
| true / false | bool | Флаг; не строки "true" и "false". |
| Число | int либо float | Очень большое целое может потерять точность без отдельного правила. |
| Строка в двойных кавычках | string UTF-8 | Имя, код, телефон, дата; у JSON нет отдельного типа даты. |
| [элементы] | array со списком | Последовательность заказов. |
| {"имя": значение} | stdClass либо array по associative | Набор именованных полей. JSON-объект не создаёт ваш класс Order. |
- JSON null → PHP null.
- JSON false → PHP bool false.
- JSON-строка "0041" → PHP string с сохранёнными нулями.
- JSON [4,1] → PHP array с двумя целыми значениями.
<?php
var_dump(json_decode('null'));
var_dump(json_decode('false'));
var_dump(json_decode('"0041"'));
var_dump(json_decode('[4, 1]'));
Ожидаемый результат
NULL
bool(false)
string(4) "0041"
array(2) {
[0]=>
int(4)
[1]=>
int(1)
}
Внешние одинарные кавычки относятся к PHP; внутренние двойные — к JSON. Для строки "0041" двойные кавычки являются частью переданного JSON-текста. JSON не поддерживает комментарии, одинарные кавычки вместо двойных, запятую после последнего элемента, NaN и Infinity.
Синтаксически верный документ ещё не заказ. Приложение отдельно требует объект, ключи, типы, диапазоны и доступ к данным. Повторяющиеся имена полей опасны при обмене между разными парсерами: PHP оставляет последнее значение. JSON-функции не дают встроенного режима «запретить дубликаты имён». Не проверяйте это регулярным выражением; для соответствующего протокола нужен парсер с такой политикой.
Установка, версии и точность чисел
В PHP 8 JSON является обязательным расширением и всегда включён. В более старых сборках его можно было отключить. json_encode/json_decode появились в PHP 5.2, json_last_error — 5.3, JsonSerializable — 5.4, текст ошибки — 5.5, JsonException и JSON_THROW_ON_ERROR — 7.3, json_validate — 8.3. Примеры последней функции требуют PHP 8.3+.
- Текущий процесс PHP → его собственный список расширений.
- extension_loaded("json") → true: JSON доступен.
- function_exists("json_validate") → проверка конкретной функции, добавленной в 8.3.
- Результаты проверок относятся к этому процессу, не к соседнему веб-серверу.
<?php
var_dump(extension_loaded("json"));
var_dump(function_exists("json_validate"));
Ожидаемый результат
bool(true)
bool(true)
Ожидаемый результат относится к проверяемому PHP 8.5. На PHP 8.2 первая проверка истинна, вторая ложна. Если всё равно нужны данные, json_decode с обработкой ошибок подходит и без отдельного validate.
С PHP 7.1 формат float при кодировании зависит от serialize_precision; обычное значение −1 выбирает необходимое представление. Это не делает двоичные дроби точной десятичной арифметикой. Деньги передавайте целыми минимальными единицами или согласованной десятичной строкой. Большой ID лучше объявлять строкой ещё в API: JSON_BIGINT_AS_STRING защищает только целые числа при декодировании в PHP и не исправит точность, уже потерянную источником.
Две модели ошибки: результат или исключение
У json_encode без специальных флагов ошибка возвращает false; у json_decode — null. Но null бывает и правильным JSON-значением. В старом стиле сразу после вызова читают json_last_error. В новом коде удобно указать JSON_THROW_ON_ERROR и перехватить JsonException: успешный null тогда не смешивается с ошибкой разбора.
- json_decode($body, true, 16, JSON_THROW_ON_ERROR) начинает разбор.
- Текст повреждён → выбрасывается JsonException, присваивание $data не завершается.
- catch получает объект $error → код ошибки из getCode().
- Обработчик выбирает понятный отказ; ошибочный ответ не превращается в пустой заказ.
<?php
foreach (['null', '{broken'] as $body) {
try {
$data = json_decode($body, true, 16, JSON_THROW_ON_ERROR);
var_dump($data);
} catch (JsonException $error) {
echo "Документ не разобран\n";
var_dump($error->getCode() === JSON_ERROR_SYNTAX);
}
}
Ожидаемый результат
NULL
Документ не разобран
bool(true)
foreach по очереди подставляет два текста. try отмечает действие, в котором возможна ошибка; catch принимает исключение. getCode() — метод объекта ошибки, возвращающий её числовую категорию. Сравниваем её с именованной константой, а не с угаданной цифрой. Флаг объединяется с другими через |, а не через логическое ||.
У json_decode и json_validate значение depth вне допустимого диапазона даёт ValueError — это ошибка настройки вызова, а не испорченный документ. У json_encode поведение другое: превышение предела при обходе структуры относится к JSON_ERROR_DEPTH; скаляр вообще не требует такого обхода. Задавайте положительный предел и не рассчитывайте на общий для всех функций ValueError. Нарушение типа параметра может дать TypeError. Пользовательский jsonSerialize способен сам выбросить исключение; JSON_THROW_ON_ERROR не превращает все ошибки приложения в JsonException. Подробности try/catch и исключений нужны после первого понятного вызова, а не вместо него.
JsonException: что хранится в объекте ошибки
JsonException наследует Exception. Его создаёт JSON-операция с JSON_THROW_ON_ERROR при ошибке данных. Наследование здесь полезно: у разных ошибок общий способ получить сообщение, код, файл и цепочку причин. Приложение может обработать именно JSON-сбой, а выше по уровню — общий сбой импорта.
| Часть Exception | Для чего у JsonException |
|---|---|
| getCode() | Категория JSON_ERROR_*; сравнивайте с константой. |
| getMessage() | Текст для диагностики; не договор для ветвления и не обязательно готовое сообщение пользователю. |
| getFile(), getLine() | Где выброшено исключение. Пути сервера не нужно показывать посетителю. |
| getTrace(), getTraceAsString() | Стек вызовов как массив либо текст. В аргументах могут быть чувствительные данные. |
| getPrevious() | Предыдущее исключение при передаче причины через конструктор. |
| __construct(message, code, previous) | Позволяет создать объект ошибки; обычно JsonException создаёт сама JSON-функция. |
| __toString() | Подробное текстовое представление для разработки; не публичный HTTP-ответ. |
| __clone() | Закрыт: объекты исключений не предназначены для клонирования. |
Служебные свойства message, code, file, line защищены, string, trace, previous закрыты. Читайте их указанными методами. Смысл этих областей видимости одинаков и в собственных классах.
- readSupplierPayload("{broken") → json_decode.
- Повреждённый документ → JsonException в $cause.
- Новый RuntimeException хранит понятное сообщение и previous=$cause.
- Внешний catch получает RuntimeException; getPrevious() возвращает исходный JsonException.
<?php
function readSupplierPayload(string $body): mixed
{
try {
return json_decode($body, true, 32, JSON_THROW_ON_ERROR);
} catch (JsonException $cause) {
throw new RuntimeException("Поставщик вернул неверный JSON", 0, $cause);
}
}
try {
readSupplierPayload('{broken');
} catch (RuntimeException $error) {
echo $error->getMessage(), "\n";
var_dump($error->getPrevious() instanceof JsonException);
}
Ожидаемый результат
Поставщик вернул неверный JSON
bool(true)
Верхний уровень узнаёт, какая операция сорвалась, а диагностический код при необходимости читает исходный JsonException через getPrevious. Тело ответа и токены не добавляются в сообщение. instanceof проверяет принадлежность объекта классу. Сетевого запроса здесь нет: мы проверяем разбор уже полученного тела.
Флаги: выбирать по договору, а не включать все сразу
Флаг — именованное целое значение, включающее режим функции. Совместимые флаги объединяются побитовым |. Их номера не нужно запоминать или складывать вручную. У decode, encode и validate разные допустимые режимы.
| Флаг / где применяется | Что меняет и когда нужен |
|---|---|
| JSON_OBJECT_AS_ARRAY / decode | Создаёт массивы из JSON-объектов, если associative=null; явные true/false задают выбор прямо. |
| JSON_BIGINT_AS_STRING / decode | Сохраняет целые за пределами int строками. Не защищает дроби/экспоненту и не заставляет все ID стать строками. |
| JSON_HEX_TAG / encode | Представляет < и > через Unicode escape. |
| JSON_HEX_AMP / encode | Представляет & через Unicode escape. |
| JSON_HEX_APOS / encode | Представляет одинарную кавычку через Unicode escape. |
| JSON_HEX_QUOT / encode | Представляет двойную кавычку внутри строк через Unicode escape. |
| JSON_FORCE_OBJECT / encode | Превращает PHP-списки, включая пустые, в JSON-объекты; действует рекурсивно. Для одного пустого объекта лучше явно создать (object) []. |
| JSON_NUMERIC_CHECK / encode | Превращает числовые строки в числа. Может испортить телефон, артикул, ведущие нули и точность ID; задавайте типы полей заранее. |
| JSON_PRETTY_PRINT / encode | Добавляет читаемые отступы и переводы строк; увеличивает размер документа. |
| JSON_UNESCAPED_SLASHES / encode | Оставляет / без обратной косой черты. Смысл JSON-строки тот же. |
| JSON_UNESCAPED_UNICODE / encode | Оставляет Unicode-буквы буквами, а не последовательностями \uXXXX. Это оформление текста, не исправление кодировки. |
| JSON_UNESCAPED_LINE_TERMINATORS / encode, PHP 7.1+ | Вместе с UNESCAPED_UNICODE оставляет U+2028/U+2029 неэкранированными. Не включайте ради абстрактного «очистить JSON». |
| JSON_PRESERVE_ZERO_FRACTION / encode | Сохраняет .0 у float вроде 12.0. Не задаёт два знака после запятой и не решает денежную точность. |
| JSON_PARTIAL_OUTPUT_ON_ERROR / encode | Разрешает частичный результат с заменами неподдерживаемых значений. Имеет приоритет над THROW_ON_ERROR, поэтому может скрыть неполноту ответа. |
| JSON_INVALID_UTF8_IGNORE / encode, decode; validate / PHP 7.2+, validate 8.3+ | Пропускает некорректные UTF-8-байты. Данные меняются, а не становятся точным восстановлением исходного текста. |
| JSON_INVALID_UTF8_SUBSTITUTE / encode, decode / PHP 7.2+ | Заменяет неверные последовательности на U+FFFD. Подходит только при явно разрешённой потере данных; не принимается json_validate. |
| JSON_THROW_ON_ERROR / encode, decode / PHP 7.3+ | Бросает JsonException вместо записи кода ошибки в общее состояние. Не принимается json_validate. |
- Данные: name → Болт, path → /catalog/41.
- UNESCAPED_UNICODE оставляет буквы; UNESCAPED_SLASHES оставляет слеши.
- PRETTY_PRINT добавляет отступы; THROW задаёт путь ошибки.
- json_encode возвращает одну строку с теми же полями — флаги не отправляют её по сети.
<?php
$data = ["name" => "Болт", "path" => "/catalog/41"];
echo json_encode($data, JSON_THROW_ON_ERROR | JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES | JSON_PRETTY_PRINT);
Ожидаемый результат
{
"name": "Болт",
"path": "/catalog/41"
}Четыре режима собраны через |. Получился формат для просмотра человеком. Убирая PRETTY_PRINT, можно получить компактный текст с теми же данными. Не путайте визуально короткую запись со сжатием транспорта.
<?php
echo json_encode(12.0), "\n";
echo json_encode(12.0, JSON_PRESERVE_ZERO_FRACTION);
Ожидаемый результат
12
12.0Оба документа содержат JSON-число. Флаг сохраняет дробную форму float, но не обещает 12.00. Если внешний договор требует десятичную строку с двумя знаками, формируйте именно строковое поле по этому договору.
<?php
$data = ["sku" => "0041", "quantity" => 2];
echo json_encode($data, JSON_THROW_ON_ERROR), "\n";
echo json_encode($data, JSON_THROW_ON_ERROR | JSON_NUMERIC_CHECK);
Ожидаемый результат
{"sku":"0041","quantity":2}
{"sku":41,"quantity":2}Во втором ответе потеряны нули артикула. Правильный тип quantity уже int, ему флаг не нужен. Код товара и телефон должны оставаться строками, даже если состоят только из цифр.
<?php
$data = ["filters" => (object) [], "items" => []];
echo json_encode($data, JSON_THROW_ON_ERROR), "\n";
echo json_encode($data, JSON_THROW_ON_ERROR | JSON_FORCE_OBJECT);
Ожидаемый результат
{"filters":{},"items":[]}
{"filters":{},"items":{}}(object) [] создаёт пустой объект для одного поля. FORCE_OBJECT изменил и items, нарушив договор «массив товаров». Это видно ещё до реального HTTP-запроса.
<?php
$text = "A\xFFB";
echo json_encode($text, JSON_INVALID_UTF8_IGNORE), "\n";
echo json_encode($text, JSON_INVALID_UTF8_SUBSTITUTE);
Ожидаемый результат
"AB"
"A\ufffdB"\xFF обозначает байт, который здесь не является допустимым UTF-8. IGNORE удалил его, SUBSTITUTE оставил знак замены. Оба варианта теряют исходное содержимое; для подписанного пакета, ID или финансовых данных молчаливое исправление обычно неприемлемо.
<?php
$data = ["ratio" => INF];
echo json_encode($data, JSON_THROW_ON_ERROR | JSON_PARTIAL_OUTPUT_ON_ERROR), "\n";
var_dump(json_last_error() === JSON_ERROR_INF_OR_NAN);
Ожидаемый результат
{"ratio":0}
bool(true)
INF — бесконечность, у JSON такого числа нет. Частичный режим подставил 0, хотя математически это другое значение; исключение не выброшено. В передаче измерений лучше явно решить, означает ли ошибка отказ или отдельное поле null/status, и не скрывать её этим флагом.
Все категории JSON_ERROR_*
| Константа | Что выяснить при таком результате |
|---|---|
| JSON_ERROR_NONE | Последняя учитываемая операция завершилась без ошибки. |
| JSON_ERROR_DEPTH | Вложенность превысила заданный предел. Это отличается от недопустимого параметра depth. |
| JSON_ERROR_STATE_MISMATCH | Нарушена структура вложенности/режим парсера, например неправильное закрытие контейнера. |
| JSON_ERROR_CTRL_CHAR | Внутри строки оказался недопустимый неэкранированный управляющий символ. |
| JSON_ERROR_SYNTAX | JSON-синтаксис нарушен: одинарные кавычки, лишняя запятая, посторонний текст и другие случаи. |
| JSON_ERROR_UTF8 | Строковые данные не являются правильным UTF-8. |
| JSON_ERROR_RECURSION | При encode найдена циклическая ссылка. PARTIAL заменяет проблемное место на null. |
| JSON_ERROR_INF_OR_NAN | В encode попали INF/NAN. PARTIAL может заменить их на 0. |
| JSON_ERROR_UNSUPPORTED_TYPE | В encode попал неподдерживаемый тип, например ресурс. PARTIAL заменяет его на null. |
| JSON_ERROR_INVALID_PROPERTY_NAME | При создании PHP-объекта имя свойства начинается с NUL. Декодирование в массив имеет другие ограничения ключей. |
| JSON_ERROR_UTF16 | В JSON escape встретился одиночный UTF-16 surrogate вместо корректной пары. Исходный транспорт по-прежнему должен быть UTF-8. |
| JSON_ERROR_NON_BACKED_ENUM / PHP 8.1+ | Обычный enum без backing value нельзя автоматически представить значением JSON. Явно выберите имя/поле или JsonSerializable. |
Код ошибки полезен для машинного решения, текст — для диагностики. Не публикуйте весь документ, трассировку и токены в сообщении посетителю. Ошибка UTF-16 здесь относится к последовательности \uXXXX внутри JSON, а не к разрешению отправлять JSON-файл в UTF-16.
- {"a":} → пропущено значение → JSON_ERROR_SYNTAX.
- Байт FF внутри строки → неверный UTF-8 → JSON_ERROR_UTF8.
- [[[1]]] при depth=2 → JSON_ERROR_DEPTH.
- Одиночный Unicode surrogate → JSON_ERROR_UTF16; после каждого опыта код читается сразу.
<?php
$cases = [
['{"a":}', 16, JSON_ERROR_SYNTAX],
['"' . "\xFF" . '"', 16, JSON_ERROR_UTF8],
['[[[1]]]', 2, JSON_ERROR_DEPTH],
['"\uD800"', 16, JSON_ERROR_UTF16],
];
foreach ($cases as [$body, $depth, $expectedCode]) {
json_decode($body, true, $depth);
var_dump(json_last_error() === $expectedCode);
}
Ожидаемый результат
bool(true)
bool(true)
bool(true)
bool(true)
Внешний массив содержит отдельные опыты, каждый со своим ожидаемым кодом. Результат ошибки читается немедленно после decode, до любого другого JSON-вызова. [переменные] в foreach распаковывает три позиции строки примеров.
Как объект определяет публичное JSON-представление
Без специального договора json_encode берёт публичные свойства объекта. Если нужны другие имена полей, вычисленные значения или стабильный внешний формат, класс реализует интерфейс JsonSerializable. Интерфейс требует публичный метод jsonSerialize без параметров. Этот метод возвращает PHP-данные, которые затем кодирует json_encode.
- json_encode(["order" => $order]) доходит до объекта.
- Объект реализует JsonSerializable → вызывается $order->jsonSerialize().
- Метод возвращает массив разрешённых полей, а не готовую JSON-строку.
- Кодировщик превращает этот массив в JSON внутри поля order.
- json_encode возвращает один итоговый текст вызывающему коду.
JSON-объект и PHP-объект класса — разные понятия. Для начала не нужен собственный класс: массив отлично подходит для простого ответа. Метод полезен, когда формат повторяется у многих экземпляров. JsonSerializable::jsonSerialize содержит минимальный класс, вложенный ответ и объяснение каждого шага.
Граница интеграции: синтаксис, схема и транспорт
Сначала проверьте статус HTTP, размер тела и ожидаемый Content-Type. Затем разбирайте JSON и проверяйте структуру данных. Успех HTTP не гарантирует полезный JSON, а верный JSON не гарантирует нужные поля. Ошибку авторизации в виде HTML не надо «исправлять», вырезая участок от первой фигурной скобки.
- Входные байты: EF BB BF, затем {"stock":0}.
- str_starts_with проверяет ровно три начальных байта BOM.
- substr($body, 3) оставляет текст {"stock":0}.
- json_decode создаёт массив; чтение stock возвращает число 0.
<?php
$body = "\xEF\xBB\xBF" . '{"stock":0}';
if (str_starts_with($body, "\xEF\xBB\xBF")) {
$body = substr($body, 3);
}
$data = json_decode($body, true, 16, JSON_THROW_ON_ERROR);
echo $data['stock'];
Ожидаемый результат
0Это адресная совместимость с известным экспортёром, который добавляет UTF-8 BOM. Удаляем точную последовательность только в начале. trim/ltrim с набором этих байтов — не удаление точного префикса. В обычном API предпочтительно исправить отправителя, а для подписи проверять исходные байты до нормализации по правилам протокола.
Не вызывайте stripslashes, html_entity_decode или «очистку всех управляющих» наугад: это меняет допустимые данные и способно сломать экранирование. Если источник прислал JSON внутри JSON-строки, нужно подтвердить такой договор, а не декодировать многократно до исчезновения ошибки. Диагностика реального ответа показывает дальнейший разбор.
Декодирование требует памяти для исходного текста и структуры; последующее encode создаёт ещё одну строку. Не загружайте огромный архив как одно тело без лимитов. Для больших потоков выбирайте согласованный построчный формат, пагинацию или специализированный потоковый парсер. JSON-функции из этой категории целиком обрабатывают переданное значение.
- Нужно число из поля stock: decode с ошибкой, затем проверить объект/массив, наличие поля, int и допустимый диапазон.
- Нужно только проверить JSON-файл перед хранением: validate подходит, но лимит размера и доверие к содержимому остаются отдельными.
- После array_filter клиент видит объект вместо списка: если ключи технические, восстановить array_values; если это словарь, ключи сохранять.
- После encode у телефона пропал + или нули: убрать NUMERIC_CHECK, проверить типы исходных полей.
- Для повторяемого формата ответа объекта: JsonSerializable возвращает выбранный массив, json_encode вызывается один раз снаружи.
Все функции и интерфейс JSON
Функции и методы этой темы
Откройте карточку, чтобы увидеть договор функции, примеры, ограничения и связанные инструменты.
json_last_errorПолучить числовую категорию последней JSON-операции, которая записывает общее состояние.
PHP 5.3+ · json
json_last_error(): intПолучить числовую категорию последней JSON-операции, которая записывает общее состояние.
| Часть договора | Объяснение |
|---|---|
| Параметры | Отсутствуют. |
| Возврат | JSON_ERROR_NONE либо одна из JSON_ERROR_*; код относится к последней учитываемой операции. |
| Область действия | decode/encode без действующего THROW и json_validate. THROW сам по себе состояние не обновляет; PARTIAL_OUTPUT_ON_ERROR имеет приоритет и может обновить его даже вместе с THROW. |
- json_decode("null") → null; JSON_ERROR_NONE.
- json_decode("{broken") → null; JSON_ERROR_SYNTAX.
- Только код ошибки отличает два результата в режиме без исключений.
<?php
$value = json_decode('null');
var_dump($value);
var_dump(json_last_error() === JSON_ERROR_NONE);
$value = json_decode('{broken');
var_dump($value);
var_dump(json_last_error() === JSON_ERROR_SYNTAX);
Ожидаемый результат
NULL
bool(true)
NULL
bool(true)
У json_last_error нет параметров: он читает общее состояние JSON-расширения. Сравнение с константой проверяет причину; сравнение результата decode с null само по себе недостаточно.
<?php
json_decode('{broken');
$decodeError = json_last_error();
$logPayload = json_encode(["event" => "import_rejected"]);
var_dump(json_last_error() === JSON_ERROR_NONE);
var_dump($decodeError === JSON_ERROR_SYNTAX);
Ожидаемый результат
bool(true)
bool(true)
Успешный encode перезаписал глобальное состояние. Сохранённая переменная относится именно к decode. Пример только создаёт строку журнала в памяти, ничего не записывая.
<?php
json_decode('{broken');
json_decode('{}', true, 16, JSON_THROW_ON_ERROR);
var_dump(json_last_error() === JSON_ERROR_SYNTAX);
try {
json_decode('[[[1]]]', true, 2, JSON_THROW_ON_ERROR);
} catch (JsonException $error) {
var_dump($error->getCode() === JSON_ERROR_DEPTH);
}
var_dump(json_last_error() === JSON_ERROR_SYNTAX);
Ожидаемый результат
bool(true)
bool(true)
bool(true)
Вызовы с THROW не обновляют json_last_error. После них старый SYNTAX не описывает текущую операцию. В catch используйте $error->getCode(); не смешивайте две модели диагностики. Частичный encode — отдельный режим, описанный выше.
Рядом: json_last_error_msg, json_decode, json_encode. Полный список флагов и ошибок.
json_last_error_msgПолучить читаемое описание последней учитываемой JSON-ошибки.
PHP 5.5+ · json
json_last_error_msg(): stringПолучить читаемое описание последней учитываемой JSON-ошибки.
| Часть договора | Объяснение |
|---|---|
| Параметры | Отсутствуют. |
| Возврат | Описание ошибки, при отсутствии — строка No error. |
| Ограничение | Та же модель общего состояния, что у json_last_error; после THROW читайте сообщение исключения. |
- Неудачный json_decode записывает код и описание.
- json_last_error_msg() возвращает строку; сам не печатает.
- Сохранить текст до следующего JSON-вызова, показать человеку своё прикладное сообщение.
<?php
json_decode('{broken');
echo json_last_error_msg(), "
";
json_decode('null');
echo json_last_error_msg();
Ожидаемый результат
Syntax error
No errorСтроки показаны для проверяемого PHP. Для выбора действий сравнивайте JSON_ERROR_*: текст предназначен для чтения, а не устойчивого машинного договора.
<?php
$value = json_decode('{broken');
$code = json_last_error();
$message = json_last_error_msg();
if ($code !== JSON_ERROR_NONE) {
$diagnostic = json_encode(["stage" => "supplier_decode", "message" => $message], JSON_THROW_ON_ERROR);
echo $diagnostic;
}
Ожидаемый результат
{"stage":"supplier_decode","message":"Syntax error"}В журнале выбран этап и текст ошибки; исходный ответ с возможными секретами не добавлен. Сообщение для посетителя можно сформулировать иначе: «Не удалось обновить остатки, попробуйте позже». Строка журнала здесь остаётся только демонстрационным выводом.
Рядом: json_last_error, json_decode, json_validate. Полный список флагов и ошибок.
Источники и обсуждения
- PHP: book.json
- PHP: json.setup
- PHP: json.installation
- PHP: json.constants
- PHP: class.jsonexception
- PHP: class.jsonserializable
- PHP: jsonserializable.jsonserialize
- PHP: ref.json
- PHP: function.json-decode
- PHP: function.json-encode
- PHP: function.json-last-error
- PHP: function.json-last-error-msg
- PHP: function.json-validate
Код и руководство с собой
Скачайте самостоятельные примеры с исходными данными, инструкциями и ожидаемыми результатами. Примеры HTTP и фрагменты для проекта помечены отдельно: им нужно указанное окружение.
Код не исполняется на сайте. Скачайте нужный пример и запускайте его в своём локальном окружении.
Материалы сверены 2026-10-12. Примеры и объяснения написаны для этого руководства; источники и обсуждения доступны в каждой главе.


