2017-10-11 112 views
2

序章:在Django如何使/使用自定義數據庫功能

這是所以經常出現的一個問題:

,並可以應用到上面,以及在以下幾點:

我想對SO文檔組成一個例子,但因爲它得到了8月8日關閉, 2017年,我會按照this widely upvoted and discussed meta answer的建議寫我的例子作爲自我回復的帖子。

當然,我很樂意看到任何不同的方法!


問:

的Django/GeoDjango內置有一些數據庫功能,如Lower()MakeValid()可以使用這樣的:

Author.objects.create(name='Margaret Smith') 
author = Author.objects.annotate(name_lower=Lower('name')).get() 
print(author.name_lower) 

有沒有辦法使用和/或創建我自己的基於現有數據庫功能的自定義數據庫功能,如:

如何申請/使用這些功能在Django/GeoDjango內置ORM?

回答

2

Django提供的Func()表達促進數據庫函數的調用的查詢集:

Func()表達式是所有表達式的基本類型,涉及像COALESCELOWER,或聚集體數據庫功能如SUM

有關於如何使用在Django/GeoDjango內置ORM數據庫功能2種選擇:

爲方便起見,我們假設該模型被命名爲MyModel並且該子存儲在一個名爲變量subst

from django.contrib.gis.db import models as gis_models 

class MyModel(models.Model): 
    name = models.CharField() 
    the_geom = gis_models.PolygonField() 
  1. 使用Func()調用的函數d irectly:

    我們還需要下面讓我們查詢工作:

    查詢:

    MyModel.objects.aggregate(
        pos=Func(F('name'), Value(subst), function='POSITION') 
    ) 
    
  2. 創建自己的數據庫功能擴展Func

    我們可以擴展Func類來創建我們自己的數據庫功能:

    class Position(Func): 
        function = 'POSITION' 
    

    ,並在查詢中使用它:

    MyModel.objects.aggregate(pos=Position('name', Value(subst))) 
    

GeoDjango內置附錄:

GeoDjangoFunc()方法得到的替換爲GeoFunc(),並以相同的方式使用它。


廣義含自定義數據庫功能附錄:

如果你想創建一個自定義的數據庫功能(選2),你希望能夠在不知道這一點,事前與任何數據庫使用它,你可以使用Funcas_<database-name>方法,前提是你要使用的功能,在每個數據庫存在:

class Position(Func): 
    function = 'POSITION' # MySQL method 

    def as_sqlite(self, compiler, connection): 
     #SQLite method 
     return self.as_sql(compiler, connection, function='INSTR') 

    def as_postgresql(self, compiler, connection): 
     # PostgreSQL method 
     return self.as_sql(compiler, connection, function='STRPOS') 
相關問題