2011-07-28 12 views
13

estoy usando el método to_json en mi modelo de objetos que creé haciendo algo como:Ruby on Rails 3 - a_json sin incluir todos los atributos

user = User.find(1)

Cuando hago user.to_json, una gran cantidad de atributos faltan, incluyendo user.id de la cadena JSON codificada. Parece que todos los atributos que he agregado como attr_accessible del modelo de Usuario están ahí, pero ninguno de los otros. Quizás eso es lo que to_json está haciendo, pero creo que agregar id a attr_accessible es un no ir.

¿Cuál es la forma correcta de resolver este problema?

ACTUALIZACIÓN

Esto parece ser un tema específico con inventar. Si comento a cabo lo siguiente de user.rb, todo funciona como se esperaba:

devise :rememberable, :trackable, :token_authenticatable, :omniauthable

+0

Esto es realmente extraño ... ¿Qué pasa si escribe explícitamente 'user.to_json (: except =>: created_at)'. – apneadiving

+0

¿trataste de trabajar desde la consola? ¿Y el objeto antes de to_json? ¿Tiene todos los atributos establecidos? – pasine

+0

el objeto _does_ contiene id antes del to_json (verificado en la consola). Intenté (: except =>: created_at) y eso no lo hizo. Me pregunto si Devise está haciendo algo extraño para mi objeto. – randombits

Respuesta

5

No he comprobado pero creo Diseñar hace por usted; incluye solo ciertos atributos a través de attr_accessible.

En cualquier caso, la forma correcta de resolver esto es reemplazar el método as_json así:

def as_json(options = nil) 
    { 
    my_attr: my_attr, 
    etc: etc 
    } 
end 

Es un hash simple y es un método muy potente para generar JSON en AR, sin jugar con el to_json método.

0

incluir algo como esto en la clase del modelo:

attr_accessible :id, :email, :password, :password_confirmation, :remember_me 

Inicialmente, el ID no se incluyó en JSON pero después he añadido a attr_accessible funcionó !!

2

Por defecto, Devise anula el método serializable_hash para exponer solo los atributos accesibles (por lo que cosas como la contraseña_cifrada no se serializa de manera predeterminada en las API).

Se podría tratar de reemplazar este método y añadir la auth_token al hash, algo como esto:

def serializable_hash (opciones = nil) super (opciones) .merge ("auth_token" => auth_token) fin

2

De hecho, el dispositivo filtra los atributos para usted, como lo menciona kain. Sin embargo, prefiero adjuntar exactamente lo que necesito en lugar de anular la lógica de Devise.

En cambio, yo prefiero hacer

def as_json(options={}) 
    json_res = super options 
    json_res['locked_at'] = self.locked_at 
    json_res['confirmed_at'] = self.confirmed_at 
end 

o cualquier otro atributo de su usuario podría tener que desea pasar

2

Si usted vino aquí en busca de los carriles 4, como lo hice, aquí hay algo de información que ayudará.

Como dijo anteriormente Alan David Garcia, Devise anula serializable_hash.Para forzar una anulación, puede hacer lo siguiente, por ejemplo, devolver todos los atributos excepto password_digest al llamar al Model#as_json.

def as_json(options = {}) 
    options[:force_except] ||= [:password_digest] 
    super(options) 
end 

Puede especificar los atributos de cualquier modelo deseado para excluir en lugar de sólo options[:force_except]:password_digest.