Skip to content

Commit

Permalink
Add special option for json encoder/decoder
Browse files Browse the repository at this point in the history
  • Loading branch information
aranega committed Mar 10, 2024
1 parent 43a3fd3 commit 435c3b7
Show file tree
Hide file tree
Showing 2 changed files with 40 additions and 2 deletions.
12 changes: 10 additions & 2 deletions pyecore/resources/json.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,8 @@
@unique
class JsonOptions(Enum):
SERIALIZE_DEFAULT_VALUES = 0
ENCODER = 1
DECODER = 2


NO_OBJECT = object()
Expand All @@ -27,9 +29,13 @@ def __init__(self, uri=None, use_uuid=False, indent=None, ref_tag='$ref'):
self.default_mapper = DefaultObjectMapper()

def load(self, options=None):
self.options = options or {}
self.cache_enabled = True
json_value = self.uri.create_instream()
d = json.loads(json_value.read().decode('utf-8'))

decoder = self.options.get(JsonOptions.DECODER)
d = json.loads(json_value.read().decode('utf-8'), cls=decoder)

if isinstance(d, list):
for x in d:
self.to_obj(x, first=True)
Expand All @@ -51,8 +57,10 @@ def save(self, output=None, options=None):
if len(dict_list) <= 1:
dict_list = dict_list[0]

stream.write(json.dumps(dict_list, indent=self.indent)
encoder = self.options.get(JsonOptions.ENCODER)
stream.write(json.dumps(dict_list, indent=self.indent, cls=encoder)
.encode('utf-8'))

stream.flush()
self.uri.close_stream()
self.options = None
Expand Down
30 changes: 30 additions & 0 deletions tests/json/test_json_save.py
Original file line number Diff line number Diff line change
Expand Up @@ -285,3 +285,33 @@ class Root(object):
dct = json.load(open(str(f)))
print(dct)
assert dct['many_a'] == []


# def test_json_custom_encoder(tmpdir):
# class DoubleEncoder(json.JSONEncoder):
# def default(self, o):
# import ipdb; ipdb.set_trace() # fmt: skip

# if isinstance(o, float):
# return f"#({o})"
# return super().default(o)

# def encode(self, o):
# import ipdb; ipdb.set_trace() # fmt: skip


# f = tmpdir.mkdir('pyecore-tmp').join('test.json')
# resource = JsonResource(URI(str(f)))

# p = Point()
# p.x = 0.0
# p.z = 0.0
# resource.append(p)
# resource.save(options={JsonOptions.ENCODER: DoubleEncoder, JsonOptions.SERIALIZE_DEFAULT_VALUES: True})

# dct = json.load(open(str(f)))
# import ipdb; ipdb.set_trace() # fmt: skip

# assert dct['x'] == 0.0
# assert dct['z'] == 0.0
# assert 'y' not in dct

0 comments on commit 435c3b7

Please sign in to comment.