本文档包含查找的API引用,用于构建 WHERE
数据库查询的子句。学会如何 use 查找,见 进行查询 ;学习如何 创造 新查找,请参见 如何编写自定义查找 .
查找API有两个组件:A RegisterLookupMixin
注册查找的类,以及 Query Expression API 类必须实现的一组方法才能作为查找进行注册。
Django有两个基本类,它们遵循查询表达式API,并从中派生所有Django内置查找:
查找表达式由三部分组成:
字段部分(例如 Book.objects.filter(author__best_friends__first_name...
;
转换部分(可以省略)(例如 __lower__first3chars__reversed
;
查找(例如) __icontains
)如果省略,则默认为 __exact
.
Django使用 RegisterLookupMixin
为类提供在其自身或其实例上注册查找的接口。两个突出的例子是 Field
,所有模型字段的基类,以及 Transform
,是所有Django变换的基类。
在类上实现查找API的混合。
在类或类实例中注册新查找。例如::
DateField.register_lookup(YearExact)
User._meta.get_field("date_joined").register_lookup(MonthExact)
将注册 YearExact
查找上 DateField
和 MonthExact
在网上查找 User.date_joined
(您可以使用 Field Access API 以检索单个字段实例)。它将覆盖已存在的同名查找。在字段实例上注册的查找优先于在类上注册的查找。 lookup_name
将用于此查找(如果提供),否则为 lookup.lookup_name
将会被使用。
要使类成为查找,它必须遵循 Query Expression API . Lookup
和 Transform
当然要遵循这个API。
查询表达式API是一组常见的方法,类将这些方法定义为可在查询表达式中使用,以便将它们自己转换为SQL表达式。直接字段引用、聚合和 Transform
是遵循此API的示例。当类实现以下方法时,称其遵循查询表达式API:
为表达式生成SQL片段。返回元组 (sql, params)
在哪里 sql
是SQL字符串,并且 params
是查询参数的列表或元组。这个 compiler
是一个 SQLCompiler
对象,它具有 compile()
可用于编译其他表达式的方法。这个 connection
是用于执行查询的连接。
调用 expression.as_sql()
通常不正确-相反 compiler.compile(expression)
应该使用。这个 compiler.compile()
方法将负责调用表达式的特定于供应商的方法。
如果自定义关键字参数可能是 as_vendorname()
方法或子类需要提供数据来重写SQL字符串的生成。见 Func.as_sql()
例如用法。
作品像 as_sql()
方法。当表达式由编译时 compiler.compile()
,Django将首先尝试调用 as_vendorname()
在哪里 vendorname
是用于执行查询的后端的供应商名称。这个 vendorname
是其中之一 postgresql
, oracle
, sqlite
或 mysql
用于Django的内置后端。
必须返回名为的查找 lookup_name
. 例如,通过返回 self.output_field.get_lookup(lookup_name)
.
必须返回名为的查找 transform_name
. 例如,通过返回 self.output_field.get_transform(transform_name)
.
Transform
参考¶A Transform
是用于实现字段转换的泛型类。一个突出的例子是 __year
它改变了 DateField
变成一个 IntegerField
.
使用的符号 Transform
在查找表达式中是 <expression>__<transformation>
(例如) date__year
)
本课程遵循 Query Expression API ,这意味着您可以使用 <expression>__<transform1>__<transform2>
. 这是一个专门的 Func() expression 只接受一个论点。它也可以在过滤器的右侧使用,或者直接用作注释。
一个布尔值,指示此转换是否应同时应用于 lhs
和 rhs
. 双边转变将适用于 rhs
与它们在查找表达式中的显示顺序相同。默认设置为 False
. 例如用法,请参见 如何编写自定义查找 .
左手边——正在改变的东西。它必须跟随 Query Expression API .
查找的名称,用于在分析查询表达式时对其进行标识。它不能包含字符串 "__"
.
Lookup
参考¶A Lookup
是用于实现查找的泛型类。查找是一个左侧的查询表达式, lhs
;右侧, rhs
和一个 lookup_name
用于在 lhs
和 rhs
如 lhs in rhs
或 lhs > rhs
.
在表达式中使用查找的主要表示法是 <lhs>__<lookup_name>=<rhs>
。查找也可以直接用于 QuerySet
过滤器::
Book.objects.filter(LessThan(F("word_count"), 7500))
…或注解:
Book.objects.annotate(is_short_story=LessThan(F("word_count"), 7500))
左手边--正在查找的内容。该对象通常跟随在 Query Expression API 。它也可能是一个普通的价值。
右手边-什么 lhs
正在与进行比较。它可以是一个普通值,也可以是编译成SQL的值,通常是 F()
对象或 QuerySet
.
此查找的名称,用于在分析查询表达式时标识它。它不能包含字符串 "__"
.
默认为 True
。什么时候 rhs
是一个简单的值, prepare_rhs
确定是否应准备将其用作查询中的参数。为了做到这一点, lhs.output_field.get_prep_value()
如果已定义,则调用,或者 rhs
被包裹在 Value()
否则的话。
返回元组 (lhs_string, lhs_params)
,由返回 compiler.compile(lhs)
. 可以重写此方法以优化 lhs
进行处理。
compiler
是一个 SQLCompiler
对象,用作 compiler.compile(lhs)
编译用 lhs
. 这个 connection
可用于编译特定于供应商的SQL。如果 lhs
不是 None
,将其用作已处理的 lhs
而不是 self.lhs
.
行为方式与 process_lhs()
,右侧。
12月 18, 2023