Django小项目
需求
整体架构图
技术细节
环境配置
-
django-admin startprojrct rmysite1 # 创建项目
-
cd rmysite1 # 进入项目目录
-
python manage.py startapp user # 创建应用
-
mysql 创建数据库 rmysite1 # Navivate 创建数据库 rmysite1
-
Navivate 创建数据库 rmysite1
-
conda 安装 redis包
各文件配置
settings.py
INSTALLED_APPS = [
...
'user', # 加入应用
]
# 。。。。
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.mysql',
'NAME': 'rmysite1',
'USER':'root',
'PASSWORD':'自己密码',
'HOST':'127.0.0.1',
'PORT':'3306',
}
}
TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [os.path.join(BASE_DIR,'templates')], # 在项目目录创建
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
],
},
},
]
LANGUAGE_CODE = 'zh-Hans'
TIME_ZONE = 'Asia/Shanghai'
urls.py
多级路由
from django.urls import path
from . import views
urlpatterns = [
# path('user/',include('user.urls')),
path('detail/<int:user_id>',views.user_detail),
path('update',views.user_update),
]
views.py
from django.http import HttpResponse
from django.shortcuts import render
from .models import User
import redis
# 全局变量
r = redis.Redis(host='127.0.0.1',port=6379,db=0,password='123456')
# Create your views here.
def user_detail(request,user_id):
# user/detail/1
cacahe_key = 'user:%s'%(user_id)
# 优先查看缓存
if r.exists(cacahe_key):
data = r.hgetall(cacahe_key)
# {b'username':b'xxx',b'desc':b'xxx'} 字节形式
# 转换为字符串形式
new_data= {k.decode():v.decode() for k,v in data.items()}
username = new_data['username']
desc = new_data['desc']
html = 'cache username is %s ; desc is %s'%(username,desc)
return HttpResponse(html)
# 没有缓存数据
try:
user = User.objects.get(id=user_id)
except Exception as e:
print('-- get user error is %s'%(e))
return HttpResponse('-----no user!!!------')
username = user.username
desc = user.desc
# 更新缓存 存储到缓存
r.hmset(cacahe_key,{'username':username,'desc':desc})
r.expire(cacahe_key,60) # 哈希只能整体加过期时间
html = 'mysql username is %s ; desc is %s'%(username,desc)
return HttpResponse(html)
def user_update(request):
if request.method == 'GET':
return render(request,'user_update.html')
elif request.method == 'POST':
username = request.POST['username']
desc = request.POST['desc']
try:
user = User.objects.get(username=username)
except Exception as e:
print('-- update user error is %s' % (e))
return HttpResponse('-----no user!!!------')
# user.username = username
user.desc = desc # 只更改desc
user.save()
# 删除旧缓存
cache_key = 'user:%s' %(user.id)
r.delete(cache_key)
return HttpResponse('-----update successfully!!!------')
user_update.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>更新</title>
</head>
<body>
<form action="/user/update" class="action" method="post">
{% csrf_token %} <!--- CSRF验证机制 ---->
<p>
用户名:<input type="text" name="username">
</p>
<p>
个人描述:<input type="text" name="desc">
</p>
<p>
<input type="submit" value="更新">
</p>
</form>
</body>
</html>
结果
- 第一次运行结果
- 第二次运行
修改个人信息 返回 并从新访问
更新后 立即删除旧缓存数据
更新后的第一次访问:redis缓存没有该信息 mysql数据库查找 并将数据存入redis缓存
更新后的第二次访问 redis缓存数据中存在 直接访问
相关代码补充
r.hgetall(cacahe_key)
在 Redis 中,HGETALL 命令用于获取哈希表中指定键的所有字段和值。
HGETALL 返回一个列表,其中每个字段的值按字段名和值交替排列。例如,如果哈希表包含字段 field1 和 field2,其值分别为 value1 和 value2,则 HGETALL 将返回 [b'field1', b'value1', b'field2', b'value2']
(在某些客户端库中返回的可能是字节字符串)
new_data= {k.decode():v.decode() for k,v in data.items()}
data.items():获取 data 字典的键值对项,返回一个迭代器,每个项是一个元组 (key, value)。
在字典推导式 {k.decode():v.decode() for k,v in data.items()} 中,对于 data.items() 返回的每个键值对 k 和 v:
k.decode():将键 k 从字节字符串解码为普通字符串。如果 k 已经是普通字符串,这个调用将引发 AttributeError。
v.decode():将值 v 从字节字符串解码为普通字符串。如果 v 已经是普通字符串,这个调用同样会引发错误。
{k.decode():v.decode() for k,v in data.items()}:创建一个新字典 new_data,其键和值都是解码后的字符串。
new_data:是解码后的新字典,可以用于需要普通字符串键和值的场合。
data = {
b'key1': b'value1',
b'key2': b'value2'
}
# 使用字典推导式解码所有键和值
new_data = {k.decode(): v.decode() for k, v in data.items()}
print(new_data) # 输出: {'key1': 'value1', 'key2': 'value2'}