Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to achieve the reverse of "attr.asdict(MyObject)" using Python module 'attrs'

In documentation of Python module attrs stated that there is a method to convert attributes’ class into dictionary representation:

Example:

>>> @attr.s
... class Coordinates(object):
...     x = attr.ib()
...     y = attr.ib()
...
>>> attr.asdict(Coordinates(x=1, y=2))
{'x': 1, 'y': 2}

How can I achive the oposite: get instance of the Coordinates from its valid dictionary representation without boilerplate and with a joy of the attrs module?

like image 973
kuza Avatar asked Jun 28 '17 12:06

kuza


2 Answers

Apparently as easy as using dictionary unpacking (double star) operator in corresponding attrs class instantiation.

Example:

>>> Coordinates(**{'x': 1, 'y': 2})
Coordinates(x=1, y=2)
like image 195
kuza Avatar answered Nov 12 '22 11:11

kuza


As a more universal solution, which works with attrs nested classes, enums or any other type annotated structures you can use https://github.com/Tinche/cattrs

Example:

import attr, cattr

@attr.s(slots=True, frozen=True)  # It works with normal classes too.
class C:
        a = attr.ib()
        b = attr.ib()

instance = C(1, 'a')
cattr.unstructure(instance)
# {'a': 1, 'b': 'a'}
cattr.structure({'a': 1, 'b': 'a'}, C)
# C(a=1, b='a')
like image 34
zhukovgreen Avatar answered Nov 12 '22 11:11

zhukovgreen