2012-10-29 15 views
23

Questa domanda si riferisce ad AMS 0,8Serializzatori modello attivo belongs_to

Ho due modelli:

class Subject < ActiveRecord::Base 
    has_many :user_combinations 
    has_ancestry 
end 

class UserCombination < ActiveRecord::Base 
    belongs_to :stage 
    belongs_to :subject 
    belongs_to :user 
end 

E due serializzatori:

class UserCombinationSerializer < ActiveModel::Serializer 
     attributes :id 
     belongs_to :stage 
     belongs_to :subject 
end 

class SubjectSerializer < ActiveModel::Serializer 
    attributes :id, :name, :description, :subjects 

    def include_subjects? 
    object.is_root? 
    end 

    def subjects 
    object.subtree 
    end 
end 

Quando un UserCombination viene serializzato, Voglio incorporare l'intero sotto-soggetto delle materie.

Quando cerco di usare questa impostazione ottengo questo errore:

undefined method `belongs_to' for UserCombinationSerializer:Class 

Ho provato a cambiare il UserCombinationSerializer a questo:

class UserCombinationSerializer < ActiveModel::Serializer 
    attributes :id, :subject, :stage 
end 

In questo caso ottengo nessun errore, ma il subject è serializzato nel modo sbagliato - non usando lo SubjectSerializer.

Le mie domande:

  1. non dovrei essere in grado di utilizzare un rapporto belongs_to nel serializzatore?
  2. In caso contrario - come posso ottenere il comportamento desiderato - incorporare l'albero soggetto utilizzando SubjectSerializer?

risposta

37

questo non è davvero elegante, ma sembra funzionare:

class UserCombinationSerializer < ActiveModel::Serializer 
    attributes :id, :stage_id, :subject_id 

    has_one :subject 
end 

non mi piace chiamare has_one, mentre in realtà è un associazione belongs_to:/

EDIT: Ignorare il mio commento su has_one/belongs_to ambiguità, il documento è abbastanza chiaro a riguardo: http://www.rubydoc.info/github/rails-api/active_model_serializers/frames

+4

Va bene, sì, questo funziona. Penso di capire meglio il metodo 'has_one' ora. In un 'Serializer', l'unica cosa interessante è se un metodo restituisce uno o più oggetti. Quindi distinguere tra has_one e belongs_to non è interessante. È un po 'subottimale che la formulazione coincida con la terminologia ActiveRecord, poiché i termini non significano la stessa cosa. – Jesper

+0

Mi sono imbattuto in questo stesso problema solo di recente. Sì, usando l'has_one: l'attributo funziona per me. –

+11

La documentazione per 'ActiveModel :: Serializer' dichiara esplicitamente:" I serializzatori riguardano solo la molteplicità e non la proprietà. Appartiene_ alle associazioni ActiveRecord possono essere incluse utilizzando has_one nel serializzatore. " – awendt

3

E se provaste con qualcosa li ke questo:

class UserCombinationSerializer < ActiveModel::Serializer 
    attributes :subject, 
      :stage, 
      :id 

    def subject 
    SubjectSerializer.new(object.subject, { root: false }) 
    end 

    def stage 
    StageSerializer.new(object.stage, { root: false }) 
    end 
end 
0

In Active Modello Serializzatore 0-10-stabile, belongs_to è ora disponibile.

belongs_to :author, serializer: AuthorPreviewSerializer 
belongs_to :author, key: :writer 
belongs_to :post 
belongs_to :blog 
def blog 
    Blog.new(id: 999, name: 'Custom blog') 
end 

https://github.com/rails-api/active_model_serializers/blob/0-10-stable/docs/general/serializers.md#belongs_to

Così si potrebbe fare:

class UserCombinationSerializer < ActiveModel::Serializer 
    attributes :id 
    belongs_to :stage, serializer: StageSerializer 
    belongs_to :subject, serializer: SubjectSerializer 
end 
Problemi correlati