2013-04-04 109 views
1

我想从一个嵌套的窗体构建一个多态关系,这个窗体向后是我找到的所有示例。我希望有人指出我的方式的错误。Rails 3多态嵌套属性

class Container < ActiveRecord::Base 
     belongs_to :content, :polymorphic => true 
end 
class Notice < ActiveRecord::Base 
     has_one :container, :as => :content 
end 
class Form < ActiveRecord::Base 
     has_one :container, :as => :content 
end 

似乎大多数人会从通知或表格建立一个集装箱,但在我的情况下,通知或表格包含的内容(文件位置或几个数据库字段)少量所以它是多干呃从容器中建立通知或表格。

我想我可以通过添加accepts_nested_attributes_for :content解决,但是这给了我一个unrecognized attribute :notice当我尝试创建一个嵌套的通知集装箱(寻找内容,而不是多态关联)

我可以手动和明确的做排除像

if params[:container].has_key('notice') 
    @c = Container.new(params[:container].except(:notice)) 

嵌套的领域,然后建立,但是,这不是一个味道?有没有更好的办法?

谢谢您的阅读!

回答

0

嵌套属性被设计用于从父到孩子,而不是其他方式。此外,在这种情况下,嵌套属性如何知道您是否尝试创建NoticeForm对象?

如果您发现机建立从容器中的内容,你可能有你的协会内而外 - 试着改变你的架构:

class Container < ActiveRecord::Base 
    has_one :notice 
    has_one :form 
end 

class Notice < ActiveRecord::Base 
    belongs_to :container 
end 

class Form < ActiveRecord::Base 
    belongs_to :container 
end 

您可以使用验证,以确保只有一个孩子(:notice:form)实际上是相关的,如果需要的话。

+0

嗯。我以为它会通过simple_fields_for键知道要创建什么对象的方式与我所做的相同。如果我做了你提到的has_one,我就失去了执行Container.find(1).content.get_data的能力,其中get_data已在Notice和Form中定义。 – Questor 2013-04-04 21:22:52

+0

然后你可以改变它来使用STI,并且从一个抽象的Content类继承Notice和Form。或者,您可以在Container模型中创建帮助程序方法和/或缓存以查找内容。 – PinnyM 2013-04-05 02:56:25

+0

+1为abstract_class。我与STI一起去了,但会查看.abstract_class = true来删除重复的字段。谢谢! – Questor 2013-04-09 00:43:38