2014-07-25 78 views
5

如何將這個mysql查詢導入到django ORM中?Django具有多個連接字段的ORM查詢

SELECT search_products.model, search_products.year, search_products.size, search_avg_price.estimated_price 
FROM search_products 
left JOIN search_avg_price 
ON search_products.model=search_avg_price.model and search_products.size=search_avg_price.size and search_products.year=search_avg_price.year 

我已經嘗試

latest_products = Products.objects.all().prefetch_related("avg_price") 

,但是這是由Django的翻譯爲

SELECT `search_products`.`id`, `search_products`.`size`, `search_products`.`year`, , `search_products`.`model`, `search_products`.`avg_price_id` 
FROM `search_products` 

latest_products = Products.objects.all().select_related("avg_price") 

這是由Django的翻譯爲:

SELECT `search_products`.`id`, `search_products`.`size`, `search_products`.`year`, , `search_products`.`model`, `search_products`.`avg_price_id`, `search_avg_price`.`id`, `search_avg_price`.`model`, `search_avg_price`.`size`, `search_avg_price`.`year`, `search_avg_price`.`estimated_price` 
FROM `search_products` 
INNER JOIN `search_avg_price` ON (`search_products`.`avg_price_id` = `search_avg_price`.`id`) 

,如果我在數據庫中運行我得到正確的結果上面的SQL ...

編輯:模型和視圖

class Avg_price(models.Model): 
model = models.CharField(max_length=50, blank=True) 
size= models.IntegerField(blank=True, null=True) 
year= models.IntegerField(blank=True, null=True) 
estimated_price= models.IntegerField(blank=True, null=True) 

class Products(models.Model): 
product_id =models.IntegerField(blank=True, null=True) 
link_id = models.CharField(max_length=200, blank=True) 
location = models.CharField(max_length=200, blank=True) 
model = models.CharField(max_length=50, blank=True) 
size= models.IntegerField(blank=True, null=True) 
price= models.IntegerField(blank=True, null=True) 
year= models.IntegerField(blank=True, null=True) 
type=models.ForeignKey(Type) 
avg_price = models.ForeignKey(Avg_price) 

def __unicode__(self): # Python 3: def __str__(self): 
    return self.location 

模板

{% if latest_products %} 
    {% for product in latest_products %} 
    <ul> 
    <li id="col_one"> 
     <h5>{{product.avg_price.estimated_price}}</h5> 
     <h5>{{product.model}}</h5> 
+0

你不爲此需要'select_related'或'prefetch_related',假設使用外鍵或多對多關係,您希望使用過濾器與另一個模型綁定。你能發佈你的模型代碼嗎? – Tom

回答

1

嘗試查詢像這樣:

qs = Product.objects.filter(
    avg_price__model__isnull=True).filter(
    avg_price__size__isnull=True).filter(
    avg_price__year__isnull=True).values_list(
    'model', 'year', 'size', 'avg_price__estimated_price') 

測試:

print(qs.query) 

說明:

從您的產品型號,您正在訪問每次ForeignKeyavg_price和其他所需的當您返回的時間是NULL這種模式相對場該查詢基於LEFT JOIN。這裏有跨越的關係看UPS的文檔:

https://docs.djangoproject.com/en/dev/topics/db/queries/#lookups-that-span-relationships

然後values_list使你可以指定哪些值返回。下面是關於values_list文檔:

https://docs.djangoproject.com/en/dev/ref/models/querysets/#django.db.models.query.QuerySet.values_list

+0

我試過並得到錯誤:「FieldError:無法將關鍵字'avg_price.estimated_price'解析爲字段」。看來django無法看到其他表格......並且我需要顯示錶格產品的所有結果,並在每次出現時添加表格avg_price的結果(年份,模型和大小)......感謝幫助 – user2950162

+0

用'avg_price__estimated_price'而不是'avg_price.estimated_price'怎麼樣? –

+0

結果查詢是從一個我想建立不同的... SELECT'search_productsmodel','search_products'.'year','search_products'.'size','search_avg_price'.'estimated_price' FROM'search_products' INNER JOIN'search_avg_price' ON('search_products'.'avg_price_id' ='search_avg_price'.'id') WHERE('search_avg_price'.'model' IS NULL AND'search_avg_price'.'size' IS NULL AND'search_avg_price'.'年份是空的) – user2950162

1

你可以通過表列表方法額外的()並把條件從您的SQL查詢的ON到其中部分額外的()

Product.objects.extra(
    tables=['search_avg_price'], 
    where=[ 
     '"search_products"."model"="search_avg_price"."model"', 
     '"search_products"."size"="search_avg_price"."size"', 
     '"search_products"."year"="search_avg_price"."year"' 
    ] 
) 

閱讀更多關於額外的: https://docs.djangoproject.com/en/1.6/ref/models/querysets/#extra