Pergunta

Alguém sabe como fazer uma associação polimórfica em Mongoid Isso é de favor relacional, mas não a incorporação.

Por exemplo, este é o meu Assignment modelo:

class Assignment
  include Mongoid::Document
  include Mongoid::Timestamps

  field :user
  field :due_at, :type => Time

  referenced_in :assignable, :inverse_of => :assignment
end

Isso pode ter uma relação polimórfica com vários modelos:

class Project
  include Mongoid::Document
  include Mongoid::Timestamps

  field :name, :type => String

  references_many :assignments
end

Isso lança um erro dizendo constante desconhecido atribuível. Quando eu mudo o reference para embed, tudo isso funciona como documentado em Documentação de Mongoid, mas eu preciso que seja reference.

Obrigado!

Foi útil?

Solução

Do grupo Mongoid Google, parece que isso não é suportado. Aqui está o Postagem mais recente relevante Eu encontrei.

De qualquer forma, isso não é difícil de implementar manualmente. Aqui está meu link polimórfico chamado sujeito.

A implementação de parte inversa da relação pode ser um pouco mais complicada, especialmente porque você precisará do mesmo código em várias classes.

class Notification
  include Mongoid::Document
  include Mongoid::Timestamps

  field :type, :type => String
  field :subject_type, :type => String
  field :subject_id, :type => BSON::ObjectId

  referenced_in :sender, :class_name => "User", :inverse_of => :sent_notifications
  referenced_in :recipient, :class_name => "User", :inverse_of => :received_notifications

  def subject
    @subject ||= if subject_type && subject_id
      subject_type.constantize.find(subject_id)
    end
  end

  def subject=(subject)
    self.subject_type = subject.class.name
    self.subject_id   = subject.id
  end
end

Outras dicas

Respondendo a um post antigo, mas alguém pode achar útil.

Agora há também um polimórfico belongs_to:

class Action                                                                                                                           
  include Mongoid::Document                                                                                                            
  include Mongoid::Timestamps::Created                                                                                                 

  field :action, type: Symbol

  belongs_to :subject, :polymorphic => true                                                                                            
end

class User                                                                                                                             
  include Mongoid::Document                                                                                                            
  include Mongoid::Timestamps                                                                                                          
  field :username, type: String
  has_many :actions, :as => :subject   
end

class Company                                                                                                                          
  include Mongoid::Document                                                                                                            
  include Mongoid::Timestamps                                                                                                          

  field :name, type: String                                                                                                            

  has_many :actions, :as => :subject
end

Rails 4+

Veja como você implementaria Associações polimórficas dentro Mongóide para Comment modelo que pode pertencer a ambos Post e Event modelo.

o Comment Modelo:

class Comment
  include Mongoid::Document
  belongs_to :commentable, polymorphic: true

  # ...
end

Post / Event Modelos:

class Post
  include Mongoid::Document
  has_many :comments, as: :commentable

  # ...
end

Usando preocupações:

No Rails 4+, você pode usar o padrão de preocupação e criar um novo módulo chamado commentable dentro app/models/concerns:

module Commentable
  extend ActiveSupport::Concern

  included do
    has_many :comments, as: :commentable
  end
end

e somente include Este módulo em seus modelos:

class Post
  include Mongoid::Document
  include Commentable

  # ...
end
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top