从rails中的表中获取项目集合的最佳方法?

时间:2012-08-27 09:50:55

标签: ruby-on-rails ruby-on-rails-3 activerecord

我有一个表中的项目列表,我想在新表中创建这些项目的集合。我看过has_many和has_many:通过,但我不确定这些是正确的选择,我不完全确定它们在我的情况下是如何工作的。

一个特殊情况是我希望通过名为typeID的唯一字段而不是普通ID来识别表中的项目。

更多信息:

我的模特:

  create_table "products", :force => true do |t|
    t.integer  "typeID"
    t.string   "name"
    t.decimal  "basePrice",   :precision => 17, :scale => 4
    t.datetime "created_at",                                 :null => false
    t.datetime "updated_at",                                 :null => false
  end

我有很多产品,我需要把它们中的一些捆绑到我可以使用的包中(作为捆绑销售)。这些产品需要能够包含在多个不同的包中。

2 个答案:

答案 0 :(得分:3)

在最简单的情况下,您只需要one to manymany to many关系

一对多:假设一个包可以包含多个项目

class Package < ActiveRecord::Base
    has_many :products
end


class Product < ActiveRecord::Base
    belogs_to :package
end

通过这种方式,您可以将products捆绑在一个包中。

多对多(可能你需要这个)根据你问题的上次更新。

class Package < ActiveRecord::Base
    has_and_belongs_to_many :products
end


class Product < ActiveRecord::Base
    has_and_belongs_to_many :packages
end

现在,您的包裹还应该有一个价格列,其中包含所属产品的价格(可能有一定的折扣:)。这有帮助吗?


你可能不需要这个:
但是,如果您的产品分为几种类型(食品,电子产品,服装等),并且您希望为每个产品分别继承Product,那么您只需要Single Table Inheritance


答案 1 :(得分:1)

如果每种产品只属于一个包装,我会向Samiron推荐一种类似的方法。

但是,如果情况并非如此,我建议使用has_many:through。这是一个例子:

class Package
  has_many :product_listings
  has_many :products, :through => :product_listings

  # allows you to make convenient create/build calls like i do below
  accepts_nested_attributes_for :product_listings
end

class Product
  # defining these relations are only necessary if you want to be able to get all
  # packages a product exists in
  has_many :product_listings
  has_many :packages, :through => :product_listings
end

class ProductListing
  belongs_to :package
  belongs_to :product

  attr_accessible :package_id, :product_id
end

然后,在某种观点中,你可以这样做:

Package.all.each do |package|
  <%= package.name %>  # or whatever attribute the package has
  package.products.each do |product|
    <%= product.name %>  # or whatever attribute the product has
  end
end

修改

请参阅包模型的补充。

以下是将产品添加到产品包中的方法:

package = Package.create(:name => 'some package')

# Rails naming convention for attributes is snake_case, not camelCase (if you care) 
product = Product.create(:name => 'mouse', :base_price => 20.00)

package.product_listings.create(:product_id => product.id)