Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Bug: Custom Method serialization of List items throws AttributeError #1993

Open
benedekh opened this issue May 29, 2022 · 2 comments · May be fixed by #1994
Open

Bug: Custom Method serialization of List items throws AttributeError #1993

benedekh opened this issue May 29, 2022 · 2 comments · May be fixed by #1994

Comments

@benedekh
Copy link

Let's have the following Schema:

class ExampleSchema(Schema):
	dummy_list = fields.List(fields.Method(serialize="serialize_me"))

	def serialize_me(self, obj):
		return [str(value) for value in obj["dummy_list"]]

Let's have the following serialization code:

obj = {"dummy_list": ["hello", "world"]}
dumped = ExampleSchema().dump(obj)

ExampleSchema().dump(obj) throws AttributeError: 'List' object has no attribute 'serialize_me' error.

The full stack trace is:

    dumped = ExampleSchema().dump(obj)
..\src\marshmallow\schema.py:399: in __init__
    self._init_fields()
..\src\marshmallow\schema.py:975: in _init_fields
    self._bind_field(field_name, field_obj)
..\src\marshmallow\schema.py:1034: in _bind_field
    field_obj._bind_to_schema(field_name, self)
..\src\marshmallow\fields.py:757: in _bind_to_schema
    self.inner._bind_to_schema(field_name, self)
..\src\marshmallow\fields.py:1858: in _bind_to_schema
    getattr(schema, self.serialize_method_name)
E   AttributeError: 'List' object has no attribute 'serialize_me'

The bug exists in marshmallow 3.16.0.

@lafrech
Copy link
Member

lafrech commented Jun 26, 2022

I still need to get my head around this. I suppose Tuple would be impacted as well.

In your example, I don't understand why you use List in the first place. Shouldn't it be

class ExampleSchema(Schema):
	dummy_list = fields.Method(serialize="serialize_me")

	def serialize_me(self, obj):
		return [str(value) for value in obj["dummy_list"]]

?

@benedekh
Copy link
Author

benedekh commented Jun 28, 2022

@lafrech: That would be also a way to go. However, I wanted to keep the same data types for the field as in the data class.

Originally, I discovered the bug in a @dataclass, where I declared the fields type-correctly and then defined a Schema separately, because I had some special fields in the @dataclass that could not be (de)serialized normally. One of these fields was List[CustomDataType] (where CustomDataType is the type which had to be (de)serialized manually).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants