Skip to content

Commit

Permalink
Updated serialization and deserialization to support
Browse files Browse the repository at this point in the history
objects with the dict and list interfaces.

refs #18
refs #16
  • Loading branch information
jaimegildesagredo committed Jan 29, 2014
1 parent d2d02d6 commit f64b814
Show file tree
Hide file tree
Showing 4 changed files with 54 additions and 27 deletions.
15 changes: 11 additions & 4 deletions booby/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -202,7 +202,7 @@ def deserialize(self, raw):
for name, field in self._fields.items():
value = raw[field.options.get('name', name)]

if (isinstance(value, dict) and
if (isinstance(value, collections.MutableMapping) and
isinstance(field, fields.Embedded)):

value = field.model.deserialize(value)
Expand All @@ -219,10 +219,17 @@ def serialize(self):

if isinstance(value, Model):
value = value.serialize()
elif isinstance(value, list):
for i, item in enumerate(value):
elif isinstance(value, collections.MutableSequence):
new_value = []

for item in value:
if isinstance(item, Model):
value[i] = item.serialize()
new_value.append(item.serialize())
else:
new_value.append(item)

value = new_value
del new_value

result[field.options.get('name', name)] = value

Expand Down
20 changes: 20 additions & 0 deletions tests/unit/_helpers.py
Original file line number Diff line number Diff line change
Expand Up @@ -33,3 +33,23 @@ def __len__(self):

def insert(self, index, value):
pass


class MyDict(collections.MutableMapping):
def __init__(self, **kwargs):
self._store = kwargs

def __getitem__(self, key):
return self._store[key]

def __setitem__(self, key, value):
pass

def __delitem__(self, key):
pass

def __len__(self):
pass

def __iter__(self):
return iter(self._store)
22 changes: 1 addition & 21 deletions tests/unit/fields/test_embedded.py
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
# -*- coding: utf-8 -*-

from __future__ import unicode_literals
import collections

from expects import expect
from .._helpers import MyDict

from booby import fields, errors, models

Expand Down Expand Up @@ -69,23 +69,3 @@ class User(models.Model):
class Group(models.Model):
name = fields.String()
admin = fields.Embedded(User)


class MyDict(collections.MutableMapping):
def __init__(self, **kwargs):
self._store = kwargs

def __getitem__(self, key):
return self._store[key]

def __setitem__(self, key, value):
pass

def __delitem__(self, key):
pass

def __len__(self):
pass

def __iter__(self):
return iter(self._store)
24 changes: 22 additions & 2 deletions tests/unit/test_models.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
import json

from expects import expect
from ._helpers import MyList
from ._helpers import MyList, MyDict

from booby import errors, fields, models

Expand Down Expand Up @@ -228,7 +228,7 @@ def test_should_return_dict_with_model_mapped_fields(self):

expect(result).to.have.keys(name='Jack', email='[email protected]')

def test_should_deserialize_embedded_model_if_field_is_embedded_field(self):
def test_should_deserialize_embedded_dict_if_field_is_embedded_field(self):
result = UserWithTokenAndMappedFields.deserialize({
'name': 'Jack', 'email': '[email protected]',
'token': {
Expand All @@ -238,6 +238,16 @@ def test_should_deserialize_embedded_model_if_field_is_embedded_field(self):

expect(result['token']).to.have.keys(key='foo', secret='bar')

def test_should_deserialize_embedded_mutable_mapping_if_field_is_embedded_field(self):
result = UserWithTokenAndMappedFields.deserialize({
'name': 'Jack', 'email': '[email protected]',
'token': MyDict(
accessToken='foo', secretToken='bar'
)
})

expect(result['token']).to.have.keys(key='foo', secret='bar')


class TestSerializeModel(object):
def test_should_return_dict_with_model_fields(self):
Expand Down Expand Up @@ -285,6 +295,16 @@ def test_should_serialize_list_of_models_and_values(self):
expect(result['tokens']).to.equal([self.token1.serialize(), 'foo',
self.token2.serialize()])

def test_should_serialize_mutable_sequence_of_models(self):
user = UserWithList(
name='Jack', email='[email protected]',
tokens=MyList(self.token1, self.token2))

result = user.serialize()

expect(result['tokens']).to.equal([self.token1.serialize(),
self.token2.serialize()])

def setup(self):
self.token1 = TokenWithMappedFields(key='foo', secret='bar')
self.token2 = TokenWithMappedFields(key='fuu', secret='baz')
Expand Down

0 comments on commit f64b814

Please sign in to comment.