2013-07-26 38 views
0

我有一个产品表和相关产品的表,相关工作的一种方式:填充自连接表中的Rails 4

Product(id: int, name: string) 
RelatedProduct(id: int, product1: int, product2: int) 

有如下型号:

class Product < ActiveRecord::Base 
    validates :name, :uniqueness => true, :presence => true 
    has_many :relations, :class_name => "RelatedProducts", :foreign_key => :product1, inverse_of: :source 
    has_many :related_products, through: :relations, :source => :destination 
end 

class RelatedProducts < ActiveRecord::Base 
    belongs_to :source, :class_name => "Product", inverse_of: :relations 
    belongs_to :destination, :foreign_key => :product2, :class_name => "Product" 
end 

这工作,如果我预填充RelatedProducts表,show view将正确显示所有相关产品。我无法弄清楚如何从html中填充RelatedProducts?

<%= form_for(@product) do |f| %> 

    <div class="field"> 
    <%= f.label :name %> 
    <%= f.text_field :name %> 
    </div> 

    <div class="related-products field"> 
    <h3>Related Products</h3> 
    <%= f.collection_check_boxes :related_products, Product.where.not(id: @product.id), :self, :name %> 
    </div> 

    <div class="actions"> 
    <%= f.submit 'Update Products' %> 
    </div> 
<% end %> 

强参数被定义为:

params.require(:product).permit(:name, related_products: [:id, :name]) 
+0

也许尝试为related_products模型制作form_for – amb110395

回答

0

我的解决办法是使该视图使用ID,然后提交他们

<div class="related-products field"> 
    <h3>Related Products</h3> 
    <%= f.collection_check_boxes :related_products, Product.where.not(id: @product.id), :id, :name %> 
</div> 

我随后在功能耦合这将id列表转换为产品列表的型号

def related_products_list=(ids) 
    self.related_products = ids.reject(&:empty?).collect { |id| Product.find(id) } 
end 

这工作提交,但复选框不会预先检查编辑。这是因为该模型谈论的产品,但该视图有一个ID列表,所以不会找到匹配。我使用的解决方案是手动循环访问集合来创建复选框,而不是使用collection_check_boxes。

<% Product.where.not(id: @product.id).each do |p| %> 
    <%= check_box_tag 'product[related_products][]', p.id, @product.is_related_to?(p), id: "product_related_products_" + p.id.to_s %> 
    <%= label_tag "product_related_products_" + p.id.to_s, p.name %> 
<% end %>