redis事务与关系型数据库事务比较

redis 是一个高性能的key-value 数据库。作为no sql 数据库redis 与传统关系型数据库相比有简单灵活、数据结构丰富、高速读写等优点。

本文主要针对redis 在事务方面的处理与传统关系型数据库(使用mysql)进行比对,所使用的环境为ubuntu 14.04.1,mysql 5.5.49,redis 3.2.3。

1、操作事务命令

mysql 使用start transaction 开启事务,rollback 回滚事务,commit 提交事务。redis 使用multi 开始事务,discard 取消事务,exec 提交事务。开始实验前为mysql 和redis 准备测试数据,tom1 账户准备1000元,tom2 账户准备500元。

(图1-数据准备)


场景1:使用事务从tom1转100元到tom2 。

步骤如下:


(图2-mysql 事务执行过程)
(图3-redis 事务执行过程)

从场景1中可以看出mysql 开启事务后事务中的sql 语句在commit 之前就已经执行了sql 语句的,只是并未真正提交到数据库。redis 使用multi 开启事务后,编写的sql 语句都进入queue 队列中,待执行exec 提交事务时才一次性按进入queue 队列的顺序提交到数据库。同样针对回滚,mysql 执行rollback 会将提交的数据回滚,redis 因为没有提交到数据,使用discard 只是单纯取消在queue 中的sql 语句。

场景2: 在执行tom1 向tom2 转过程中100元的过程中使用了语法错误的sql。


(图4-mysql 事务中存在语法错误语句)
(图5-redis 事务中存在语法错误语句)

从场景2中可以看出,mysql 事务即使遇到错误的语句也会提交正确的sql 到数据库,需要程序员控制当遇到语句异常时进行回滚,redis 与mysql 不同,提交事务时当queue 中有语法错误语句会discard 整个事务中的sql 语句。

场景3: 在执行tom1 向tom2 转过程中100元的过程中使用了错误的执行对象。

步骤如下:


(图6-mysql 中存在操作错误对象的sql 语句)
(图7-redis 中存在操作错误对象的sql语句)

从场景3中可以看出,mysql 和redis 事务当遇到操作对象类型不正确的时候都会提交执行事务。

2、事务锁

在关系型数据库中主要通过乐观锁和悲观锁进行数据库事务的并发控制。而在redis 中是通过watch 加乐观锁对数据库进行并发控制。

mysql 悲观锁是通过select * from table where for update将数据加锁,导致其他线程或事务不能更新该数据。相对于悲观锁,在对数据库进行处理的时候,乐观锁并不会使用数据库提供的锁机制。一般的实现乐观锁的方式就是记录数据版本。数据版本为数据增加的一个版本标识。当读取数据时,将版本标识的值一同读出,数据每更新一次,同时对版本标识进行更新。当我们提交更新的时候,判断数据库表对应记录的当前版本信息与第一次取出来的版本标识进行比对,如果数据库表当前版本号与第一次取出来的版本标识值相等,则予以更新,否则认为是过期数据。

关系型数据库mysql 实现数据版本主要有两种方式,第一种是使用版本号,第二种是使用时间戳。使用版本号时,可以在数据初始化时指定一个版本号,每次对数据的更新操作都对版本号执行+1操作。并判断当前版本号是不是该数据的最新的版本号。

(图8-mysql乐观锁)

图8展示了mysql 乐观锁的示例,开启两个mysql 客户端,客户端1执行start transaction 查询数据,这时客户端2更新了客户端1查询到的数据及version 字段,然后客户端1在第3步试图更新在第一步中查询到的数据时因version 已改变因此更新失败。

(图9-redis 乐观锁(watch))

redis 是通过watch 命令监控数据是否发生变化实现乐观锁的。如图9所示打开两个redis 客户端,客户端1对数据tom2 进行watch,打开事务更改tom1,tom2,客户端2更改客户端1中watch 的对象,步骤3客户端1提交事务由于watch 的对象被更改了,导致事务放弃执行。

3、事务的ACID 性质

下面讨论下事务的ACID 性质。传统关系型数据库事务具备ACID 性质,这里不做详细讨论。

针对Redis 事务具有原子性(Atomicity),一致性(Consistency),和隔离性(Isolation),当redis 在持久化模式运行时,也具备持久性(Durability)。在场景1~3和乐观锁示例中redis 全部执行事务队列中的sql 语句即使其中sql存在操作对象错误,要么全部discard放弃执行,因此redis 事务具有原子性(Atomicity)。

redis 事务在执行过程中发生错误或进程被终结,都能保证数据的一致性(Consistency)。因为redis 使用单线程串行方式来执行事务的,在执行事务期间不会对事务进行中断(一致性),因此redis 事务也具有隔离性(Isolation)。redis 可以只将运行结果保存在内存中,但当redis 服务器使用AOF 持久化模式并appendfsync 设置为always 时,程序执行sql 后会调用sync 函数将数据保存到硬盘里,因此redis 事务也可以具有持久性(Durability)。

通过下表对redis 事务和关系型数据库事务做一个简单的总结。

参考文档:

http://redis.io/topics/transactions

《redis设计与实现》黄健宏


本文作者:Tom(点融黑帮),现任点融Fin-Tech高级研发工程师,曾任职于IBM。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,547评论 6 477
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,399评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,428评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,599评论 1 274
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,612评论 5 365
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,577评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,941评论 3 395
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,603评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,852评论 1 297
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,605评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,693评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,375评论 4 318
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,955评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,936评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,172评论 1 259
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 43,970评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,414评论 2 342

推荐阅读更多精彩内容