设置多态 has_many :through 关系 [英] Setting up a polymorphic has_many :through relationship

查看:19
本文介绍了设置多态 has_many :through 关系的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

rails g model Article name:string
rails g model Category name:string
rails g model Tag name:string taggable_id:integer taggable_type:string category_id:integer

我已经创建了我的模型,如前面的代码所示.文章将是许多可以带有标签的模型之一.类别模型将包含可以分配的所有类别.标签模型将是一个多态连接表,它表示标记的关系.

I have created my models as shown in the preceding code. Articles will be one of many models which can have tags. The category model will contain all categories which may be assigned. The tag model will be a polymorphic join-table which represents tagged relationships.

class Article < ActiveRecord::Base
  has_many :tags, :as => :taggable
  has_many :categories, :through => :taggable
end

class Category < ActiveRecord::Base
  has_many :tags, :as => :taggable
  has_many :articles, :through => :taggable
end

class Tag < ActiveRecord::Base
  belongs_to :taggable, :polymorphic => true
  belongs_to :category
end

我似乎无法让它工作,我可以做到非多态,但我一定是多态部分有问题.有什么想法吗?

I can't seem to get this to work, I can do it non polymorphic, but I must have something wrong with the polymorphic part. Any ideas?

仍然没有做到这一点:

class Article < ActiveRecord::Base
    has_many :taggables, :as => :tag
    has_many :categories, :through => :taggables, :source => :tag, :source_type => "Article"
end
class Category < ActiveRecord::Base
    has_many :taggables, :as => :tag
    has_many :articles, :through => :taggables, :source => :tag, :source_type => "Article"
end
class Tag < ActiveRecord::Base
  belongs_to :taggable, :polymorphic => true
  belongs_to :category
end

推荐答案

要创建多态 has_many :through,您必须首先创建您的模型.我们将使用Article"、Category"和Tag",其中Tag"是连接模型,Article 是可以用类别标记"的众多对象之一.

To create a polymorphic has_many :through, you must first create your models. We will use'Article,' 'Category,' and 'Tag' where 'Tag' is the join-model and Article is one of many objects which can be "tagged" with a category.

首先创建文章"和类别"模型.这些是不需要特别注意的基本模型,只是:

First you create your 'Article' and 'Category' models. These are basic models which do not need any special attention, just yet:

rails g model Article name:string
rails g model Category name:string

现在,我们将创建我们的多态连接表:

Now, we will create our polymorphic join-table:

rails g model Tag taggable_id:integer taggable_type:string category_id:integer

连接表将两个表连接在一起,或者在我们的例子中通过多态行为将一个表连接到许多其他表.它通过从两个单独的表中存储 ID 来实现这一点.这将创建一个链接.我们的Category"表将始终是Category",因此我们包含category_id".它链接到的表格各不相同,因此我们添加了一个项目taggable_id",其中包含任何可标记项目的 ID.然后,我们使用 'taggable_type' 来完成链接,让链接知道它所链接的内容,例如一篇文章.

The join-table joins together two tables, or in our case one table to many others via polymorphic behavior. It does this by storing the ID from two separate tables. This creates a link. Our 'Category' table will always be a 'Category' so we include 'category_id.' The tables it links to vary, so we add an item 'taggable_id' which holds the id of any taggable item. Then, we use 'taggable_type' to complete the link allowing the link to know what it is linked to, such as an article.

现在,我们需要设置我们的模型:

Now, we need to set up our models:

class Article < ActiveRecord::Base
  has_many :tags, :as => :taggable, :dependent => :destroy
  has_many :categories, :through => :tags
end
class Category < ActiveRecord::Base
  has_many :tags, :dependent => :destroy
  has_many :articles, :through => :tags, :source => :taggable, :source_type => 'Article'
end
class Tag < ActiveRecord::Base
  belongs_to :taggable, :polymorphic => true
  belongs_to :category
end

在此之后,使用以下方法设置您的数据库:

After this, setup your database using:

rake db:migrate

就是这样!现在,您可以使用真实数据设置数据库:

That's it! Now, you can setup your database with real data:

Category.create :name => "Food"
Article.create :name => "Picking the right restaurant."
Article.create :name => "The perfect cherry pie!"
Article.create :name => "Foods to avoid when in a hurry!"
Category.create :name => "Kitchen"
Article.create :name => "The buyers guide to great refrigeration units."
Article.create :name => "The best stove for your money."
Category.create :name => "Beverages"
Article.create :name => "How to: Make your own soda."
Article.create :name => "How to: Fermenting fruit."

现在您有几个类别和各种文章.但是,它们不使用标签进行分类.所以,我们需要这样做:

Now you have a few categories and various articles. They are not categorized using tags, however. So, we will need to do that:

a = Tag.new
a.taggable = Article.find_by_name("Picking the right restaurant.")
a.category = Category.find_by_name("Food")
a.save

然后您可以为每个重复此操作,这将链接您的类别和文章.执行此操作后,您将能够访问每篇文章的类别和每个类别的文章:

You could then repeat this for each, this will link your categories and articles. After doing this you will be able to access each article's categories and each categorie's articles:

Article.first.categories
Category.first.articles

注意事项:

1) 无论何时您要删除由链接模型链接的项目,请确保使用销毁".当您销毁链接对象时,它也会销毁链接.这可确保没有坏链接或死链接.这就是为什么我们使用 ':dependent => :destroy'

1)Whenever you want to delete an item that is linked by a link-model make sure to use "destroy." When you destroy a linked object, it will also destroy the link. This ensures that there are no bad or dead links. This is why we use ':dependent => :destroy'

2)在设置我们的文章"模型时,它是我们的可标记"模型之一,必须使用:as 链接.因为在前面的例子中我们使用了 'taggable_type' 和 'taggable_id',所以我们使用 :as => :taggable.这有助于 Rails 知道如何将值存储在数据库中.

2)When setting up our 'Article' model, which is one our 'taggable' models, it must be linked using :as. Since in the preceeding example we used 'taggable_type' and 'taggable_id' we use :as => :taggable. This helps rails know how to store the values in the database.

3)当将分类链接到文章时,我们使用:has_many :articles, :through => :tags, :source => :taggable, :source_type => '文章'这告诉类别模型它应该有很多 :articles 到 :tags.来源是 :taggable,原因与上述相同.源类型是文章",因为模型会自动将 taggable_type 设置为自己的名称.

3)When linking categories to articles, we use: has_many :articles, :through => :tags, :source => :taggable, :source_type => 'Article' This tells the category model that it should have many :articles through :tags. The source is :taggable, for the same reason as above. The source-type is "Article" because a model will automatically set taggable_type to its own name.

这篇关于设置多态 has_many :through 关系的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆