天天看點

django 1.8 官方文檔翻譯: 2-2-3 查找 API 參考查找 API 參考

查找 API 參考

New in Django 1.7.           

這篇文檔是查找 API 的參考,Django 用這些API 建構資料庫查詢的

WHERE

子句。若要學習如何使用 查找,參見

執行查詢

;若要了解如何建立 新的查找,參見

自定義查找

查找 API 由兩個部分組成:

RegisterLookupMixin

類,它用于注冊查找;

查詢表達式API

,它是一個方法集,類必須實作它們才可以注冊成一個查找。

Django 有兩個類遵循查詢表達式API,且Django 所有内建的查找都繼承自它們:

  • Lookup

    :用于查找一個字段(例如

    field_name__exact

    中的

    exact

  • Transform

    :用于轉換一個字段

查找表達式由三部分組成:

  • 字段部分(例如,

    Book.objects.filter(author__best_friends__first_name...)

  • 轉換部分(可以省略)(例如,

    __lower__first3chars__reversed

    );
  • 查找部分(例如,

    __icontains

    ),如果省略則預設為

    __exact

注冊 API

Django 使用

RegisterLookupMixin

來為類提供接口,注冊它自己的查找。兩個最突出的例子是

Field

(所有模型字段的基類)和

Aggregate

(Django 所有聚合函數的基類)。

class lookups.RegisterLookupMixin

一個mixin,實作一個類上的查找API。

classmethod register_lookup(lookup)

在類中注冊一個新的查找。例如,

DateField.register_lookup(YearExact)

将在

DateField

上注冊一個

YearExact

查找。它會覆寫已存在的同名查找。

get_lookup(lookup_name)

傳回類中注冊的名為

lookup_name

Lookup

。預設的實作會遞歸查詢所有的父類,并檢查它們中的任何一個是否具有名稱為

lookup_name

的查找,并傳回第一個比對。

get_transform(transform_name)

傳回一個名為

transform_name

Transform

。預設的實作會遞歸查找所有的父類,并檢查它們中的任何一個是否具有名稱為

transform_name

一個類如果想要成為查找,它必須實作查詢表達式API。

Lookup

Transform

一開始就遵循這個API。

查詢表達式API是一個通用的方法集,在查詢表達式中可以使用定義了這些方法的類,來将它們自身轉換為SQL表達式。直接的字段引用,聚合,以及

Transform

類都是遵循這個API的示例。當一個對象實作以下方法時,就被稱為遵循查詢表達式API:

as_sql(self, compiler, connection)

負責從表達式中産生查詢字元串和參數。

compiler

是一個

SQLCompiler

對象,它擁有可以編譯其它表達式的

compile()

方法。

connection

是用于執行查詢的連接配接。

調用

expression.as_sql()

一般是不對的 – 而是應該調用

compiler.compile(expression)

compiler.compile()

方法應該在調用表達式的供應商特定方法時格外小心。

as_vendorname(self, compiler, connection)

as_sql()

的工作方式類似。當一個表達式經過

compiler.compile()

編譯之後, Django會首先嘗試調用

as_vendorname()

,其中

vendorname

是用于執行查詢的後端供應商。對于Django内建的後端,

vendorname

postgresql

oracle

sqlite

,或者

mysql

之一。

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()

方法所傳回的類的類型。必須為

Field

的執行個體。

Transform 類參考

class Transform

Transform

是用于實作字段轉換的通用類。一個顯然的例子是

__year

會把

DateField

轉換為

IntegerField

在表達式中執行查找的标記是

Transform<expression>__<transformation>

(例如

date__year

)。

這個類遵循查詢表達式API,也就是說你可以使用

<expression>__<transform1>__<transform2>

bilateral

New in Django 1.8.           

一個布爾值,表明是否對

lhs

rhs

都應用這個轉換。如果對兩側都應用轉換,應用在

rhs

的順序和在查找表達式中的出現順序相同。預設這個屬性為

False

。使用方法的執行個體請見自定義查找。

lhs

在左邊,也就是被轉換的東西。必須遵循查詢表達式API。

lookup_name

查找的名稱,用于在解析查詢表達式的時候識别它。

output_field

為這個類定義轉換後的輸出。必須為

Field

的執行個體。預設情況下和

lhs.output_field

相同。

as_sql()

需要被覆寫;否則抛出

NotImplementedError

異常。

get_lookup(lookup_name)

get_lookup()

get_transform(transform_name)

get_transform()

Lookup 類參考

class Lookup

Lookup

是實作查找的通用的類。查找是一個查詢表達式,它的左邊是

lhs

,右邊是

rhs

lookup_name

用于構造

lhs

rhs

之間的比較,來産生布爾值,例如

lhs in rhs

或者

lhs > rhs

<lhs>__<lookup_name>=<rhs>

這個類并不遵循查詢表達式API,因為在它構造的時候出現了

=<rhs>

:查找總是在查找表達式的最後。

lhs

在左邊,也就是被查找的東西。這個對象必須遵循查詢表達式API。

rhs

在右邊,也就是用來和

lhs

比較的東西。它可以是個簡單的值,也可以是在SQL中編譯的一些東西,比如

F()

對象或者

QuerySet

lookup_name

process_lhs(compiler, connection[, lhs=None])

傳回元組

(lhs_string, lhs_params)

,和

compiler.compile(lhs)

所傳回的一樣。這個方法可以被覆寫,來調整

lhs

的處理方式。

compiler

SQLCompiler

對象,可以像

compiler.compile(lhs)

這樣使用來編譯

lhs

connection

可以用于編譯供應商特定的SQL語句。

lhs

如果不為

None

, 會代替

self.lhs

作為處理後的

lhs

使用。

process_rhs(compiler, connection)

對于右邊的東西,和

process_lhs()

的行為相同。

譯者: Django 文檔協作翻譯小組 ,原文: Lookup expressions 本文以 CC BY-NC-SA 3.0 協定釋出,轉載請保留作者署名和文章出處。 人手緊缺,有興趣的朋友可以加入我們,完全公益性質。交流群:467338606。