2011-02-01 99 views
6

我有一個站點下的一個Django應用程序,我想實施站點範圍緩存。但它被證明是一個真正的麻煩。Django - 多站點站點緩存

發生什麼事是settings.CACHE_MIDDLEWARE_KEY_PREFIX在啓動時設置一次,我不能繼續並根據當前網站的情況進行更改。因此,如果一頁url http://website1.com/abc/被高速緩存,則http://website2.com/abc/會呈現http://website1.com/abc/的高速緩存版本。這兩個網站都運行在同一個Django實例上,因爲這正是Django網站允許我們做的事情。

這是不正確的做法?因爲我無法在運行時動態設置CACHE_MIDDLEWARE_KEY_PREFIX,所以我無法使用Django的全站高速緩存來緩存多個站點。我也無法爲模板和視圖緩存執行此操作。

我得到的印象是,真正需要設置的方式是,每個站點都需要自己的Django實例,除了設置文件外,它們幾乎完全相同,在我的情況下,它只會與CACHE_MIDDLEWARE_KEY_PREFIX的值不同。這些Django實例都讀取和寫入同一個數據庫。這涉及到我,因爲它可能會產生一些新問題。

我會走向正確的軌道還是我誤解了多站點架構如何工作?我檢查了Django文檔,並沒有真正提到如何爲服務多個站點的Django應用程序處理緩存(這不是低級緩存)。

+0

你找到一個解決方案是什麼? – 2012-09-24 14:52:09

回答

1

(免責聲明:以下純屬炒作,並沒有經過測試服用含少許鹽。)

可能可以使用vary_on_headers視圖修飾以包括「主機」緩存鍵中的標題。這應該導致包含HTTP主機頭的緩存鍵,從而有效地隔離您的網站的緩存。

@vary_on_headers('Host') 
def my_view(request): 
    # .... 

當然,這隻會在每個視圖的基礎工作,並且具有一個裝飾添加到所有視圖可以是一個大麻煩。

挖掘source of @vary_on_headers揭示了使用patch_vary_headers()哪些人可能能夠在中間件中使用,以在站點級別應用相同的行爲。沿着線的東西:

from django.utils.cache import patch_vary_headers 

class VaryByHostMiddleware(object): 
    def process_response(self, request, response): 
     patch_vary_headers(response, ('Host',)) 
     return response 
0

您需要更改get_full_path在django.util.cache

def _generate_cache_header_key(key_prefix, request): 
"""Returns a cache key for the header cache.""" 
#path = md5_constructor(iri_to_uri(request.get_full_path())) 
path = md5_constructor(iri_to_uri(request.build_absolute_uri())) # patch using full path 
cache_key = 'views.decorators.cache.cache_header.%s.%s' % (
    key_prefix, path.hexdigest()) 
return _i18n_cache_key_suffix(request, cache_key) 


def _generate_cache_key(request, method, headerlist, key_prefix): 
"""Returns a cache key from the headers given in the header list.""" 
ctx = md5_constructor() 
for header in headerlist: 
    value = request.META.get(header, None) 
    if value is not None: 
     ctx.update(value) 
#path = md5_constructor(iri_to_uri(request.get_full_path())) 
path = md5_constructor(iri_to_uri(request.build_absolute_uri())) 
cache_key = 'views.decorators.cache.cache_page.%s.%s.%s.%s' % (
    key_prefix, request.method, path.hexdigest(), ctx.hexdigest()) 
return _i18n_cache_key_suffix(request, cache_key) 

到build_absolute_uri或創建自己的多站點略有改變緩存中間件。 http://macrotoma.blogspot.com/2012/06/custom-multisite-caching-on-django.html

1

我最近面臨這個問題。我基於documentation所做的就是創建一個自定義方法,將網站ID添加到用於緩存視圖的密鑰中。

在設置中。PY添加KEY_FUNCTION說法:

CACHES = { 
    'default': { 
     'BACKEND': 'path.to.backend', 
     'LOCATION': 'path.to.location', 
     'TIMEOUT': 60, 
     'KEY_FUNCTION': 'path.to.custom.make_key_per_site', 
     'OPTIONS': { 
      'MAX_ENTRIES': 1000 
     } 
    } 
} 

而且我的自定義make_key方法:

def make_key_per_site(key, key_prefix, version): 
    site_id = '' 
    try: 
     site = get_current_site() # Whatever you use to get your site's data 
     site_id = site['id'] 
    except: 
     pass 
    return ':'.join([key_prefix, site_id, str(version), key]) 
+0

get_current_site()需要'請求'參數。這是一個好主意,但最終不起作用。 – Florian 2017-03-27 12:21:20