phalcon/cphalcon · error · Phalcon\Support\Helper\Json\Exceptions\JsonDecodeError
json_decode error: {message}
Error message
json_decode error: {message} What it means
Phalcon\Support\Helper\Json\Decode wraps json_decode with throw-on-error semantics and rethrows any JsonException as Phalcon\Support\Helper\Json\Exceptions\JsonDecodeError ("json_decode error: {message}"), preserving the code and the previous exception. It fires for exactly the reasons json_decode() fails: syntax errors, unexpected tokens, or nesting deeper than the $depth argument (default 512). Also reachable via HelperFactory as 'jsonDecode'.
Source
Thrown at phalcon/Support/Helper/Json/Decode.zep:51
/**
* @param int<1, max> $depth Recursion depth.
*
* @throws JsonDecodeError if the JSON cannot be decoded.
* @link https://www.php.net/manual/en/function.json-decode.php
*/
public function __invoke(
string data,
bool associative = false,
int depth = 512,
int options = 79
) {
var ex;
try {
return this->toDecode(data, associative, depth, options);
} catch JsonException, ex {
throw new JsonDecodeError(ex->getMessage(), ex->getCode(), ex);
}
}
}
View on GitHub (pinned to b7419de9cd)
Solutions
- Validate before decoding: json_validate($raw) on PHP >= 8.3, or a decode-and-check-json_last_error probe
- Check the upstream response status and Content-Type before treating the body as JSON
- Pass a larger $depth for deeply nested documents
- Strip BOM/whitespace: $raw = preg_replace('/^\xEF\xBB\xBF/', '', trim($raw));
Example fix
// before
$data = (new Decode())($response->getBody()); // 'json_decode error: Syntax error'
// after
$raw = trim($response->getBody());
if (json_validate($raw)) { // PHP 8.3+
$data = (new Decode())($raw);
} else {
$logger->error('Non-JSON body: ' . substr($raw, 0, 200));
$data = [];
} Defensive patterns
Strategy: validation
Validate before calling
$raw = trim($response->getBody());
if (json_validate($raw)) { // PHP 8.3+; older: decode + json_last_error check
$data = (new Decode())($raw);
} else {
$logger->error('Non-JSON body: ' . substr($raw, 0, 200));
$data = [];
} Type guard
function isJsonString(string $raw): bool
{
json_decode($raw);
return JSON_ERROR_NONE === json_last_error();
} Try / catch
use Phalcon\Support\Helper\Json\Exceptions\JsonDecodeError;
try {
$data = $decode($raw);
} catch (JsonDecodeError $e) {
// "json_decode error: Syntax error" etc.; previous holds the JsonException
$data = null;
$logger->error($e->getMessage());
} Prevention
- Assert Content-Type: application/json and a success status before decoding remote bodies
- json_validate() first when targeting PHP 8.3+
- Log a payload snippet on failure — truncation and HTML error pages are the most common causes
- Pass $depth explicitly for deeply nested documents
When it happens
Trigger: (new Decode())('{"a":') or $helpers->jsonDecode($raw) where $raw is an HTML error page from an upstream API ('Syntax error'); a JSON body truncated by a size limit; nesting beyond 512 levels.
Common situations: Remote APIs returning HTML or empty bodies on 5xx, gateway error pages, BOM-prefixed UTF-8 exports, payloads cut off by proxy/body-size limits, strings with smart quotes pasted into 'JSON' files.
Related errors
- json_encode error: {message}
- json_last_error_msg()
- Configuration file {fileName} cannot be loaded
- Configuration file {fileName} cannot be loaded
- Unknown method: [{method}]
AI-assisted analysis of phalcon/cphalcon@b7419de9cd (2026-08-21).
Data as JSON: /api/errors/50e23fad94ae88de.
Report an issue: GitHub.