Skip to content

feat: allow different json library imports #285

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 17 commits into from
May 29, 2025
2 changes: 1 addition & 1 deletion azure/functions/_cosmosdb.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,9 @@
# Licensed under the MIT License.

import collections
import json

from . import _abc
from ._jsonutils import json


class Document(_abc.Document, collections.UserDict):
Expand Down
87 changes: 87 additions & 0 deletions azure/functions/_jsonutils.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
from abc import ABC, abstractmethod
import types


class JsonInterface(ABC):
@abstractmethod
def dumps(self, obj) -> str:
pass

@abstractmethod
def loads(self, s: str):
pass


class OrJsonAdapter(JsonInterface):
def __init__(self):
import orjson
self.orjson = orjson

def dumps(self, obj) -> str:
return self.orjson.dumps(obj).decode("utf-8")

def loads(self, s: str):
return self.orjson.loads(s)


class UJsonAdapter(JsonInterface):
def __init__(self):
import ujson
self.ujson = ujson

def dumps(self, obj) -> str:
return self.ujson.dumps(obj)

def loads(self, s: str):
return self.ujson.loads(s)


class SimpleJsonAdapter(JsonInterface):
def __init__(self):
import simplejson
self.simplejson = simplejson

def dumps(self, obj) -> str:
return self.simplejson.dumps(obj)

def loads(self, s: str):
return self.simplejson.loads(s)


class StdJsonAdapter(JsonInterface):
def __init__(self):
import json
self.json = json

def dumps(self, obj, **kwargs) -> str:
return self.json.dumps(obj, **kwargs)

def loads(self, s: str):
return self.json.loads(s)


json_impl = None
for adapter_cls in (OrJsonAdapter, UJsonAdapter, SimpleJsonAdapter, StdJsonAdapter):
try:
json_impl = adapter_cls()
break
except ImportError:
continue


def dumps(obj, **kwargs) -> str:
if json_impl is None:
raise ImportError("No JSON adapter found")
return json_impl.dumps(obj, **kwargs)


def loads(s: str):
if json_impl is None:
raise ImportError("No JSON adapter found")
return json_impl.loads(s)


json = types.SimpleNamespace(
dumps=dumps,
loads=loads
)
Loading