Skip to content

Commit

Permalink
Fix issue with serialization of vocabulary items
Browse files Browse the repository at this point in the history
Vocabulary items are not hashable and thus we can't cast them to the
fields type. We always return lists as JSON doesn't support other
container types anyway.
  • Loading branch information
buchi committed Oct 26, 2019
1 parent c1ab8aa commit 8191681
Show file tree
Hide file tree
Showing 4 changed files with 28 additions and 1 deletion.
2 changes: 2 additions & 0 deletions news/788.bugfix
@@ -0,0 +1,2 @@
Fix serialization of vocabulary items for fields that need hashable items (e.g. sets).
[buchi]
2 changes: 1 addition & 1 deletion src/plone/restapi/serializer/dxfields.py
Expand Up @@ -68,7 +68,7 @@ def __call__(self):
for v in value:
term = value_type.vocabulary.getTerm(v)
values.append({u"token": term.token, u"title": term.title})
value = self.field._type(values)
value = values
return json_compatible(value)


Expand Down
12 changes: 12 additions & 0 deletions src/plone/restapi/tests/dxtypes.py
Expand Up @@ -193,6 +193,18 @@ class IDXTestDocumentSchema(model.Schema):
required=False,
)
test_set_field = schema.Set(required=False)
test_set_field_with_choice_with_vocabulary = schema.Set(
value_type=schema.Choice(
vocabulary=SimpleVocabulary(
[
SimpleTerm(u"value1", "token1", u"title1"),
SimpleTerm(u"value2", "token2", u"title2"),
SimpleTerm(u"value3", "token3", u"title3"),
]
)
),
required=False,
)
test_text_field = schema.Text(required=False)
test_textline_field = schema.TextLine(required=False)
test_time_field = schema.Time(required=False)
Expand Down
13 changes: 13 additions & 0 deletions src/plone/restapi/tests/test_dxfield_serializer.py
Expand Up @@ -156,6 +156,19 @@ def test_set_field_serialization_returns_list(self):
self.assertTrue(isinstance(value, list), "Not a <list>")
self.assertEqual([u"a", u"b", u"c"], sorted(value))

def test_set_field_with_vocabulary_choice_serialization_returns_terms(self):
value = self.serialize(
"test_set_field_with_choice_with_vocabulary", set([u"value1", u"value3"])
)
self.assertTrue(isinstance(value, list), "Not a <list>")
self.assertEqual(
[
{u"token": u"token1", u"title": u"title1"},
{u"token": u"token3", u"title": u"title3"},
],
sorted(value, key=lambda x: x[u"token"]),
)

def test_text_field_serialization_returns_unicode(self):
value = self.serialize("test_text_field", u"Käfer")
self.assertTrue(isinstance(value, six.text_type), "Not an <unicode>")
Expand Down

0 comments on commit 8191681

Please sign in to comment.