|
一.Redis key相关操作:
1.del key [key..]
删除一个或多个key,如果不存在则忽略
2.keys pattern
keys模式匹配,符合glob风格通配符,glob风格的通配符规则:
? 匹配一个字符
[]匹配任一个字符,可以使用-表示一个范围
\x 匹配x,用于转义字符
如:keys * 查看所有key, keys *o* 查看包含o字符的key
KYES命令需要遍历redis中所有键,当键数量较多时会影响性能,因此不建议在生产中使用
3.exists key
检查key是否存在该DB中,存在返回1否则0
4.rename key newkey
rename更名,如果key与newkey相同或者key不存在则发生错误
5.type key
检查key类型,返回值有:none(不存在), string(字符串), list(数组), set(集合), zset(有序集合), hash(哈希)
其他
1.randomkey 数据库中随机返回一个key,若数据库为空则返回nil
2.TTL key 返回给定key的剩余生存时间(time to live),秒为单位,如果没有设置则返回-1
3.expire key seconds 设置key过期时间.
4.PERSIST key 移除给定key的过期时间
5.move key db 将key 移动到另一个数据库中,如果另一个db存在该同名key或者原db没有对应的key则move无任何效果.
二.Redis key 设计
Redis键值设计并没有一致性要求,对于复杂的key,一般使用冒号做分割符.较好的实践是:对象类型:对象ID:对象属性, 如:user:1:sex 处理成set user:1:sex 男 表示表user中id为1的用户性别设置男性.
对于多个单词推荐使用.分割.
对于上述key 的设计,在编程语言中如Python也很好处理:
>>> s = "user:1:sex"
>>> s.split(':')[2:]
['sex']
三.User表设计实现
一般一张User表包含以下字段:> 对于user表Redis Key的设计,我们有两种方案:
(1).user:1:username的形式
(2).user:1 username value hash类型的设计
能够使用hash尽量使用,它比String的效率会高很多!
这里选择hash类型在命令行下设置如下:
127.0.0.1:6379> hmset user:1 username BeginMan pwd root sex 1 is_active 1 is_admin 1 avatar http://beginman.sinaapp.com/site_media/img/my.jpg login_count 0
OK
127.0.0.1:6379> hgetall user:1
1) "username"
2) "BeginMan"
3)"pwd"
4)"root"
5) "sex"
6) "1"
7) "is_active"
8) "1"
9) "is_admin"
10) "1"
11) "avatar"
12) "http://beginman.sinaapp.com/site_media/img/my.jpg"
13) "login_count"
14) "0"
这里先设置了一个管理员用户,那么在django中相当于执行manage.py createsuperuser. 这里还有个字段last_login_date没有写入,KV(key-value)数据库不像关系型数据库那样必须保持一致性,在后期只要用户登陆过那么就设置该字段,同时login_count累加.
然后再定义一个表用来记录用户名对应的ID,如下:
127.0.0.1:6379> set "us:BeginMan:id" 1
OK
Django完成该登陆的流程:
(1).检查该用户是否存在Redis中
(2).匹配Redis,us,pwd,若匹配成功则跳转成功页面
登陆表单类:
class LoginForm(forms.Form): us = forms.CharField(label=u'用户名',max_length=100,widget=forms.TextInput(
attrs={'class': 'form-control', 'placeholder': u'用户名', 'required': '', 'autofocus': ''}
),
)
pwd = forms.CharField(label=u'密码',widget=forms.PasswordInput(
attrs={'class': 'form-control', 'placeholder': u'密码', 'required': ''}
)
)
view方法:
# coding=utf-8
__author__ = 'beginman'
from django.shortcuts import render
from django.http import HttpResponseRedirect
from form import LoginForm
import redis
import datetime
r = redis.StrictRedis(host='localhost', port='6379', db=0)
def home(request):
return render(request, 'index.html')
def usLogin(request):
context = {}
if request.method == 'POST':
form = LoginForm(request.POST)
if form.is_valid():
us = form.cleaned_data['us']
pwd = form.cleaned_data['pwd']
if r.exists('us:%s:id' %us): # 检查是否存在该用户关系键值
uid = r.get('us:%s:id' %us) # 获取该用户在user表中对应的id
if r.exists('user:%s' %uid): # 检查是否存在该用户键值(如user:1)
us_, pwd_ = r.hmget('user:%s' %uid, 'username', 'pwd') # 获取该用户的用户名密码
if us_ == us and pwd_ == pwd: # 校验成功
r.hincrby('user:%s' %uid, 'login_count', 1) # 登陆次数累加
r.hset('user:%s' %uid, 'last_login_date', datetime.datetime.now()) # 添加最近登陆
return HttpResponseRedirect('/')
context['msg'] = u'账号或密码错误'
context['form'] = form
form = LoginForm()
context['form'] = form
return render(request, 'login.html', context)
登陆后我们在Redis中看看该记录:
127.0.0.1:6379> hgetall user:1 1) "username"
2) "BeginMan"
3) "sex"
4) "1"
5) "is_active"
6) "1"
7) "is_admin"
8) "1"
9) "avatar"
10) "http://beginman.sinaapp.com/site_media/img/my.jpg"
11) "login_count"
12) "1" # 登陆次数+1
13) "pwd"
14) "root"
15) "last_login_date" # 添加了登陆时间
16) "2014-08-01 10:26:47.711227"
Redis&Django实现blog平台该项目已经放置在github.
四.参考资料
1.Redis 键 |
|