redis pipline 操作


做开发的同学都知道,一旦设计到底层存储优化,数据结构甚至数据库的变更,通常都会进行数据迁移的工作。如果系统运行时间过长,数据迁移的数量可能非常庞大。这时候,如何进行高效的数据迁移,实际也是上线质量的直接影响因素之一。

下面内容是转载的一个小技巧,无法适用于各种变化的场景,仅供大家参考。

场景是从MySQL中将数据导入到Redis的Hash结构中。当然,最直接的做法就是遍历MySQL数据,一条一条写入到Redis中。这样可能没什么错,但是速度会非常慢。而如果能够使MySQL的查询输出数据直接能够与Redis命令行的输入数据协议相吻合,可能就省事多了。

800w的数据迁移,时间从90分钟缩短到2分钟。

案例如下:
MySQL数据表结构:

Redis存储结构:
HSET events_all_time [action] [count]
下面是重点,能过下面SQL语句将MySQL输出直接变更成redis-cli可接收的格式:

然后用管道符重定向输出即可:

  1.    "hmset","usr"+i,"userid","usr"+i,"username","usrname"+i

格式: HSET events_all_time [15154668565] [d9ceef502ebc7ff98d3cdff3e3d0f51d]

参数个数,长度,命令,长度,命令......

*4
$4
HSET
$15
events_all_time
$11
15154668565
$32
d9ceef502ebc7ff98d3cdff3e3d0f51d
*4
$4
HSET
$15
events_all_time
$11
15154668565
$32
6b19f6970bf1c48221790374b0c000bd
*4
$4
HSET
$15
events_all_time
$11
15154668565
$32
51d2f0e3db7a901d7a42010a6ae53d4f

 

使用redis内部的数据格式然后走pipeline,比遍历mysql一行一行的写redis快多了!

 

使用Python操作Redis:

2 . 简单的redis操作

redis连接实例是线程安全的,可以直接将redis连接实例设置为一个全局变量,直接使用。如果需要另一个Redis实例(or Redis数据库)时,就需要重新创建redis连接实例来获取一个新的连接。同理,python的redis没有实现select命令。

 

 

3. pipeline操作

管道(pipeline)是redis在提供单个请求中缓冲多条服务器命令的基类的子类。它通过减少服务器-客户端之间反复的TCP数据库包,从而大大提高了执行批量命令的功能。

 

 

管道的命令可以写在一起,如:

 

默认的情况下,管道里执行的命令可以保证执行的原子性,执行pipe = r.pipeline(transaction=False)可以禁用这一特性。

总结:redis的pipeline就是这么简单,实际生产环境,根据需要去编写相应的代码。思路同理。线上的redis一般都是集群模式,集群模式下使用pipeline的时候,在创建pipeline的对象时,需要指定

pipe =conn.pipeline(transaction=False)

经过线上实测,利用pipeline取值3500条数据,大约需要900ms,如果配合线程or协程来使用,每秒返回1W数据是没有问题的,基本能满足大部分业务。


转自: http://www.ttlsa.com/database/mysql_data_will_be_migrated_to_redis/

           http://blog.51cto.com/leizhu/1825733

 

posted @ 2018-04-17 16:56  故穿庭树作飞花  阅读(1600)  评论(0编辑  收藏  举报