一、什么是缓存
缓存是一类可以快速读取数据的介质统称,常用的读取速度很快的介质有内存,所以一般将缓存存储在内存中。
从数据库读多次把所需要的数据取出来,要比从内存或者硬盘等一次读出来付出的成本大很多。缓存对于创建一个高性能的网站和提升用户体验来说是非常重要的。
二、为什么要使用缓存
在 Django 项目中,当用户请求达到视图后,视图会先从数据库中提取数据,然后将其放在模板中渲染。若每次都从数据库中提取数据,必然会导致网站性能降低。不仅服务器压力大,而且客户端也无法及时获得响应。
如果能将渲染后的结果放在速度更快的介质中,每次请求来时,先从这个介质中检查是否有对应的资源。若有直接取出响应即可,大大提高了网站的性能,节省了数据和渲染的时间,而且能提高用户体验。
三、缓存应用场景
缓存主要适用于对页面实时性要求不高的页面。存放在缓存的数据,通常是频繁访问的,而不会经常修改的数据。如:
- 博客文章:假设用户一天更新一篇文章,那么可以为博客设置1天的缓存,一天后会刷新。
- 购物网站:商品的描述信息几乎不会变化,而商品的购买数量需要根据用户情况实时更新。我们可以只选择缓存商品描述信息。
- 缓存网页片段:比如缓存网页导航菜单和脚部(Footer)
像实时监控股票走势、实时显示网站访问量这种需要实时刷新的数据,就不适合用缓存,需要从数据库中立马提取数据。
四、Django 缓存机制
Django 提供多种缓存方式,如:Redis
、Memcached
,不同的缓存介质需要设置不同的缓存后台 backend。
Django settings 中 cache 默认为
`{`` ``'default'``: {`` ``'BACKEND'``: ``'django.core.cache.backends.locmem.LocMemCache'``,`` ``}``}`
也就是默认利用本地的内存来当缓存,速度很快。当然可能出来内存不够用的情况。其他内建可用的 Backend有:
'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'
数据库缓存
需要创建高速缓存表 my_table_name
:
python manage.py createcachetable
CACHES = {
'default': {
'BACKEND': 'django.core.cache.backends.db.DatabaseCache',
'LOCATION': 'my_cache_table',
}
文件系统缓存
CACHES = {
'default': {
'BACKEND': 'django.core.cache.backends.filebased.FileBasedCache',
'LOCATION': '/var/tmp/django_cache', # 文件夹的路径
#'LOCATION': 'E:filedjango_cache', # Windows
}
}
本地内存缓存
CACHES = {
'default': {
'BACKEND': 'django.core.cache.backends.locmem.LocMemCache',
'LOCATION': 'unique-snowflake'
}
}
五、Memcached 缓存
Memcached 是一个自由开源的,高性能,分布式内存对象缓存系统。Django 原生支持的最快最有效的缓存系统。对于大多数场景,我们推荐使用Memcached,数据缓存在服务器端。可以同时支持多个服务器上面的 memcached。
1、安装:
pip3 install python-memcached
pip3 install pylibmc
2、配置 settings
:
普通 TCP 套接字连接(常用方式):
CACHES = {
'default': {
'BACKEND': 'django.core.cache.backends.memcached.MemcachedCache',
'LOCATION': '127.0.0.1:11211',
}
}
CACHES = {
'default': {
'BACKEND': 'django.core.cache.backends.memcached.MemcachedCache',
'LOCATION': [
'172.19.26.240:11211',
'172.19.26.242:11211',
]
# 我们也可以给缓存机器加权重,权重高的承担更多的请求,如下
'LOCATION': [
('172.19.26.240:11211',5),
('172.19.26.242:11211',1),
]
}
}
Unix 域套接字连接
CACHES = {
'default': {
'BACKEND': 'django.core.cache.backends.memcached.MemcachedCache',
'LOCATION': 'unix:/tmp/memcached.sock',
}
}
3、使用
三种方式:视图、路由、模板中使用。
视图:
from django.views.decorators.cache import cache_page
@cache_page(60 * 15) # 过期时间 15 分钟
def index(request):
...
路由:
from django.views.decorators.cache import cache_page
urlpatterns = [
path('index/<int:code>/', cache_page(60 * 15)(index)),
]
模板:
{% load cache %}
{% cache 500 sidebar request.user.username %}
.. sidebar for logged in user ..
{% endcache %}
相关网站:
六、Redis 缓存
使用 redis 缓存也是比较常用的,redis 访问默认不需要密码,但为了安全,我们需要设置好密码:
# redis 默认绑定本机,所以如果是远程访问需要注销
sudo vim /etc/redis/redis.conf
#bind 127.0.0.1 # 注释
# 修改密码
sudo vim /etc/redis/redis.conf
# 找到下面这一行并去除注释(可以搜索requirepass)
requirepass foobared # 未修改之前
requirepass 123456789 # 修改之后
修改后重启服务器使配置生效:
sudo /etc/init.d/redis-server restart
修改 redis 密码后,重新登录 redis,需要输入密码认证。
其他命令:
redis-cli -a password -h hostip # 从另一台linux服务器访问redis
databases 64 # redis 数据库默认 16 个,可在 redis.conf 中修改
在 Django 中使用 Redis 缓存
1、安装 django-redis
模块:
pip3 install django-redis
2、修改 settings
:
CACHES = {
'default': {
'BACKEND': 'django_redis.cache.RedisCache',
'LOCATION': "redis://127.0.0.1:6379/1", # redis ip
"OPTIONS": {
"CLIENT_CLASS": "django_redis.client.DefaultClient",
"PASSWORD": "yoursecret", # redis 密码
},
},
}
REDIS_TIMEOUT=7*24*60*60 # 超时时间,七天,0:立即过期,None:永不超时
CUBES_REDIS_TIMEOUT=60*60
NEVER_REDIS_TIMEOUT=365*24*60*60
URL 格式示例:
redis://[:password]@localhost:6379/0 # 普通的 TCP 套接字连接
rediss://[:password]@localhost:6379/0 # SSL 包裹的 TCP 套接字连接
unix://[:password]@/path/to/socket.sock?db=0 # Unix 域套接字连接
3、测试缓存是否成功:
python manage.py shell
>>> from django.core.cache import cache # 引入缓存模块
>>> cache.set('v', '555', 60*60) # 写入key为v,值为555的缓存,有效期30分钟
>>> cache.has_key('v') # 判断key为v是否存在
>>> cache.get('v') # 获取key为v的缓存
作为 session backend 使用配置
Django 默认可以使用任何 cache backend 作为 session backend, 将 django-redis 作为 session 储存后端不用安装任何额外的 backend
SESSION_ENGINE = "django.contrib.sessions.backends.cache"
SESSION_CACHE_ALIAS = "default"