[php-src] Issue #22137: json_file_encode()/json_file_decode(): provide a higher‑level, file‑oriented shortcut

[email protected] (ndividua861) Sat, 23 May 2026 22:39:02 +0000
Newsgroups php.bugs
Message-ID <[email protected]>
Issue: https://github.com/php/php-src/issues/22137
Author: ndividua861

### Description

### Motivation

To load a text file into an array PHP already provides `file()`.  
For JSON, however, the common pattern is more verbose:

```php
$data = json_decode(file_get_contents($file), true);
```

This combination is used so often that it deserves its own pair of helper functions.

***

### Proposed functions

1. **`json_file_decode(string $fileName[, ?bool $object = true]): array|object|false`**  
2. **`json_file_encode(string $fileName, array $array): true|false`**

These functions are meant as convenience wrappers around `json_decode` and `json_encode` + file I/O, modeled after helpers such as `file()`.

***

### Behavior and rationale

#### `json_file_decode`

- Reads the contents of `$fileName` and decodes it as JSON in one call.  
- The optional `$object` parameter mirrors `json_decode`’s second argument:  
  - `true` (default): return an associative array.  
  - `false`: return objects.  
  - `null`: treated as `true` (array), for consistency with `json_decode`.  
- Returns the decoded value (`array` or `object`) on success, or `false` on failure (file not readable, missing, or invalid JSON).  
- On failure, it does not throw by default; consumers can check the return value and inspect `json_last_error()` / `json_last_error_msg()` for details.

#### `json_file_encode`

- Encodes `$array` to a JSON string and writes it to `$fileName` in a single call.  
- Returns `true` on success, `false` on failure (encoding error or I/O error).  
- The implementation should use an atomic‑style write (write to temporary file in the same directory, then `rename`) to avoid partial writes or corruption.  
- Future versions could extend this with flags for options such as pretty‑printing or different JSON constants, but the initial API stays minimal.

***

### Example usage

```php
// Read JSON file into array
$data = json_file_decode('/path/to/config.json');
if ($data === false) {
    die('Failed to load or parse JSON.');
}

// Read JSON file into object
$obj = json_file_decode('/path/to/data.json', false);
if ($obj === false) {
    die('Failed to load or parse JSON.');
}

// Write array back to JSON file
if (!json_file_encode('/path/to/data.json', $data)) {
    die('Failed to write JSON.');
}
```

***

### Sample PHP implementation


```php
<?php
/**
 * Read a JSON file and decode it into an array or object.
 *
 * @param string $fileName Path to the JSON file.
 * @param bool|null $object If true, return associative array; if false, return objects.
 *                         If null, default to true (array).
 * @return array|object|false Decoded data, or false on error.
 */
function json_file_decode(string $fileName, ?bool $object = true): array|object|false
{
    // Treat null as true (array) for consistency with json_decode.
    $assoc = ($object === null) ? true : !$object;

    if (!is_readable($fileName)) {
        return false;
    }

    $json = @file_get_contents($fileName);
    if ($json === false) {
        return false;
    }

    $data = json_decode($json, $assoc);
    return ($data === null && json_last_error() !== JSON_ERROR_NONE) ? false : $data;
}

/**
 * Encode an array as JSON and write it to a file.
 *
 * @param string $fileName Path to the JSON file.
 * @param array $array Data to encode and write.
 * @return bool True on success, false on failure.
 */
function json_file_encode(string $fileName, array $array): bool
{
    $json = json_encode($array, JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE);
    if ($json === false) {
        return false;
    }

    // Use a temporary file in the same directory for atomic‑style write.
    $dir = dirname($fileName);
    $temp = tempnam($dir, 'json_');
    if ($temp === false) {
        return false;
    }

    $ok = file_put_contents($temp, $json) !== false;
    if ($ok) {
        $ok = rename($temp, $fileName);
    }

    if (!$ok && file_exists($temp)) {
        @unlink($temp);
    }

    return $ok;
}
```

***

### Compatibility and naming

- The proposed names are descriptive and follow PHP naming conventions for file helpers.  
- Return `false` on failure, consistent with `file_get_contents` and similar functions.  
- The functions do not replace `json_decode` / `json_encode` but provide a higher‑level, file‑oriented shortcut for one of the most common patterns with JSON in PHP.