Source code for efrotools.jsontools

# Released under the MIT License. See LICENSE for details.
#
"""Json related tools functionality."""

from __future__ import annotations

import json
from typing import TYPE_CHECKING, override

if TYPE_CHECKING:
    from typing import Any


[docs] class NoIndent: """Used to prevent indenting in our custom json encoder. Wrap values in this before passing to encoder and all child values will be a single line in the json output.""" def __init__(self, value: Any) -> None: self.value = value
[docs] class NoIndentEncoder(json.JSONEncoder): """Our custom encoder implementing selective indentation.""" def __init__(self, *args: Any, **kwargs: Any): super().__init__(*args, **kwargs) self.kwargs = dict(kwargs) del self.kwargs['indent'] self._replacement_map: dict = {}
[docs] @override def default(self, o: Any) -> Any: import uuid if isinstance(o, NoIndent): key = uuid.uuid4().hex self._replacement_map[key] = json.dumps(o.value, **self.kwargs) # pylint: disable=consider-using-f-string return '@@%s@@' % (key,) return super().default(o)
[docs] @override def encode(self, o: Any) -> Any: result = super().encode(o) for k, v in self._replacement_map.items(): # pylint: disable=consider-using-f-string result = result.replace('"@@%s@@"' % (k,), v) return result
# Docs-generation hack; import some stuff that we likely only forward-declared # in our actual source code so that docs tools can find it. from typing import (Coroutine, Any, Literal, Callable, Generator, Awaitable, Sequence, Self) import asyncio from concurrent.futures import Future from pathlib import Path from enum import Enum