2017-06-12 47 views
1

在Django中,我可以在多個模型上重新使用現有的Q對象,而無需使用兩次相同的過濾器?我可以使用Django ORM中的Q對象查找相關字段嗎?

我在想沿下方的僞Django的代碼行的東西,但沒有找到文檔中任何相關信息:

class Author(Model): 
    name = TextField() 
    company_name = TextField() 

class Book(Model): 
    author = ForeignKey(Author) 

# Create a Q object for the Author model 
q_author = Q(company_name="Books & co.") 

# Use it to retrieve Book objects 
qs = Book.objects.filter(author__matches=q_author) 

如果這是不可能的,我可以擴展現有的Q對象在相關領域工作?僞例如:

# q_book == Q(author__company_name="Books & co.") 
q_book = q_author.extend("author") 

# Use it to retrieve Book objects 
qs = Book.objects.filter(q_book) 

我發現接近使用子查詢,這是一個有點笨拙的唯一的事:

qs = Book.objects.filter(author__in=Author.objects.filter(q_author)) 
+0

喜歡它只是需要'author__company_name =「書籍和Co」我不明白你的'Q'對象在這裏,你的第一個查詢看起來使用' – Sayse

+0

對不起,我想我應該有使它更清晰。我真正的Q對象非常大(遠遠超過我的例子),我真的很想在相關模型上重用它,而不必重新定義它兩次。 –

回答

3

從我的評論中可以看出,它看起來像是在嘗試將一組通用參數傳遞給多個過濾器,爲此您只需打開一個字典即可打包

在字典中的值仍然可以爲Q對象如果需要的話,如果它是你會傳遞到過濾器參數的值通常

args = { 'author__company_name': "Books & co" } 
qs = Book.objects.filter(**args) 

args['author_name'] = 'Foo' 
qs = Book.objects.filter(**args) 

不同車型之間共享這一點,你必須做一些字典重整

author_args = { k.lstrip('author__'): v for k, v in args.items } 
+0

謝謝!我在一些地方實際上使用了這種模式。我的目標是能夠將同一組過濾器傳遞給多個_models_。很明顯,''Book.objects.filter(** args)'和'Author.objects.filter(** args)'具有相同的'args'不能直接使用,但這正是我想要實現的。 –

+0

@ F.X。 - 對啊,我現在看到,我認爲沒有比以相同/類似方式使用解壓縮更好的方式,無論您遇到同樣的問題,以確保兩個模型中都存在字段 – Sayse

+0

字段實際上來自在這兩種情況下都是Author模型,但我想通過使用完全相同的一組過濾器來過濾相關的'author'字段中的'Books'。我想沒有辦法做到這一點,然後... –

2

你可以做到這一點

books = Book.objects.filter(author__company_name="Books & co") 
+0

這當然有效,但我編輯了我的問題,以清楚說明我想避免重新定義過濾器,如答案。抱歉! –

相關問題