Rails 3 STI模型嵌套形式

时间:2014-04-23 14:22:14

标签: ruby-on-rails-3 nested-forms sti

我正在尝试在Rails 3中构建一个CRUD控制器和表单。

我有

class Publication < ActiveRecord::Base

  has_many :posts

end

其中Posts是STI模型:

class Post < ActiveRecord::Based
  attr_accessible :title, :description
end

我有一些继承的模型:

class Image < Post
end

class Video < Post
end

class Status < Post
end

我想创建一个用于发布的CRUD,用户可以根据需要添加任意数量的帖子,为任何类型的帖子动态添加嵌套表单。

我是否可以使用支持STI的嵌套表单的宝石?

我尝试构建一个表单,但是我需要修改Publication类并为每个额外的继承模型引入嵌套属性。有没有办法避免这样做?

class Publication < ActiveRecord::Base

  has_many :videos, :dependent => :destroy
  accepts_nested_attributes_for :videos, allow_destroy: true
  attr_accessible :videos_attributes

  has_many :posts

end

2 个答案:

答案 0 :(得分:2)

你可以这样做。

在您的出版物控制器

class PublicationsController < ApplicationController
    def new
       @publication = Publication.new
       @publication.build_post
    end
end

你的模特应该是这样的

class Publication < ActiveRecord::Base
    has_many :posts, dependent: :destroy
    accepts_nested_attributes_for :posts    
end

class Post < ActiveRecord::Base
    belongs_to :publication
    Post_options = ["Image", "Video", "Status"]
end

以您的形式

<%= form_for(@publication) do |f| %>
  <p>
    <%= f.label :title %><br>
    <%= f.text_field :title %>
  </p>

  <p>
    <%= f.label :description %><br>
    <%= f.text_area :description %>
  </p>

   <%= f.fields_for :post do |p| %>
      <%= p.label :post_type %>
      <%= p.select(:post_type, Post::Post_options , {:prompt => "Select"}, {class: "post"}) %>
   <% end %>
  <p>
    <%= f.submit %>
  </p>
<% end %>

注意:您的post_type模型中应该有一个Post属性才能实现此功能。

答案 1 :(得分:2)

我在http://www.powpark.com/blog/programming/2014/05/07/rails_nested_forms_for_single_table_inheritance_associations

撰写了一篇关于此问题的简短博文

我基本上决定使用cocoon gem,它提供了两个辅助方法 - link_to_add_associationlink_to_remove_association,它们动态地将相应的修饰类字段添加到表单中(例如{{ 1}},PostImage

Video

# _form.html.haml = simple_form_for @publication, :html => { :multipart => true } do |f| = f.simple_fields_for :items do |item| = render 'item_fields', :f => item = link_to_add_association 'Add a Post', f, :items, :wrap_object => Proc.new { |item| item = Item.new } = link_to_add_association 'Add an Image', f, :items, :wrap_object => Proc.new { |item| item = Image.new } = link_to_add_association 'Add a Video', f, :items, :wrap_object => Proc.new { |item| item = Video.new } = f.button :submit, :disable_with => 'Please wait ...', :class => "btn btn-primary", :value => 'Save' proc生成正确的对象,在:wrap_object部分内部呈现,如:

_item_fields