0

我正在开发一个新的 Rails 项目,在这个项目中我有产品和产品类别。

因此,这些类别彼此非常不同,例如,船、房屋、汽车。

汽车类别可能具有“Mph”、“型号”、“品牌”、“年份”等标准。房屋类别将包含“房间”、“年份”、“城市”、“邮政编码”等内容。

我希望这是非常动态的,以便我能够从后端面板添加/删除标准和添加/删除类别。

现在我的问题是,我一直在玩这个,我无法真正弄清楚这个概念的逻辑,我尝试了一些解决方案,但是它们非常奇怪而且效率很低。也许一些铁杆 Rails 编码器可以给我一个提示,如何解决这个难题?

所以我能想出的最好的解决方案是:

四种型号:

 _______________________
| Product.rb            |
 -----------------------
| id          | integer |
 -----------------------
| category_id | integer |
 -----------------------
| Title       | string  |
 -----------------------
| Description | text    |
 -----------------------

 _______________________
| Category.rb           |
 -----------------------
| id          | integer |
 -----------------------
| Title       | string  |
 -----------------------
| Description | text    |
 -----------------------

 _______________________
| Criteria.rb           |
 -----------------------
| id          | integer |
 -----------------------
| category_id | integer |
 -----------------------
| Name        | string  |
 -----------------------
| Default     | string  |
 -----------------------
| Description | text    |
 -----------------------

 _______________________
| ProductInfo.rb        |
 -----------------------
| id          | integer |
 -----------------------
| product_id  | integer |
 -----------------------
| Name        | string  |
 -----------------------
| Value       | text    |
 -----------------------

它是如何连接的:

Criteria.rb is connected to Category.rb with a category_id and has_many/belongs_to relation
Product.rb is connected to Category.rb with a category_id and has_many/belongs_to relation
ProductInfo.rb is connected to Product.rb with a product_id and has_many/belongs_to relation.
Category.rb is the heart og this solution. The category model, both have many products and criterias.

实际上它应该如何工作:

In the show category page, i would first print out all the criterias for the given category.
Afterwards i would make a @products.each do |product|.
In the @products.each block, i would make a @category.criterias.each do |criteria|.
In the @category.criterias.each block, i would then run something like product.productinfos.where(:name => criteria.name). 
And then run it one by one.

结论,这个解决方案确实有效,但我怀疑它是最好的解决方案。它将产生非常大的加载时间,高流量和大量数据。而且我需要编写非常奇怪和不可读的代码。

这是一个相当长的问题,并且可能非常令人困惑,所以如果有什么请直接说。另外,我在 Stackoverflow 和谷歌上都搜索了很多这样的问题,但我找不到这样的问题。

奥鲁夫尼尔森。

4

2 回答 2

1

在我看来,由于很多性能问题,最好不要定义额外的表来处理这个问题。我处理此类事情的偏好是在产品表中使用序列化列。这种方法降低了直接在数据库中搜索的能力,但无论如何您都不想这样做。要处理搜索,您必须添加某种索引搜索机制。像acts_as_ferret 甚至Solr 或ElasticSearch。

如果您使用的是 postgres,请查看https://github.com/softa/activerecord-postgres-hstore

对于 Mysql,使用 Rails 内置的“存储” http://api.rubyonrails.org/classes/ActiveRecord/Store.html

class Product < ActiveRecord::Base
  has_and_belongs_to_many :categories
  store :settings
end

要为每个类别设置标准,请执行以下类似操作:

class Category < ActiveRecord::Base
  has_and_belongs_to_many :products


  def criteria
     @criteria_list ||= self[:criteria].split('|')
     @criteria_list
  end

  def criteria=(names)
    self[:criteria] = names.join('|')
  end

end

每次将产品添加到类别时,请检查该类别中的所有条件是否在产品的属性哈希键中可用。如果没有,请根据需要添加默认值。

您还可以使用从产品类别的所有标准字段动态获取访问器名称的过程为属性哈希存储设置访问器?(不确定这个,因为我以前没有这样做过)

您还可以使用 products 表中的类型字段来研究使用 STI(单表继承)。(有据可查)这种方法稍微好一点,因为当产品从一个类别转移到另一个类别时,属性不会改变。

class Gadget < Product
   store_accessor :manufacturer, :model
end

class Phone < Gadget
   store_accessor :os, :touch_screen, :is_smart
end

希望这可以帮助

于 2012-07-05T01:02:56.513 回答
0

否则,第二种方法是使用 nosql 数据库。用 mongoid 试试 mogodb,相当稳定。这将非常适合您对变量属性的要求。您也可以稍后轻松添加任何其他类别。

据我所知,使用 mysql,您最终将创建多个数据库来存储这些动态数据,这势必会影响性能。

更新 -

除了使用 nosql 可以使您的数据变得灵活之外,在转移到那里之前您还需要考虑许多事情。我只是根据您需要灵活的数据库结构的事实提出建议。从 mogodb 文档开始,它们是很好的起点。

于 2012-07-19T14:02:46.597 回答