Skip to content

Instantly share code, notes, and snippets.

@ianfoo
Created March 29, 2023 00:11
Show Gist options
  • Save ianfoo/148d639520f9370d0b863a6945d94c5f to your computer and use it in GitHub Desktop.
Save ianfoo/148d639520f9370d0b863a6945d94c5f to your computer and use it in GitHub Desktop.
Prototype for a serializable decimal field for Marshmallow
from decimal import Decimal
from marshmallow import Schema, ValidationError, fields, post_load
class SerializableDecimal(fields.Field):
def _serialize(self, value, attr, obj, **kwargs):
if value is None:
return None
if not isinstance(value, Decimal):
raise ValidationError("must be a Decimal value")
return str(value)
def _deserialize(self, value, attr, data, **kwargs):
try:
return Decimal(value)
except Exception as error:
raise ValidationError("cannot deserialize as Decimal") from error
class MyDecimal:
dec: Decimal
class Schema(Schema):
dec = SerializableDecimal()
class Meta:
strict = True
@post_load
def objectify(self, data):
return MyDecimal(**data)
def __init__(self, dec: Decimal):
self.dec = dec
def __repr__(self):
return f'MyDecimal(dec={self.dec})'
if __name__ == '__main__':
my_dec = MyDecimal(Decimal('10.44244422008'))
serialized = MyDecimal.Schema().dumps(my_dec).data
print(serialized)
deserialized = MyDecimal.Schema().loads(serialized).data
print(deserialized)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment