我有一个用户模型,其中我使用Amistad gem。到目前为止一切都很好。
在我的应用中,我还有一个members
表,其中只有两个字段:user_id
和group_id
。
由于我需要使用此members
表来存储社区成员,因此我决定将其作为多态表:
class CreateMembers < ActiveRecord::Migration
def change
create_table :members do |t|
t.integer :user_id
t.string :memberable_type
t.integer :memberable_id
end
end
end
要继续,我创建了一个memberable
关注我和我的群组和社区:
# app/models/concerns/memberable.rb
module Memberable
extend ActiveSupport::Concern
included do
has_many :members_users, as: :memberable, class_name: Member
has_many :members, through: :members_users, source: :user
end
end
# app/models/group.rb
class Group < ActiveRecord::Base
include Memberable
belongs_to :user
end
# app/models/community.rb
class Community < ActiveRecord::Base
include Memberable
belongs_to :user
end
到目前为止,所有的协会都很好。但是,由于我的members
表格将包含Groups
和Communities
,因此我需要能够检索我所属的所有具有用户的群组。所以在我的用户模型中,我做了:
class User < ActiveRecord::Base
has_many :members
has_many :groups, through: :members, source: :memberable, source_type: 'Group'
has_many :created_groups, class_name: Group
end
此代码本身运行正常,当我调用user.groups
时,它会生成以下查询:
SELECT `groups`.*
FROM `groups`
INNER JOIN `members` ON `groups`.`id` = `members`.`memberable_id`
WHERE `members`.`user_id` = 1
AND `members`.`memberable_type` = 'Group'
但正如我在开头标题及上面提到的那样,我使用Amistad gem所以我把它包括在内:
class User < ActiveRecord::Base
include Amistad::FriendModel
has_many :members
has_many :groups, through: :members, source: :memberable, source_type: 'Group'
has_many :created_groups, class_name: Group
end
这打破了我的多态关系,我不知道为什么。当调用user.groups
时,Rails会生成以下查询(BAD ONE):
SELECT `groups`.*
FROM `groups`
INNER JOIN `members` ON `groups`.`id` = `members`.`memberable_id`
WHERE `members`.`user_id` = 1
AND `groups`.`memberable_type` = 'Group'
请注意最后一行:AND groups.memberable_type = 'Group'
。我试图查看宝石内部而没有发现为什么会有任何冲突。
任何想法的人?
修改
我分叉了宝石并试图破解。看来gem正在使用squeel
,这正是这个问题的根源。
编辑2
Yeeaaahhh,我找到了解决办法。在我的Member
模型中,我曾经有过:
class Member < ActiveRecord::Base
belongs_to :user
belongs_to :memberable, polymorphic: true
end
为了解决与Squeel
的冲突,我不得不改变它:
class Member < ActiveRecord::Base
belongs_to :user
belongs_to :memberable, polymorphic: true, foreign_type: 'members.memberable_type'
end
答案 0 :(得分:0)
我现在问了这个问题,但事实证明上述情况不起作用。实际上我需要从 Amistad gem 上的Squeel
中移除friend_model/friends
。
可以在https://github.com/softmonkeyjapan/amistad