2017-02-07 5 views
1

Je frappe cette exception avec jsonpickle, lorsque j'essaie de décaper un objet plutôt complexe que je ne suis malheureusement pas sûr de décrire ici. Je sais qui le rend difficile à dire beaucoup, mais pour ce que ça vaut:Erreur Python jsonpickle: L'objet 'OrderedDict' n'a pas d'attribut '_OrderedDict__root'

>>> frozen = jsonpickle.encode(my_complex_object_instance) 
>>> thawed = jsonpickle.decode(frozen) 

Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
    File "/Library/Python/2.7/site-packages/jsonpickle/__init__.py", 
    line 152, in decode 
    return unpickler.decode(string, backend=backend, keys=keys) 
     : 
     : 
    File "/Library/Python/2.7/site-packages/jsonpickle/unpickler.py", 
    line 336, in _restore_from_dict 
    instance[k] = value 
    File "/Library/Python/2.7/site-packages/botocore/vendored/requests/packages/urllib3/packages/ordered_dict.py", 
    line 49, in __setitem__ 
    root = self.__root 
AttributeError: 'OrderedDict' object has no attribute '_OrderedDict__root' 

Je ne trouve pas beaucoup d'aide quand googler l'erreur. Je vois ce qui ressemble à la même question a été réglée à un temps passé pour les objets plus simples:

https://github.com/jsonpickle/jsonpickle/issues/33

L'exemple cité dans ce rapport fonctionne pour moi:

>>> jsonpickle.decode(jsonpickle.encode(collections.OrderedDict())) 
OrderedDict() 
>>> jsonpickle.decode(jsonpickle.encode(collections.OrderedDict(a=1))) 
OrderedDict([(u'a', 1)]) 

Quelqu'un at-il jamais couru dans cela eux-mêmes et a trouvé une solution? Je demande avec la compréhension que mon cas peut être "différemment idiosynchratique" qu'un autre exemple connu.

Répondre

1

Le module de requêtes semble rencontrer des problèmes lors de la commande .decode(). Après avoir regardé un peu le code jsonpickle, j'ai décidé de le fourchonner et de changer les lignes suivantes pour voir ce qui se passait (et j'ai fini par garder une copie privée de jsonpickle avec les changements pour pouvoir avancer).

Dans jsonpickle/unpickler.py (dans ma version, il est la ligne 368), la recherche de la si la section de l'instruction dans la méthode _restore_from_dict():

if (util.is_noncomplex(instance) or 
    util.is_dictionary_subclass(instance)): 
    instance[k] = value 
else: 
    setattr(instance, k, value) 

et changer à ce (il LogError les qui échouent et ensuite vous pouvez garder le code en place ou changer la version de votre OrderedDict qui a __root)

if (util.is_noncomplex(instance) or 
    util.is_dictionary_subclass(instance)): 
    # Currently requests.adapters.HTTPAdapter is using a non-standard 
    # version of OrderedDict which doesn't have a _OrderedDict__root 
    # attribute 
    try: 
     instance[k] = value 
    except AttributeError as e: 
     import logging 
     import pprint 
     warnmsg = 'Unable to unpickle {}[{}]={}'.format(pprint.pformat(instance), pprint.pformat(k), pprint.pformat(value)) 
     logging.error(warnmsg) 
else: 
    setattr(instance, k, value)