<p>在数据库级别,没有一种有效的方法可以一次针对所有页面类型运行筛选器。由于<code>AiLabResourceMixin</code>被定义为<code>abstract = True</code>,因此该类在数据库中没有自己的表示形式-相反,为<code>AiLabCaseStudy</code>、<code>AiLabBlogPost</code>和<code>AiLabExternalLink</code>分别定义了<code>use_case</code>字段。因此,Django或Wagtail无法将<code>.filter(use_case__slug=slug)</code>转换为SQL查询,因为<code>use_case</code>引用数据库中的三个不同位置</p>
<p>有几种可能的解决方法:</p>
<ul>
<li><p>如果您的数据模型允许,请将其重新构造为使用<a href="https://docs.djangoproject.com/en/stable/topics/db/models/#multi-table-inheritance" rel="nofollow noreferrer">multi-table inheritance</a>-这看起来与您当前的定义非常相似,只是没有<code>abstract = True</code>:</p>
<pre><code>class AiLabResourcePage(ArticlePage):
use_case = models.ForeignKey(AiLabUseCase, on_delete=models.PROTECT)
class AiLabCaseStudy(AiLabResourcePage):
pass
class AiLabBlogPost(AiLabResourcePage):
pass
class AiLabExternalLink(AiLabResourcePage):
pass
</code></pre>
<p><code>AiLabResourcePage</code>将以其自身的形式存在于数据库中,并且您可以使用如下表达式查询其<code>use_case</code>字段:<code>AiLabResourcePage.objects.child_of(self).filter(use_case__slug=slug).specific()</code>。这里会有一个小的性能影响,因为Django必须从一个额外的表中提取数据来构造这些页面对象</p>
</li>
<li><p>在使用<code>specific()</code>运行最终查询之前,对每个特定页面类型运行初步查询以检索匹配的页面ID:</p>
<pre><code>case_study_ids = list(AiLabCaseStudy.objects.child_of(self).filter(use_case__slug=slug).values_list('id', flat=True))
blog_post_ids = list(AiLabBlogPost.objects.child_of(self).filter(use_case__slug=slug).values_list('id', flat=True))
external_link_ids = list(AiLabExternalLink.objects.child_of(self).filter(use_case__slug=slug).values_list('id', flat=True))
children = Page.objects.filter(id__in=(case_study_ids + blog_post_ids + external_link_ids)).specific()
</code></pre>
</li>
</ul>