我的模式有可以用Tags
标记的Articles
和Journals
。这需要一个与我的Tagging
联接表具有多态关系的has_many through:
关联。
好吧,这就是简单且有充分记录的部分。
我的问题是Articles
可以同时具有主标签和子标签。主要标签是我最感兴趣的,但我的模型也需要跟踪这些子标签。子标签只是描述Article
的标签,其重要性较低,但来自Tags
的同一全局池。(实际上,一个Article
的主标签可能是另一个的子标签(。
实现这一点需要Article
模型具有到Tagging
模型的两个关联和到Tags
的两个has_many through:
关联(即#tags和#sub-tag(
到目前为止,这就是我所拥有的,虽然有效,但并没有将主标签和子标签分开。
class Article < ActiveRecord::Base
has_many :taggings, as: :taggable
has_many :tags, through: :taggings
has_many :sub_taggings, as: :taggable, class_name: 'Tagging',
source_type: 'article_sub'
has_many :sub_tags, through: :sub_taggings, class_name: 'Tag', source: :tag
end
class Tagging < ActiveRecord::Base
# id :integer
# taggable_id :integer
# taggable_type :string(255)
# tag_id :integer
belongs_to :tag
belongs_to :taggable, :polymorphic => true
end
class Tag < ActiveRecord::Base
has_many :taggings
end
我知道在那里的某个地方我需要找到source
和source_type
的正确组合,但我无法找到。
为了完整起见,这里是我的article_spec.rb
,我正在使用它来测试这一点——目前在"不正确的标签"上失败了。
describe "referencing tags" do
before do
@article.tags << Tag.find_or_create_by_name("test")
@article.tags << Tag.find_or_create_by_name("abd")
@article.sub_tags << Tag.find_or_create_by_name("test2")
@article.sub_tags << Tag.find_or_create_by_name("abd")
end
describe "the correct tags" do
its(:tags) { should include Tag.find_by_name("test") }
its(:tags) { should include Tag.find_by_name("abd") }
its(:sub_tags) { should include Tag.find_by_name("abd") }
its(:sub_tags) { should include Tag.find_by_name("test2") }
end
describe "the incorrect tags" do
its(:tags) { should_not include Tag.find_by_name("test2") }
its(:sub_tags) { should_not include Tag.find_by_name("test") }
end
end
提前感谢您为实现这一目标提供的任何帮助。主要的问题是我不知道如何告诉Rails文章中sub_tags关联要使用的source_type。
嗯。。。再次沉默。。。?SO是什么?你好布勒?
永远不要害怕,答案如下:
在研究了单表继承(不是答案,但对于其他稍微相关的问题,这是一种有趣的技术(之后,我偶然发现了一个SO问题,该问题涉及对同一模型上多态关联的多个引用。(感谢hakunin的详细回答,+1。(
基本上,我们需要为sub_taggings
关联显式定义Taggings
表中taggable_type
列的内容,但不使用source
或source_type
,而是使用:conditions
。
下面显示的Article
模型现在通过了所有测试:
class Article < ActiveRecord::Base
has_many :taggings, as: :taggable
has_many :tags, through: :taggings, uniq: true, dependent: :destroy
has_many :sub_taggings, as: :taggable, class_name: 'Tagging',
conditions: {taggable_type: 'article_sub_tag'},
dependent: :destroy
has_many :sub_tags, through: :sub_taggings, class_name: 'Tag',
source: :tag, uniq: true
end
更新:
这是在标签上产生功能性反向多态性关联的正确Tag
模型。反向关联(即Tag.articles和Tag.sub_tagged_articles(通过测试。
class Tag < ActiveRecord::Base
has_many :articles, through: :taggings, source: :taggable,
source_type: "Article"
has_many :sub_tagged_articles, through: :taggings, source: :taggable,
source_type: "Article_sub_tag", class_name: "Article"
end
我还扩展并成功地测试了该模式,以允许标记&使用相同Tag模型和tagging联接表的其他模型的sub_tagging。希望这能帮助到别人。