Como hacer una clase serializable simplejson.

Tengo una clase definida como esta

class A: def __init__(self): self.item1 = None def __repr__(self): return str(self.__dict__) 

Cuando lo hago:

 >>> import simplejson >>> myA = A() >>> simplejson.dumps(myA) TypeError: {'item1': None} is not JSON serializable 

No puedo encontrar la razón por la que.

¿Necesito agregar algún método en particular a A para que simplejson serialice mi objeto de clase?

No puedes serializar objetos arbitrarios con simplejson . Necesitas pasar un default y object_hook para dump y load . Aquí hay un ejemplo:

 class SerializerRegistry(object): def __init__(self): self._classes = {} def add(self, cls): self._classes[cls.__module__, cls.__name__] = cls return cls def object_hook(self, dct): module, cls_name = dct.pop('__type__', (None, None)) if cls_name is not None: return self._classes[module, cls_name].from_dict(dct) else: return dct def default(self, obj): dct = obj.to_dict() dct['__type__'] = [type(obj).__module__, type(obj).__name__] return dct registry = SerializerRegistry() @registry.add class A(object): def __init__(self, item1): self.item1 = item1 def __repr__(self): return str(self.__dict__) def to_dict(self): return dict(item1=self.item1) @classmethod def from_dict(cls, dct): return cls(**dct) s = json.dumps(A(1), default=registry.default) a = json.loads(s, object_hook=registry.object_hook) 

Esto resulta en esto:

 >>> s '{"item1": 1, "__type__": ["__main__", "A"]}' >>> a {'item1': 1} 

Pero lo que realmente necesita es una función default que crea un diccionario a partir de los objetos que desea serializar, y una función object_hook que devuelve un objeto (del tipo correcto) cuando se le da un diccionario si un diccionario no es suficiente. El mejor enfoque es tener métodos en las clases serializables que crean un dictado desde el objeto y que lo construyen de nuevo, y también tener una asignación que reconozca a qué clase pertenecen los diccionarios.

También puede agregar un identificador a las clases que se usarán como un índice para las _classes . De esta manera no tendrías problemas si tuvieras que mover una clase.

De acuerdo con los documentos del módulo json (simplejson fue adoptado como json en Python 2.6), necesita extender la clase json.JSONEncoder , anulando su método predeterminado para traducir su objeto a un tipo que pueda ser serializado. No parece haber un método que busque en su objeto.