Something like this in the docstring?: "In order to support the historical JSON specification and closed ecosystem JSON, it is possible to specify an encoding other than UTF-8."
8.1. Character Encoding
JSON text exchanged between systems that are not part of a closed
ecosystem MUST be encoded using UTF-8 [RFC3629].
Previous specifications of JSON have not required the use of UTF-8
when transmitting JSON text. However, the vast majority of JSON-
based software implementations have chosen to use the UTF-8 encoding,
to the extent that it is the only encoding that achieves
interoperability.
Implementations MUST NOT add a byte order mark (U+FEFF) to the
beginning of a networked-transmitted JSON text. In the interests of
interoperability, implementations that parse JSON texts MAY ignore
the presence of a byte order mark rather than treating it as an
error.
```python
import json
import os
def dumpf(obj, path, *, encoding="UTF-8", **kwargs):
with open(os.fspath(path), "w", encoding=encoding) as f:
return json.dump(obj, f, **kwargs)
def loadf(path, *, encoding="UTF-8", **kwargs):
with open(os.fspath(path), "r", encoding=encoding) as f:
return json.load(f, **kwargs)
import pathlib
import unittest
class TestJsonLoadfAndDumpf(unittest.TestCase):
def setUp(self):
self.encodings = [None, "UTF-8", "UTF-16", "UTF-32"]
data = dict(
obj=dict(a=dict(b=[1, 2, 3])),
path=pathlib.Path(".") / "test_loadf_and_dumpf.json",
)
if os.path.isfile(data["path"]):
os.unlink(data["path"])
self.data = data
def test_dumpf_and_loadf(self):
data = self.data
for encoding in self.encodings:
path = f'{data["path"]}.{encoding}.json'
dumpf_output = dumpf(data["obj"], path, encoding=encoding)
loadf_output = loadf(path, encoding=encoding)
assert loadf_output == data["obj"]
# $ pip install pytest-cov
# $ pytest -v example.py
#
https://docs.pytest.org/en/stable/parametrize.html#
https://docs.pytest.org/en/stable/tmpdir.htmlimport pytest
@pytest.mark.parametrize("encoding", [None, "UTF-8", "UTF-16", "UTF-32"])
@pytest.mark.parametrize("obj", [dict(a=dict(b=[1, 2, 3]))])
def test_dumpf_and_loadf(obj, encoding, tmpdir):
pth = pathlib.Path(tmpdir) / f"test_loadf_and_dumpf.{encoding}.json"
dumpf_output = dumpf(obj, pth, encoding=encoding)
loadf_output = loadf(pth, encoding=encoding)
assert loadf_output == obj
```
For whoever creates a PR for this:
- [ ] add parameter and return type annotations
- [ ] copy docstrings from json.load/json.dump and open#encoding
- [ ] correctly support the c module implementation (this just does `import json`)?
- [ ] keep or drop the encoding tests?