查找API引用

本文档包含查找的API引用,用于构建 WHERE 数据库查询的子句。学会如何 use 查找,见 进行查询 ;学习如何 创造 新查找,请参见 如何编写自定义查找 .

查找API有两个组件:A RegisterLookupMixin 注册查找的类,以及 Query Expression API 类必须实现的一组方法才能作为查找进行注册。

Django有两个基本类,它们遵循查询表达式API,并从中派生所有Django内置查找:

  • Lookup :查找字段(例如 exact 属于 field_name__exact

  • Transform :转换字段

查找表达式由三部分组成:

  • 字段部分(例如 Book.objects.filter(author__best_friends__first_name...

  • 转换部分(可以省略)(例如 __lower__first3chars__reversed

  • 查找(例如) __icontains )如果省略,则默认为 __exact .

注册API

Django使用 RegisterLookupMixin 为类提供在其自身或其实例上注册查找的接口。两个突出的例子是 Field ,所有模型字段的基类,以及 Transform ,是所有Django变换的基类。

class lookups.RegisterLookupMixin

在类上实现查找API的混合。

classmethod register_lookup(lookup, lookup_name=None)

在类或类实例中注册新查找。例如::

DateField.register_lookup(YearExact)
User._meta.get_field("date_joined").register_lookup(MonthExact)

将注册 YearExact 查找上 DateFieldMonthExact 在网上查找 User.date_joined (您可以使用 Field Access API 以检索单个字段实例)。它将覆盖已存在的同名查找。在字段实例上注册的查找优先于在类上注册的查找。 lookup_name 将用于此查找(如果提供),否则为 lookup.lookup_name 将会被使用。

get_lookup(lookup_name)

返回 Lookup 名为 lookup_name 在类或类实例中注册,具体取决于调用它的内容。默认实现递归地查看所有父类,并检查是否有注册的查找名为 lookup_name ,返回第一个匹配项。实例查找将用相同的 lookup_name

get_lookups()

方法的类或类实例中注册的每个查找名称的字典。 Lookup 班级。

get_transform(transform_name)

返回一个 Transform 名为 transform_name 在类或类实例中注册。默认实现递归地查看所有父类,以检查是否有注册的转换名为 transform_name ,返回第一个匹配项。

要使类成为查找,它必须遵循 Query Expression API . LookupTransform 当然要遵循这个API。

查询表达式API

查询表达式API是一组常见的方法,类将这些方法定义为可在查询表达式中使用,以便将它们自己转换为SQL表达式。直接字段引用、聚合和 Transform 是遵循此API的示例。当类实现以下方法时,称其遵循查询表达式API:

as_sql(compiler, connection)

为表达式生成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_vendorname(compiler, connection)

作品像 as_sql() 方法。当表达式由编译时 compiler.compile() ,Django将首先尝试调用 as_vendorname() 在哪里 vendorname 是用于执行查询的后端的供应商名称。这个 vendorname 是其中之一 postgresqloraclesqlitemysql 用于Django的内置后端。

get_lookup(lookup_name)

必须返回名为的查找 lookup_name . 例如,通过返回 self.output_field.get_lookup(lookup_name) .

get_transform(transform_name)

必须返回名为的查找 transform_name . 例如,通过返回 self.output_field.get_transform(transform_name) .

output_field

定义由返回的类的类型 get_lookup() 方法。一定是A Field 实例。

Transform 参考

class Transform[源代码]

A Transform 是用于实现字段转换的泛型类。一个突出的例子是 __year 它改变了 DateField 变成一个 IntegerField .

使用的符号 Transform 在查找表达式中是 <expression>__<transformation> (例如) date__year

本课程遵循 Query Expression API ,这意味着您可以使用 <expression>__<transform1>__<transform2> . 这是一个专门的 Func() expression 只接受一个论点。它也可以在过滤器的右侧使用,或者直接用作注释。

bilateral

一个布尔值,指示此转换是否应同时应用于 lhsrhs . 双边转变将适用于 rhs 与它们在查找表达式中的显示顺序相同。默认设置为 False . 例如用法,请参见 如何编写自定义查找 .

lhs

左手边——正在改变的东西。它必须跟随 Query Expression API .

lookup_name

查找的名称,用于在分析查询表达式时对其进行标识。它不能包含字符串 "__" .

output_field

定义此转换输出的类。一定是A Field 实例。默认情况下与 lhs.output_field .

Lookup 参考

class Lookup[源代码]

A Lookup 是用于实现查找的泛型类。查找是一个左侧的查询表达式, lhs ;右侧, rhs 和一个 lookup_name 用于在 lhsrhslhs in rhslhs > 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))
lhs

左手边--正在查找的内容。该对象通常跟随在 Query Expression API 。它也可能是一个普通的价值。

rhs

右手边-什么 lhs 正在与进行比较。它可以是一个普通值,也可以是编译成SQL的值,通常是 F() 对象或 QuerySet .

lookup_name

此查找的名称,用于在分析查询表达式时标识它。它不能包含字符串 "__" .

prepare_rhs

默认为 True 。什么时候 rhs 是一个简单的值, prepare_rhs 确定是否应准备将其用作查询中的参数。为了做到这一点, lhs.output_field.get_prep_value() 如果已定义,则调用,或者 rhs 被包裹在 Value() 否则的话。

process_lhs(compiler, connection, lhs=None)[源代码]

返回元组 (lhs_string, lhs_params) ,由返回 compiler.compile(lhs) . 可以重写此方法以优化 lhs 进行处理。

compiler 是一个 SQLCompiler 对象,用作 compiler.compile(lhs) 编译用 lhs . 这个 connection 可用于编译特定于供应商的SQL。如果 lhs 不是 None ,将其用作已处理的 lhs 而不是 self.lhs .

process_rhs(compiler, connection)[源代码]

行为方式与 process_lhs() ,右侧。