有没有办法在活动记录中制作模型方法?
Is there a way to make a model method in active record?
我正在考虑创建一个方法来给我 Active::Record::Associations::CollectionProxy 中的特定对象。
例如,我有一个用户模型,其中包含许多 user_checklists 和 user_checklists belongs_to 清单模型。所以我想创建一个方法来检查清单模型中的值和 return 来自 user_checklist 模型的值。
例如。
清单 table 有以下行
╔═════════════════════╦══════════════════╗
║ id ║ name ║
╠═════════════════════╬══════════════════╣
║ 1 ║ Complete MBA ║
╠═════════════════════╬══════════════════╣
║ 2 ║ Painting class ║
╚═════════════════════╩══════════════════╝
并且用户 table 具有以下
╔═════════════════════╦══════════════════╗
║ id ║ name ║
╠═════════════════════╬══════════════════╣
║ 1 ║ name ║
╚═════════════════════╩══════════════════╝
和user_checklist有下面一行
╔════════════╦════════════╦═══════════════╦═══════════════╗
║ id ║ user_id ║ checklist_id ║ completed ║
╠════════════╬════════════╬═══════════════╬═══════════════╣
║ 1 ║ 1 ║ 1 ║ true ║
╠════════════╬════════════╬═══════════════╬═══════════════╣
║ 2 ║ 1 ║ 2 ║ false ║
╚════════════╩════════════╩═══════════════╩═══════════════╝
所以我想在 user_checklist 中制作一个名为 MBA 的方法,它将给我 MBA 完成值。
这就是我想要的调用方式
user.first.user_checklists.mba.completed
我不知道如何实现。还是我的想法完全错了?
所以我想出了一个办法。在 user_checklists 上创建范围,仅查找 mba_id 和 returns 的值形式 user_checkilust
scope :mba, -> { where(checklist_id: Checklist.where(name: "Completed MBA").first&.id) }
在那之后我可以做到
User.first.user_checklists.mba.first&.completed
所以这对我现在有用。
我建议只选择清单的 ID。
scope :mba, -> { where(checklist_id: Checklist.where(name: "Completed MBA").pluck(:id) }
将从数据库中仅查询所需的列 (id
)(具有更好的性能),
SELECT "checklists"."id" FROM "checklists" WHERE "checklists"."id" =
你可以得到和你一样的东西
User.first.user_checklists.mba.first&.completed
您可以更新范围以避免 N+1 查询:
scope :mba, -> { joins(:checklists).where('checklists.name = "Completed MBA"')
您不需要 select 作用域中的第一个和 id,因为我猜您会在下一个请求中调用 first
方法:
User.first.user_checklists.mba.first&.completed
我正在考虑创建一个方法来给我 Active::Record::Associations::CollectionProxy 中的特定对象。
例如,我有一个用户模型,其中包含许多 user_checklists 和 user_checklists belongs_to 清单模型。所以我想创建一个方法来检查清单模型中的值和 return 来自 user_checklist 模型的值。
例如。 清单 table 有以下行
╔═════════════════════╦══════════════════╗
║ id ║ name ║
╠═════════════════════╬══════════════════╣
║ 1 ║ Complete MBA ║
╠═════════════════════╬══════════════════╣
║ 2 ║ Painting class ║
╚═════════════════════╩══════════════════╝
并且用户 table 具有以下
╔═════════════════════╦══════════════════╗
║ id ║ name ║
╠═════════════════════╬══════════════════╣
║ 1 ║ name ║
╚═════════════════════╩══════════════════╝
和user_checklist有下面一行
╔════════════╦════════════╦═══════════════╦═══════════════╗
║ id ║ user_id ║ checklist_id ║ completed ║
╠════════════╬════════════╬═══════════════╬═══════════════╣
║ 1 ║ 1 ║ 1 ║ true ║
╠════════════╬════════════╬═══════════════╬═══════════════╣
║ 2 ║ 1 ║ 2 ║ false ║
╚════════════╩════════════╩═══════════════╩═══════════════╝
所以我想在 user_checklist 中制作一个名为 MBA 的方法,它将给我 MBA 完成值。
这就是我想要的调用方式
user.first.user_checklists.mba.completed
我不知道如何实现。还是我的想法完全错了?
所以我想出了一个办法。在 user_checklists 上创建范围,仅查找 mba_id 和 returns 的值形式 user_checkilust
scope :mba, -> { where(checklist_id: Checklist.where(name: "Completed MBA").first&.id) }
在那之后我可以做到
User.first.user_checklists.mba.first&.completed
所以这对我现在有用。
我建议只选择清单的 ID。
scope :mba, -> { where(checklist_id: Checklist.where(name: "Completed MBA").pluck(:id) }
将从数据库中仅查询所需的列 (id
)(具有更好的性能),
SELECT "checklists"."id" FROM "checklists" WHERE "checklists"."id" =
你可以得到和你一样的东西
User.first.user_checklists.mba.first&.completed
您可以更新范围以避免 N+1 查询:
scope :mba, -> { joins(:checklists).where('checklists.name = "Completed MBA"')
您不需要 select 作用域中的第一个和 id,因为我猜您会在下一个请求中调用 first
方法:
User.first.user_checklists.mba.first&.completed