英文:
What Am I doing wrong in the has many through association In Rails 6?
问题
所以,我有3个模型(account
,user_category
,category
),每个模型都在不同的文件夹内。
我定义了一个has_many through
关联,通过中间表User Category
将Account
关联到Category
,这样用户可以拥有多个类别,但它没有按预期工作。
账户模型
module AccountBlock
class Account < AccountBlock::ApplicationRecord
ActiveSupport.run_load_hooks(:account, self)
self.table_name = :accounts
include Wisper::Publisher
has_many :user_categories, class_name: "BxBlockCategories::UserCategory", dependent: :destroy
has_many :categories, class_name: "BxBlockCategories::Category", through: "user_categories", dependent: :delete_all
end
end
用户类别模型
module BxBlockCategories
class UserCategory < ApplicationRecord
self.table_name = :user_categories
belongs_to :account, class_name: "AccountBlock::Account", foreign_key: :account_id
belongs_to :category, class_name: "BxBlockCategories::Category", foreign_key: :category_id
end
end
类别模型
module BxBlockCategories
class Category < BxBlockCategories::ApplicationRecord
self.table_name = :categories
has_and_belongs_to_many :sub_categories, join_table: :categories_sub_categories, dependent: :destroy
has_many :contents, class_name: "BxBlockContentmanagement::Content", dependent: :destroy
has_many :ctas, class_name: "BxBlockCategories::Cta", dependent: :nullify
has_many :user_categories, class_name: "BxBlockCategories::UserCategory", dependent: :destroy
has_many :accounts, class_name: "AccountBlock::Account", through: :user_categories
end
如果我使用category.account
,它可以工作,但对于account.categories
,它返回一个空的关联。为什么会这样呢?
希望有人能帮我解决这个问题。
英文:
So, I have 3 models(account, user_category, category) every model is inside different folders.
I've defined a has_many through association to associate Account
to Category
through middle table User Category
so that a user can have many categories but it is not working as intended.
Account Model
module AccountBlock
class Account < AccountBlock::ApplicationRecord
ActiveSupport.run_load_hooks(:account, self)
self.table_name = :accounts
include Wisper::Publisher
has_many :user_categories, class_name: "BxBlockCategories::UserCategory", dependent: :destroy
has_many :categories, class_name: "BxBlockCategories::Category", through: "user_categories", dependent: :delete_all
end
User Category Model
module BxBlockCategories
class UserCategory < ApplicationRecord
self.table_name = :user_categories
belongs_to :account, class_name: "AccountBlock::Account", foreign_key: :account_id
belongs_to :category, class_name: "BxBlockCategories::Category", foreign_key: :category_id
end
end
Category Model
module BxBlockCategories
class Category < BxBlockCategories::ApplicationRecord
self.table_name = :categories
has_and_belongs_to_many :sub_categories,
join_table: :categories_sub_categories, dependent: :destroy
has_many :contents, class_name: "BxBlockContentmanagement::Content", dependent: :destroy
has_many :ctas, class_name: "BxBlockCategories::Cta", dependent: :nullify
has_many :user_categories, class_name: "BxBlockCategories::UserCategory", dependent: :destroy
has_many :accounts, class_name: "AccountBlock::Account", through: :user_categories
end
It works if I do category.account but returns an empty Association for account.categories.
Why is that?
I would love someone can help me.
I've included I've tried so far in the code above.
答案1
得分: 1
这里的问题不在于关联。问题在于您正在犯一个典型的初学者错误,尝试在整个记录集合上调用一个实例方法。
想象一下,你面前有一群人,然后你问:“你叫什么名字?” - 这会怎么工作?他们都会同时喊出他们的名字吗,还是只是盯着你看,好像你是个傻瓜?
如果您想要获取给定账户的类别,您需要遍历结果:
AccountBlock::Account.first.categories.each do |category|
puts category.name
end
关联关系也过于复杂,您可以通过正确使用模块嵌套来消除许多过度配置:
module AccountBlock
# ApplicationRecord被解析为AccountBlock::ApplicationRecord
class Account < ApplicationRecord
ActiveSupport.run_load_hooks(:account, self)
self.table_name = :accounts
has_many :user_categories,
# 好 - 我们在另一个模块中引用一个常量。
class_name: "BxBlockCategories::UserCategory",
dependent: :destroy
has_many :categories,
class_name: "BxBlockCategories::Category",
through: "user_categories",
dependent: :delete_all
end
end
module BxBlockCategories
class UserCategory < ApplicationRecord
self.table_name = :user_categories
# 当可以从关联的名称推导出时,您不需要指定`foreign_key`。
belongs_to :account, class_name: 'AccountBlock::Account'
belongs_to :category
end
end
module BxBlockCategories
class Category < ApplicationRecord
self.table_name = :categories
has_many :user_categories, dependent: :destroy
has_many :accounts,
through: :user_categories,
class_name: 'AccountBlock::Account'
end
end
英文:
The problem here isn't the assocations. It's that you're making a classic beginner misstake and calling an instance method on an whole collection of records.
Imagine you have an entire group of people in front of you and you ask "What is your name?" - how would that work? Are they all going to shout their names at the same time or just stare at your like you're an idiot?
If you want to get the categories for a given account you need to loop through the results:
AccountBlock::Account.first.categories.each do |category|
puts category.name
end
The assocations are also very overcomplicated and you can get rid of a lot of over-configuration by just using the module nesting correctly:
module AccountBlock
# ApplicationRecord is resolved as AccountBlock::ApplicationRecord
class Account < ApplicationRecord
ActiveSupport.run_load_hooks(:account, self)
self.table_name = :accounts
has_many :user_categories,
# good - we are referring to a constant in another module.
class_name: "BxBlockCategories::UserCategory",
dependent: :destroy
has_many :categories,
class_name: "BxBlockCategories::Category",
through: "user_categories",
dependent: :delete_all
end
end
module BxBlockCategories
class UserCategory < ApplicationRecord
self.table_name = :user_categories
# you don't need specify `foreign_key` when it can be derived from the name of the association.
belongs_to :account, class_name: 'AccountBlock::Account'
belongs_to :category
end
end
module BxBlockCategories
class Category < ApplicationRecord
self.table_name = :categories
has_many :user_categories, dependent: :destroy
has_many :accounts,
through: :user_categories,
class_name: 'AccountBlock::Account'
end
end
答案2
得分: 0
我发现了我之前做错的地方。
在账户模型文件中,当我使用through: "user_categories"
时,我使用了一个字符串字面量,这导致了问题。相反,我必须使用一个符号,像这样 through: :user_categories
。
英文:
So, I figured out what I was doing wrong.
In the Account Model file when I used through: "user_categories"
I used a string literal which was causing the issue. Instead I had to use a symbol like this through: :user_categories
.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论