At a project I'm contributing to we have a very simple, but important class (let's call it LegacyClass
). Modifying it would be a long process.
I'm contributing new dataclasses (like NormalDataclass
) to this project and I need to be able to serialize them to JSON.
I don't have access to the JSON encoder, so I cannot specify custom encoder.
Here you can find sample code
import dataclasses
import collections
import json
#region I cannot easily change this code
class LegacyClass(collections.abc.Iterable):
def __init__(self, a, b):
self.a = a
self.b = b
def __iter__(self):
yield self.a
yield self.b
def __repr__(self):
return f"({self.a}, {self.b})"
#endregion
#region I can do whatever I want to this part of code
@dataclasses.dataclass
class NormalDataclass:
legacy_class: LegacyClass
legacy_class = LegacyClass('a', 'b')
normal_dataclass = NormalDataclass(legacy_class)
normal_dataclass_dict = dataclasses.asdict(normal_dataclass)
#endregion
#region I cannot easily change this code
json.dumps(normal_dataclass_dict)
#endregion
What I would want to get:
{"legacy_class": {"a": "a", "b": "b"}}
What I'm getting:
TypeError: Object of type LegacyClass is not JSON serializable
Do you have any suggestions?
Specifying dict_factory
as an argument to dataclasses.asdict
would be an option, if there would not be multiple levels of LegacyClass
nesting, eg:
@dataclasses.dataclass
class AnotherNormalDataclass:
custom_class: List[Tuple[int, LegacyClass]]
To make dict_factory
recursive would be to basically rewrite dataclasses.asdict
implementation.