假设有
User
和 Document
记录。一个 User
has_many :documents
和一个 Document
belongs_to
一个 User
。
一个
Document
记录has_one_attached :file
.
我已经有两个
Document
范围,它们将返回带或不带附加文件的记录:
文档.rb
scope :without_attached_file, -> { where.missing(:file_blob) }
scope :with_attached_file, -> { where.associated(:file_blob) }
如何为
User
模型编写一个范围,以返回所有关联的 User
记录都附加了 Document
的所有 file
记录?
示例:如果
User
有 10 个关联的 Document
记录,并且所有 10 个记录都有一个附加的 file
,则范围应包括该 User
记录。
我相信我应该首先
count
关联的 Document
记录的数量,然后将该数字与 user.documents.with_attached_file.count
返回的数字进行比较,但我无法理解它。
我想出了类似的东西:
scope :with_attached_files_for_all_documents, -> {
joins(documents: :file_attachment)
.group('users.id')
.having("COUNT(documents.id) = COUNT(CASE WHEN active_storage_attachments.record_type = 'Document' THEN documents.id ELSE NULL END)")
}
但这只是返回每个给定
User
记录具有附加文件的文档计数。
有对此有用的查询模式吗?
我确信您可以在单个查询中完成此操作,但我认为这是拥有任何文档的用户与拥有任何缺少文件的文档的用户之间的一组差异。我会通过 3 个查询来完成此操作:
然后你可以像这样构建你的范围:
scope :with_attached_files_for_all_documents, -> {
users_with_files = Document.with_attached_files.select(:user_id)
users_missing_files = Document.without_attached_files.select(:user_id)
where(id: users_with_files).where.not(id: users_missing_files)
}
逻辑上,这是三个查询,但事务上只有一个。前两个在传递到第三个之前不会执行,它们在数据库中作为子查询执行。