2013-01-22 40 views
0

對不起有關奇怪的標題,但我無法用幾句話來解釋情況。讓我來說一下:django模板參數和外連接

我有一個喬布斯模型,其對象在模板中顯示。針對每項工作,我也想顯示用戶是否已經申請了這份工作。

我有這些模型

class Job(models.Model): 
    is_valid = models.BooleanField() 
    description = models.CharField() 
    def has_user_applied(self, user): 
     return jobapplication_set.filter(applicant=user).exists() 

class JobApplication(models.Model): 
    applicant = models.ForeignKey(User)  
    job = models.ForeignKey(Job) 
    cover_letter = models.CharField() 

和一個視圖中,我取的所有工作:

jobs = Job.objects.filter(is_valid=True) 
return HttpResponse(... {'jobs': jobs} ...) 

和模板中,我一一列舉:

{% for j in jobs %} 
{{ j.description }} {% if j.has_applied %} (You've already applied) {% endif %} 
{% endfor %} 

然而「has_applied」函數將「user」作爲參數,並且不允許在模板中傳遞參數。

現在我有兩個問題:

我能創造一個「背景」,這樣一些功能可以假設特定用戶是問題而不是將其明確地通過,限制了其在模板中使用?如果這是不可能的,在視圖中的模型對象中註釋這些信息的優雅方式是什麼?

其次,即使我能夠做到這一點,對於每個Job對象,我仍然需要執行一個單獨的查詢來確定用戶是否已經應用。我知道這在使用外部連接的原始SQL中是可行的,但我可以使用django的ORM嗎?

回答

1

最簡單,最詳細的做這件事將只是方式:

視圖

​​3210

模板

{% for job in jobs %} 
    {% if job.pk in jobs_applied_by_user %} 
     … 
+0

謝謝。方式比來回多次查詢更好。但是仍然有內存查找到該集合中,這也有一些成本。我們可能會稍微好一些,以便在大量提取的情況下分頁效率會更高。 – sharjeel

+1

設置查找是O(1)。這不被視爲成本。在分頁情況下,您可以添加'.filter(job__in = jobs)',其中'jobs'是當前頁面。它只會減少從數據庫發送的數據。 –

+0

也許它應該是模板中的{%if job.id in jobs_applied_by_user%}。看起來像ForeignKey字段的「values_list」返回相關的對象id而不是完整的對象。 – sharjeel

1

一個簡單的解決辦法就是寫custom filter

{% for j in jobs %} 
{{ j.description }} {% if j|has_applied:user %} (You've already applied) {% endif %} 
{% endfor %} 

這裏has_applied是自定義過濾器,它會帶user作爲參數。

+0

你沒有解決數據庫查詢線性數量的問題。在這個解決方案中'prefetch_related'是強制性的。 –