django缓存配置
- 首先在setting中配置CACHES,默认的是使用django本机内存作为网站
1
2
3
4
5
6
7'django.core.cache.backends.db.DatabaseCache'
'django.core.cache.backends.dummy.DummyCache'
'django.core.cache.backends.filebased.FileBasedCache'
'django.core.cache.backends.locmem.LocMemCache'
'django.core.cache.backends.memcached.MemcachedCache'
'django.core.cache.backends.memcached.PyLibMCCache'
'django_redis.cache.RedisCache' # 需下载django_redis
redis缓存配置
1 | # pip install django-redis |
9全局配置调用
- 即使用缓存中间件全局配置
1
2
3
4
5MIDDLEWARE = [
...
'django.middleware.cache.CacheMiddleware'
...
]
函数视图缓存
1 | from django.views.decorators.cache import cache_page |
类视图缓存
1 | from django.utils.decorators import method_decorator |
drf缓存
1 | pip install drf-extensions |
简单配置即可用
drf缓存源码分析
1.只对list和retrieve做了缓存处理配置沿用默认的配置和setting中restframework中的配置
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22class BaseCacheResponseMixin:
object_cache_key_func = extensions_api_settings.DEFAULT_OBJECT_CACHE_KEY_FUNC
list_cache_key_func = extensions_api_settings.DEFAULT_LIST_CACHE_KEY_FUNC
object_cache_timeout = extensions_api_settings.DEFAULT_CACHE_RESPONSE_TIMEOUT
list_cache_timeout = extensions_api_settings.DEFAULT_CACHE_RESPONSE_TIMEOUT
class ListCacheResponseMixin(BaseCacheResponseMixin):
@cache_response(key_func='list_cache_key_func', timeout='list_cache_timeout')
def list(self, request, *args, **kwargs):
return super().list(request, *args, **kwargs)
class RetrieveCacheResponseMixin(BaseCacheResponseMixin):
@cache_response(key_func='object_cache_key_func', timeout='object_cache_timeout')
def retrieve(self, request, *args, **kwargs):
return super().retrieve(request, *args, **kwargs)
class CacheResponseMixin(RetrieveCacheResponseMixin,
ListCacheResponseMixin):
pass2.装饰器为一个cacheResponse对象,实例化时传入key_func用作生成key,和过期时间,当访问页面时,调用该对象的call()中的inner()
1
2
3
4
5
6
7
8
9
10
11
12
13def __call__(self, func):
this = self
@wraps(func, assigned=WRAPPER_ASSIGNMENTS)
def inner(self, request, *args, **kwargs):
return this.process_cache_response(
view_instance=self,
view_method=func,
request=request,
args=args,
kwargs=kwargs,
)
return inner3.通过默认的key_func计算出键和过期时间
1
2
3
4
5
6
7
8
9key = self.calculate_key(
view_instance=view_instance,
view_method=view_method,
request=request,
args=args,
kwargs=kwargs
)
timeout = self.calculate_timeout(view_instance=view_instance)4.获取key,如果没有执行视图函数并且未报错(status不为400、500)则存入缓存,如果有直接生成response返回
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25response_triple = self.cache.get(key)
if not response_triple:
# render response to create and cache the content byte string
response = view_method(view_instance, request, *args, **kwargs)
response = view_instance.finalize_response(request, response, *args, **kwargs)
response.render()
if not response.status_code >= 400 or self.cache_errors:
response_triple = (
response.rendered_content,
response.status_code,
response._headers.copy()
)
self.cache.set(key, response_triple, timeout)
else:
# build smaller Django HttpResponse
content, status, headers = response_triple
response = HttpResponse(content=content, status=status)
for k, v in headers.values():
response[k] = v
if not hasattr(response, '_closable_objects'):
response._closable_objects = []
return response
网页限速设定
- 避免恶意频繁访问导致的压力(爬虫、或者网页攻击)
- 原理
- 利用缓存存储根据用户id或者ip存储一个人访问该网页在限定时间中的次数,每次访问时对比缓存是否超过,如果超过次数则需等待设定时间
- 该功能为drf自带,如果普通django视图需要自己手写一个限速功能
全局限速配置
- 分为陌生用户和登录用户,可以限定次数每天访问多少次, 也可限定每分钟访问多少次,10/minute
1
2
3
4
5
6
7
8
9
10REST_FRAMEWORK = {
'DEFAULT_THROTTLE_CLASSES': (
'rest_framework.throttling.AnonRateThrottle',
'rest_framework.throttling.UserRateThrottle'
),
'DEFAULT_THROTTLE_RATES': {
'anon': '100/day',
'user': '1000/day'
}
}
视图限速配置
from rest_framework.throttling import UserRateThrottle, AnonRateThrottle
class GoodsListViewSet(CacheResponseMixin, mixins.ListModelMixin, mixins.GoodsRetrieveModelMixin, viewsets.GenericViewSet):
“””the goods’s list, pagination, search, filter, ordering”””
queryset = Goods.objects.all() # 这里只是帮我们拼凑了sql脚本,并没有执行,只有在for循环的时候执行
throttle_classes = (UserRateThrottle, AnonRateThrottle)