本系列文章来源:https://blog.ansheng.me/article/python-full-stack-way
安装Redis
安装
模块GitHub地址:https://github.com/WoLpH/redis-py
[root@wangerxiao ~]# yum -y install redis
配置绑定的IP
[root@wangerxiao ~]# vim /etc/redis.conf
bind 0.0.0.0
启动并设置开机自启动
[root@wangerxiao ~]# systemctl start redis
[root@wangerxiao ~]# systemctl enable redis
Created symlink from /etc/systemd/system/multi-user.target.wants/redis.service to /usr/lib/systemd/system/redis.service.
检查
查看端口
[root@wangerxiao ~]# netstat -tlnp | grep 'redis'
tcp 0 0 127.0.0.1:6379 0.0.0.0:* LISTEN 22867/redis-server
数据写入测试
[root@wangerxiao ~]# redis-cli
127.0.0.1:6379> set url https://blog.ansheng.me
OK
127.0.0.1:6379> get url
"https://blog.ansheng.me"
127.0.0.1:6379> exit
redis-py
安装redis-py
[root@wangerxiao ~]# pip install redis
入门及使用
# 导入模块
In [1]: import redis
# 连接到Redis服务器
In [2]: conn = redis.Redis(host='127.0.0.1')
# 写入一条数据
In [3]: conn.set('name','wangerxiao')
Out[3]: True
# 获取一条数据
In [4]: conn.get('name')
Out[4]: b'wangerxiao'
In [5]: conn.get('url')
Out[5]: b'https://blog.ansheng.me'
使用连接池连接到Redis
In [6]: pool = redis.ConnectionPool(host='127.0.0.1')
In [7]: conn = redis.Redis(connection_pool=pool)
In [8]: conn.set('hello','world')
Out[8]: True
In [9]: conn.get('hello')
Out[9]: b'world'
使用套接字连接
>>> r = redis.Redis(unix_socket_path='/tmp/redis.sock')
API
redis-py提供的API用来操作redis
String API
set(name, value, ex=None, px=None, nx=False, xx=False)
参数 描述
ex 过期时间(秒)
px 过期时间(毫秒)
nx 如果设置为True,则只有name不存在时,当前set操作才执行
xx 如果设置为True,则只有name存在时,岗前set操作才执行
In [13]: conn.set('k1','v1',ex=10,nx=True)
Out[13]: True
In [14]: conn.get('k1')
Out[14]: b'v1'
In [15]: conn.get('k1')
setex(name, value, time)
设置过期时间/秒
In [16]: conn.setex('k','v',1)
Out[16]: True
In [17]: conn.get('k')
psetex(name, time_ms, value)
设置过期时间/毫秒
In [20]: conn.psetex('k',10,'v')
Out[20]: True
In [21]: conn.get('k')
setnx(name, value)
设置值,只有key不存在时,执行设置操作
In [22]: conn.get('k1')
In [23]: conn.setnx('k1','v1')
Out[23]: True
In [24]: conn.get('k1')
Out[24]: b'v1'
In [25]: conn.setnx('k1')
---------------------------------------------------------------------------
TypeError Traceback (most recent call last)
in ()
----> 1 conn.setnx('k1')
TypeError: setnx() missing 1 required positional argument: 'value'
In [26]: conn.setnx('k1','v2')
Out[26]: False
mset(*args, **kwargs)
同时设置多个key/keys
>>> conn.mset(k1='v1', k2='v2')
True
>>> conn.mset({'k1':'v1', 'k1':'v1'})
True
get(name)
获取单个值
>>> conn.get('k1')
b'v1'
mget(keys, *args)
获取多个值
>>> conn.mget('k1','k2')
[b'v1', b'v2']
# 传入列表
>>> conn.mget(['name','url'])
[b'ansheng', b'https://blog.ansheng.me']
getset(name, value)
设置新值并获取原来的值
>>> conn.set('hello', 'world')
True
>>> result = conn.getset('hello', 'Linux')
>>> result
b'world'
>>> conn.get('hello')
b'Linux'
getrange(key, start, end)
通过索引的方式来获取value的值
>>> conn.set('key','value')
True
>>> conn.getrange('key', 1, 4)
b'alue'
setrange(name, offset, value)
根据索引修改value
>>> conn.set('n','123456789')
True
>>> conn.setrange('n', 0, 'a')
9
>>> conn.get('n')
b'a23456789'
setbit(name, offset, value)
getbit(name, offset)
获取value对应某一个索引位置对应的值0/1
>>> conn.getbit('k',1)
1
bitcount(key, start=None, end=None)
获取key对应二进制中表示1的个数
bitop(operation, dest, *keys)
将多个值进行值运算,得出的结果保存到一个新值当中
>>> conn.mset(n1='abc',n2='cde',n3='adc')
True
>>> conn.bitop('AND','now_key','n1','n2','n3')
3
>>> conn.get('now_key')
b'a`a'
>>> conn.mget('n1','n2','n3')
[b'abc', b'cde', b'adc']
operation支持AND(并)、OR(或)、NOT(非)、XOR(异或)
strlen(name)
获取value的长度
>>> conn.set('name','wangerxiao')
True
>>> conn.strlen('name')
10
incr(name, amount=1)
对name的value进行自增,如果name不存在则创建,否则自增
>>> conn.get('number')
>>> conn.incr('number')
1
>>> conn.get('number')
b'1'
>>> conn.incr('number')
2
>>> conn.incr('number', 10)
12
incrbyfloat(name, amount=1.0)
同上,支持浮点数自增
>>> conn.incrbyfloat('number', 1.5)
13.5
>>> conn.incrbyfloat('number', 1.1)
14.6
decr(name, amount=1)
自减,同自增一样,如果进行自减的value不是整数就报错
>>> conn.set('n', 10)
True
>>> conn.decr('n')
9
>>> conn.decr('n', 9)
0
append(key, value)
在value后面追加内容
>>> conn.set('blog','https://blog.ansheng.me')
True
>>> conn.append('blog','/')
26
>>> conn.get('blog')
b'https://blog.ansheng.me/'
Hash API
hset(name, key, value)
设置name的键值对,有则修改,没有则创建
>>> conn.hset('dic','k1','v1')
1
>>> conn.hget('dic','k1')
b'v1'
hmset(name, mapping)
同时设置多个name的key/value
>>> conn.hmset('dic', {'k1': 'v1', 'k2': 'v2'})
True
>>> conn.hget('dic','k2')
b'v2'
hget(name, key)
获取name中key的值
>>> conn.hget('dic','k2')
b'v2'
hmget(name, keys, *args)
同时获取多个
>>> conn.hmget('dic',['k1', 'k2'])
[b'v1', b'v2']
>>> conn.hmget('dic','k1', 'k2')
[b'v1', b'v2']
hgetall(name)
获取name对应的所有key/value
>>> conn.hgetall('dic')
{b'k1': b'v1', b'k2': b'v2'}
hlen(name)
获取name对应键值对的个数
>>> conn.hlen('dic')
2
hkeys(name)
获取name中所有的key
>>> conn.hkeys('dic')
[b'k1', b'k2']
hvals(name)
获取name中所有的value
>>> conn.hvals('dic')
[b'v1', b'v2']
hexists(name, key)
检查当前name中是否有传入的key
>>> conn.hexists('dic','k1')
True
>>> conn.hexists('dic','kk')
False
hdel(self, name, *keys)
删除name中对应的key
>>> conn.hdel('dic','k1')
1
>>> conn.hget('dic','k1')
hincrby(name, key, amount=1)
name中key对应的value进行自增,如果不存在则创建
>>> conn.hincrby('dic','number')
1
>>> conn.hincrby('dic','number',10)
11
hincrbyfloat(name, key, amount=1.0)
value自增,支持浮点数,同上
>>> conn.hincrbyfloat('dic','float')
1.0
>>> conn.hincrbyfloat('dic','float',0.3)
1.3
hscan(name, cursor=0, match=None, count=None)
增量式迭代获取,hscan可以实现分片的获取数据,并非一次性将数据全部获取完,从而防止内存被撑爆
参数 描述
name redis的name
cursor 游标(基于游标分批取获取数据)
match 匹配指定key,默认None 表示所有的key
count 每次分片最少获取个数,默认None表示采用Redis的默认分片个数
hscan_iter(name, match=None, count=None)
利用yield封装hscan创建生成器,实现分批去redis中获取数据
参数 描述
match 匹配指定key,默认None 表示所有的key
count 每次分片最少获取个数,默认None表示采用Redis的默认分片个数
如:
for item in r.hscan_iter('xx'):
print item
expire(name, time)
设置过期时间
>>> conn.hset('info','BlogUrl','https://blog.ansheng.me')
1
>>> conn.expire('info', 10)
True
>>> conn.hget('info','BlogUrl')
b'https://blog.ansheng.me'
>>> conn.hget('info','BlogUrl')
ListAPI
lpush(name, *values)
在最左边添加值
>>> conn.lpush('li', 11,22,33)
3
>>> conn.lindex('li', 0)
b'33'
rpush(name, *values)
在最右边添加值
>>> conn.rpush('lli', 11,22,33)
3
>>> conn.lindex('lli', 0)
b'11'
lpushx(name, value)
只有name已经存在时,值添加到列表的最左边
>>> conn.lpushx('li', 'aa')
4
>>> conn.lindex('li', 0)
b'aa'
rpushx(name, value)
只有name已经存在时,值添加到列表的最右边
>>> conn.rpushx('li', 'bb')
5
>>> conn.lindex('li', 0)
b'aa'
>>> conn.lindex('li', 4)
b'bb'
llen(name)
获取name元素的个数
>>> conn.llen('li')
5
linsert(name, where, refvalue, value)
在name的某一个值前面或者后面插入一个新值
>>> conn.linsert('li','AFTER','11','cc')
6
>>> conn.lindex('li', 3)
b'11'
>>> conn.lindex('li', 4)
b'cc'
lset(name, index, value)
对name中index索引位置的值进行重新赋值
>>> conn.lindex('li', 4)
b'cc'
>>> conn.lset('li', 4, 'hello')
True
>>> conn.lindex('li', 4)
b'hello'
lrem(name, value, num=0)
删除指定value后面或者前面的值
num=2,从前到后,删除2个;
num=-2,从后向前,删除2个
>>> conn.llen('li')
6
>>> conn.lrem('li', 'hello')
1
>>> conn.llen('li')
5
>>> conn.lrem('li', '22', num=2)
2
>>> conn.llen('li')
3
lpop(name)
删除name中左侧第一个元素
>>> conn.lindex('li', 0)
b'11'
>>> conn.lpop('li')
b'11'
rpop(name)
删除name中右侧第一个元素
>>> conn.rpop('li')
b'33'
lindex(name, index)
获取name中对应索引的值
>>> conn.lindex('li', 0)
b'aa'
lrange(name, start, end)
使用切片获取数据
>>> conn.llen('li')
8
>>> conn.lrange('li',0,5)
[b'3', b'23', b'34', b'235', b'2', b'1']
ltrim(name, start, end)
在name对应的列表中移除没有在start-end索引之间的值
>>> conn.ltrim('li',0,5)
True
>>> conn.llen('li')
6
rpoplpush(src, dst)
从src列表中取出最右边的元素,同时将其添加至dst列表的最左边
>>> conn.lpush('li1', 1,2,3)
3
>>> conn.lpush('li2', 'a','b','c')
3
>>> conn.rpoplpush('li1','li2')
b'1'
blpop(keys, timeout=0) brpop(keys, timeout=0)
brpoplpush(src, dst, timeout=0)
从src列表的右侧移除一个元素并将其添加到dst列表的左侧
>>> conn.lpush('ll', 'a','b','c')
3
>>> conn.lpush('aa', 'a','b','c')
3
>>> conn.brpoplpush('ll','aa')
b'a'
timeout,当src对应的列表中没有数据时,阻塞等待其有数据的超时时间(秒),0 表示永远阻塞
自定义增量迭代
由于redis类库中没有提供对列表元素的增量迭代,如果想要循环name对应的列表的所有元素,那么就需要:
1.获取name对应的所有列表
2.循环列表
但是,如果列表非常大,那么就有可能在第一步时就将程序的内容撑爆,所有有必要自定义一个增量迭代的功能:
def list_iter(name):
"""
自定义redis列表增量迭代
:param name: redis中的name,即:迭代name对应的列表
:return: yield 返回 列表元素
"""
list_count = r.llen(name)
for index in xrange(list_count):
yield r.lindex(name, index)
使用
for item in list_iter('pp'):
print item
SET API
sadd(name, *values)
为name添加值,如果存在则不添加
>>> conn.sadd('s1', 1)
1
>>> conn.sadd('s1', 1)
0
scard(name)
返回name的元素数量
>>> conn.scard('s1')
1
sdiff(keys, *args)
在keys集合中不在其他集合中的数据
>>> conn.sdiff('s1','s2')
{b'c', b'v', b'a'}
sdiffstore(dest, keys, *args)
在keys集合中不在其他集合中的数据保存到dest集合中
>>> conn.sdiffstore('news','s1','s2')
3
>>> conn.scard('news')
3
sinter(keys, *args)
获取keys集合中与其他集合中的并集
>>> conn.sinter('s1','s2')
{b'2', b'3', b'1'}
sinterstore(dest, keys, *args)
获取keys集合中与其他集合中的并集数据并保存到dest集合中
>>> conn.sinterstore('news1','s1','s2')
3
sismember(name, value)
获取value是否是name集合中的成员
>>> conn.sismember('news1','1')
True
>>> conn.sismember('news1','aa1')
False
smembers(name)
获取name集合中所有的成员
>>> conn.smembers('news1')
{b'2', b'3', b'1'}
smove(src, dst, value)
将src中的value移动到dst中
>>> conn.smembers('s1')
{b'c', b'2', b'v', b'1', b'3', b'a'}
>>> conn.smembers('s2')
{b'2', b'3', b'1'}
>>> conn.smove('s1','s2','v')
True
>>> conn.smembers('s1')
{b'c', b'2', b'a', b'3', b'1'}
>>> conn.smembers('s2')
{b'2', b'v', b'3', b'1'}
spop(name)
删除并返回name中的随机成员
>>> conn.smembers('s2')
{b'2', b'v', b'3', b'1'}
>>> conn.spop('s2')
b'3'
>>> conn.smembers('s2')
{b'2', b'v', b'1'}
>>> conn.spop('s2')
b'2'
>>> conn.smembers('s2')
{b'v', b'1'}
>>> conn.spop('s2')
b'1'
>>> conn.smembers('s2')
{b'v'}
srandmember(name, number=None)
随机获取name集合中的number个成员,默认number=1
>>> conn.smembers('s1')
{b'c', b'2', b'a', b'3', b'1'}
>>> conn.srandmember('s1')
b'1'
>>> conn.srandmember('s1')
b'a'
>>> conn.srandmember('s1',number=2)
[b'3', b'a']
>>> conn.srandmember('s1',number=2)
[b'1', b'2']
srem(name, *values)
删除name集合中的values数据
>>> conn.smembers('s1')
{b'c', b'2', b'a', b'3', b'1'}
>>> conn.srem('s1','1','2')
2
>>> conn.smembers('s1')
{b'c', b'a', b'3'}
sunion(keys, *args)
获取keys集合与其他集合的并集
>>> conn.sadd('a1',1,2,3)
3
>>> conn.sadd('a2',1,2,3,4,5,6,7)
7
>>> conn.sunion('a2','a1')
{b'2', b'7', b'1', b'3', b'6', b'5', b'4'}
sunionstore(dest, keys, *args)
获取keys集合与其他集合的并集并保存到dest中
>>> conn.sunionstore('a3', 'a2','a1')
7
>>> conn.smembers('a3')
{b'2', b'7', b'1', b'3', b'6', b'5', b'4'}
Ordered set API
zadd(name, *args, **kwargs)
>>> conn.zadd('h1','n1',11,'n2',22)
2
>>> conn.zadd('h2',n1=11,n2=22)
2
zcard(name)
返回有序集合name元素的数量
>>> conn.zcard('h1')
2
zcount(name, min, max)
返回在name中值在min与max之间的值个数
>>> conn.zcount('h1',10,30)
2
zincrby(name, value, amount=1)
name中让value的值加上amount
>>> conn.zincrby('h1','n1',10)
21.0
zinterstore(dest, keys, aggregate=None) zlexcount(name, min, max)
zrange(name, start, end, desc=False, withscores=False, score_cast_func=float)
参数 描述
name redis的name
start 有序集合索引起始位置(非分数)
end 有序集合索引结束位置(非分数)
desc 排序规则,默认按照分数从小到大排序
withscores 是否获取元素的分数,默认只获取元素的值
score_cast_func 对分数进行数据转换的函数
>>> conn.zrange('h1', 1, 2, desc=True, withscores=True, score_cast_func=float)
[(b'n1', 21.0)]
>>> conn.zrange('h1', 1, 2, desc=False, withscores=True, score_cast_func=float)
[(b'n2', 22.0)]
# 从大到小排序
zrevrange(name, start, end, withscores=False, score_cast_func=float)
# 按照分数范围获取name对应的有序集合的元素
zrangebyscore(name, min, max, start=None, num=None, withscores=False, score_cast_func=float)
# 从大到小排序
zrevrangebyscore(name, max, min, start=None, num=None, withscores=False, score_cast_func=float)
zrangebylex(name, min, max, start=None, num=None)
当有序集合的所有成员都具有相同的分值时,有序集合的元素会根据成员的 值 (lexicographical ordering)来进行排序,而这个命令则可以返回给定的有序集合键 key 中, 元素的值介于 min 和 max 之间的成员
对集合中的每个成员进行逐个字节的对比(byte-by-byte compare), 并按照从低到高的顺序, 返回排序后的集合成员。 如果两个字符串有一部分内容是相同的话, 那么命令会认为较长的字符串比较短的字符串要大
参数 描述
name redis的name
min 左区间(值) + 表示正无限; - 表示负无限; ( 表示开区间; [ 则表示闭区间
min 右区间(值)
start 对结果进行分片处理,索引位置
num 对结果进行分片处理,索引后面的num个元素
如:
ZADD myzset 0 aa 0 ba 0 ca 0 da 0 ea 0 fa 0 ga
# r.zrangebylex('myzset', "-", "[ca") 结果为:['aa', 'ba', 'ca']
更多:
# 从大到小排序
zrevrangebylex(name, max, min, start=None, num=None)
zrevrangebylex(name, max, min, start=None, num=None)
zrangebyscore(name, min, max, start=None, num=None, withscores=False, score_cast_func=float)**
zrank(name, value)
返回基于0的值,指示在排序集名称的值排名
>>> conn.zrank('h1','n1')
0
>>> conn.zrank('h1','n2')
1
zrevrank(name, value),从大到小排序
zrem(name, *values)
删除name中对应的values
>>> conn.zrem('h1','n2')
1
>>> conn.zrem('h2',['n1','n2'])
2
zremrangebyrank(name, min, max)
根据排行范围进行删除
>>> conn.zremrangebyrank('h1',1,2)
1
zremrangebyscore(name, min, max)
根据分数范围进行删除
>>> conn.zremrangebyscore('h1',10,20)
2
zscore(name, value)
返回指定value的值是多少
>>> conn.zscore('h1','n1')
11.0
zunionstore(dest, keys, aggregate=None)
Global API(全局)
在redis中删除names
>>> conn.delete('ooo')
1
exists(name)
检测name是否存在
>>> conn.exists('iii')
False
>>> conn.exists('h1')
True
keys(pattern=’*’)
# 匹配数据库中所有 key
>>> conn.keys(pattern='*')
# 匹配hello,hallo和hxllo等
conn.keys(pattern='h?llo')
# 匹配hllo和heeeeello 等
conn.keys(pattern='h*llo')
# 匹配hello和hallo,但不匹配 hillo
conn.keys(pattern='h[ae]llo')
rename(src, dst)
把src重命名成dst
>>> conn.set('k','v')
True
>>> conn.get('k')
b'v'
>>> conn.rename('k', 'kk')
True
>>> conn.get('k')
>>> conn.get('kk')
b'v'
move(name, db)
将redis的某个值移动到指定的db下
randomkey()
随机获取一个redis的name,不进行删除
>>> conn.randomkey()
b'll'
>>> conn.randomkey()
b'news1'
type(name)
查看name的类型
>>> conn.type('kk')
b'string'
管道
redis-py默认在执行每次请求都会创建(连接池申请连接)和断开(归还连接池)一次连接操作,如果想要在一次请求中指定多个命令,则可以使用pipline实现一次请求指定多个命令,并且默认情况下一次pipline 是原子性操作(MySQL中的事务)。
>>> import redis
>>> pool = redis.ConnectionPool(host='127.0.0.1', port=6379)
>>> r = redis.Redis(connection_pool=pool)
# 创建一个通道支持事务
>>> pipe = r.pipeline(transaction=True)
#
>>> r.set('hello', 'world')
True
>>> r.set('blog', 'ansheng.me')
True
# 如果在设置上面两个值的过程中出错了,那么这次提交就不会执行
>>> pipe.execute()
[]
发布订阅
# monitor.py
#!/usr/bin/env python
# -*- coding:utf-8 -*-
import redis
class RedisHelper:
def __init__(self):
self.__conn = redis.Redis(host='192.168.56.100')
self.chan_sub = 'fm104.5'
self.chan_pub = 'fm104.5'
def public(self, msg):
self.__conn.publish(self.chan_pub, msg)
return True
def subscribe(self):
pub = self.__conn.pubsub()
pub.subscribe(self.chan_sub)
pub.parse_response()
return pub
# subscriber.py 订阅者
#!/usr/bin/env python
# -*- coding:utf-8 -*-
from monitor import RedisHelper
obj = RedisHelper()
redis_sub = obj.subscribe()
while True:
msg = redis_sub.parse_response()
print(msg)
# announcer.py 发布者
#!/usr/bin/env python
# -*- coding:utf-8 -*-
from monitor import RedisHelper
obj = RedisHelper()
obj.public('hello')
实例
让redis缓存tornado页面
# _*_coding:utf-8 _*_
import tornado.ioloop
import tornado.web
import time
import redis
poll = redis.ConnectionPool(host='192.168.56.100', port=6379)
conn = redis.Redis(connection_pool=poll)
class MainHandler(tornado.web.RequestHandler):
def get(self):
CurrentTim = conn.get('CurrentTim')
if CurrentTim:
self.write(CurrentTim)
else:
CurrentTim = time.strftime('%Y-%m-%d %H:%M:%S', time.localtime(time.time()))
conn.set('CurrentTim', CurrentTim, ex=5)
self.write(CurrentTim)
settings = {
"tempalte_path": "template",
}
application = tornado.web.Application([
(r'/', MainHandler),
], **settings)
if __name__ == "__main__":
application.listen(9999)
tornado.ioloop.IOLoop.instance().start()
基于Redis的Session存储
app.py
# _*_coding:utf-8 _*_
import tornado.ioloop
import tornado.web
import RedisToSession
class BaseHandler(tornado.web.RequestHandler):
def initialize(self):
self.session = RedisToSession.Session(self)
class MainHandler(BaseHandler):
def get(self):
Info = self.session.GetAll()
self.render("template/index.html", Data=Info)
def post(self, *args, **kwargs):
# 获取传过来的值
Key = self.get_argument('key')
Val = self.get_argument('val')
action = self.get_argument('action')
if action == 'set':
# 设置值
self.session[Key] = Val
elif action == 'del':
del self.session[Key]
# 获取所有信息
Info = self.session.GetAll()
# 返回给前端渲染
self.render("template/index.html", Data=Info)
settings = {
"tempalte_path": "template",
"cookie_secret": "508CE6152CB93994628D3E99934B83CC",
}
application = tornado.web.Application([
(r'/', MainHandler),
], **settings)
if __name__ == "__main__":
application.listen(9999)
tornado.ioloop.IOLoop.instance().start()
template\index.html
RedisToSession.py
# _*_ coding: utf-8 _*_
import redis
import hashlib
import uuid
import json
# 连接memcached
pool = redis.ConnectionPool(host='192.168.56.100', port=6379)
conn = redis.Redis(connection_pool=pool)
class Session:
CookieID = 'uc'
ExpiresTime = 60 * 20
def __init__(self, handler):
"""
用于创建用户session在redis中的字典
:param handler: 请求头
"""
self.handler = handler
# 从客户端获取随机字符串
SessionID = self.handler.get_secure_cookie(Session.CookieID, None)
# 客户端存在并且在服务端也存在
if SessionID and conn.exists(SessionID):
self.SessionID = SessionID
else:
# 获取随机字符串
self.SessionID = self.SessionKey()
# 把随机字符串写入memcached,时间是20分钟
conn.hset(self.SessionID, None, None)
# 每次访问超时时间就加20分钟
conn.expire(self.SessionID, Session.ExpiresTime)
# 设置Cookie
self.handler.set_secure_cookie('uc', self.SessionID)
def SessionKey(self):
"""
:return: 生成随机字符串
"""
UUID = str(uuid.uuid1()).replace('-', '')
MD5 = hashlib.md5()
MD5.update(bytes(UUID, encoding='utf-8'))
SessionKey = MD5.hexdigest()
return SessionKey
def __setitem__(self, key, value):
"""
:param key: session信息中的key
:param value: 对应的Value
"""
conn.hset(self.SessionID, key, value)
def __getitem__(self, item):
"""
:param item: Session信息中对应的Key
:return: 获取的Session信息
"""
# 获取对应的数据
ResultData = conn.hget(self.SessionID, item)
return ResultData
def __delitem__(self, key):
"""
:param key: 要删除的Key
"""
conn.hdel(self.SessionID, key)
def GetAll(self):
# 获取Session中所有的信息,仅用于测试
SessionData = conn.hgetall(self.SessionID)
return SessionData