2010-11-16 3 views
0

J'ai passé des jours sur cette tentative de toutes les bibliothèques JSON y compris la gemme JSON, Yajl-ruby, ActiveSupport :: JSON et rien ne peut faire cette tâche simple:Ruby on Rails sérialiser puis désérialiser le même objet dans JSON

user = User.find(1) 
json = user.to_json 
user2 = json.as_json # OR json.from_json 
        # OR JSON.parse(json) 
        # OR Yajl::Parser.parse(json) 
        # OR ActiveSupport::JSON.decode(json) 

Lorsque je tente d'utiliser les données désérialisés JSON pour créer un nouvel utilisateur, je reçois une des erreurs suivantes:

User.new(Yajl::Parser.parse(json)) 
# ActiveRecord::UnknownAttributeError: unknown attribute: json_class 

User.new(json.as_json) 
# NoMethodError: undefined method `stringify_keys!' for #<String:0xb6de4318> 

User.new(JSON.parse(json)) 
# NoMethodError: undefined method `stringify_keys!' for #<User:0xb6dc7470> 

User.new(ActiveSupport::JSON.decode(json)) 
# NoMethodError: undefined method `stringify_keys!' for #<User:0xb6da3764> 

Cela est si facile à faire avec l'aide YAML to_yaml et from_yaml. Pourquoi ne pas to_json produire le type de JSON que from_json pourrait convertir en un objet ruby?

Editer: J'utilise Rails 2.3.8, bien que j'ai essayé 2.3.5 et 3.0.0. De plus, j'utilise le plugin json-rpc pour créer un service JSON-RPC, bien que le même problème persiste sans le plugin.

+0

Êtes-vous sûr que votre json est vraiment un json? Cela ressemble plus à l'objet User en ce qui concerne l'erreur :( – shingara

Répondre

3
json = Episode.first.to_json 
dec = ActiveSupport::JSON.decode json 
Episode.new dec['episode'] 

Fonctionne pour moi dans Rails 3.0.1. Dans vos exemples, vous n'avez pas supprimé les attributs réels dict du wrapper dict après la conversion de JSON en Ruby. Vous devriez essayer

User.new(ActiveSupport::JSON.decode(json)['user']) 
+1

yup, cela devrait fonctionner.L'autre option, sérialiser seulement les attributs: User.first.attributes.to_json – tokland

+0

Sérialiser seulement les attributs fonctionne 'User.new (ActiveSupport: : JSON.decode (json) ['utilisateur']) 'n'a pas été. 'Json' est stocké sous forme de chaîne et après son décodage, il s'agit d'un objet Utilisateur avec des attributs vides –

+0

' User.new (ActiveSupport :: JSON.decode (json) ['attributes']) 'fonctionne dans Rails 3. –