Checking whether a string is valid JSON meant decoding it and throwing the result away, which allocates the whole structure to answer a yes-or-no question.
// before
function isValidJson(string $s): bool
{
json_decode($s);
return json_last_error() === JSON_ERROR_NONE;
}
// 8.3
json_validate($s);
// on a 12 MB webhook payload:
// json_decode + discard peak 94 MB
// json_validate peak 1 MB
The saving is proportional to the payload and matters in exactly one situation: validating something large that will then be rejected or handed on without decoding. Using it as a guard before json_decode in the normal path is worse than useless, because it parses twice — the correct pattern there is still to decode with JSON_THROW_ON_ERROR and catch.