我为此目的创建了一个联接表。这是代码:
class CreateCategoriesProductsJoin < ActiveRecord::Migration
def self.up
create_table 'categories_products', :id => false do |t|
t.column 'category_id', :integer
t.column 'product_id', :integer
end
end
def self.down
drop_table 'categories_products'
end
end
产品型号:
class Product < ActiveRecord::Base
has_and_belongs_to_many :categories
attr_accessor :new_category_name
before_save :create_category_from_name
def create_category_from_name
create_category(:name => new_category_name) unless new_category_name.blank?
end
end
和类别模型:
class Category < ActiveRecord::Base
has_and_belongs_to_many :products
end
到目前为止一切顺利。问题出在form.html.erb上。 代码在这里:
<p>
<label for="product_category_id">Category:</label><br />
<%= f.collection_select :category_id, Category.find(:all), :id, :name, :prompt => "Select a Category" %>
or create one:
<%= f.text_field :new_category_name %>
</p>
我尝试在选择框中加载类别但是我收到一条消息“未定义的方法`category_id'用于#”。
我不明白为什么?我也尝试过has_many:通过但同样的事情发生了。
我应该能够以这种方式绘制类别,因为它们是相关联的,但我不是。有什么想法吗?
我尝试了railscast.com的screancast,但没有运气。您是否考虑过产品类别,子类别关联的完整教程/示例?我还没有找到一个下降的(除了railscast,但这对我不起作用)。
非常感谢您的时间,感谢您回答的麻烦(如果您这样做的话)。
编辑:我发现产品型号存在问题。这是修复:
class Product < ActiveRecord::Base
belongs_to :category
def category_name
category.name if category
end
def category_name=(name)
self.category = Category.find_by_name(name) unless name.blank?
end
end
编辑2:我的类别也有另一个问题。
类别名称不会出现在视图中。我调用了category_name函数,但我得不到任何回报。像这样(show.html.erb):
<p>
<label for="product_category_id">Category:</label><br />
<%= f.collection_select :category_name, Category.find(:all), :id, :name, :prompt => "Select a Category" %>
or create one:
<%= f.text_field :new_category_name %>
</p>
或(show.html.erb):
<td><%= product.category_name %></td>
我尝试更改为has_and_belongs_to_many :categories
,至少我收回了“类别”作为一个奇怪的名字......因为我有4个类别。
产品只属于一个类别。
PS:再次,谢谢你的时间。
答案 0 :(得分:0)
<%= f.collection_select :category_id ... %>
该行正在表单对象上查找.category_id
,该表单对象具有依赖于为其创建表单的对象的访问器(我假设它是一个产品对象)。产品对象具有has_and_belongs_to_many
与类别的关系的属性,但它不是单个类别ID。可用的方法列于here。我不确定因为我没有使用has_and_belongs_to_many
,但我认为你会想要
<%= f.collection_select :categories_singular_ids ... %>
collection_select需要是一个多选项,因此对于你的html,你需要在最后一个选项哈希中:multiple => true
。
答案 1 :(得分:0)
尝试以下方法:
<%= f.select :category_ids, Category.pluck(:name, :id), { prompt: "Select a Category" }, multiple: true %>
不要忘记允许category_ids
,即:
params.require(:product).permit(category_ids: [])