Redis入门指南 第3版

978-7-115-56989-9
作者: 李子骅
译者:
编辑: 刘雅思
分类: Redis

图书目录:

详情

本书是一本Redis的入门指导图书,以通俗易懂的方式介绍了Redis基础与实践方面的知识,包括历史与特性,在开发环境和生产环境中部署运行Redis,数据类型与命令,使用Redis实现事务、排序、消息通知、管道、Redis存储空间的优化,持久化等内容,并采用“任务驱动”的方式介绍了PHP、Ruby、Python和Node.js这4种编程语言的Redis客户端库的使用方法。   本书的目标读者不仅包括Redis新手,还包括已经掌握Redis使用方法的读者。对新手而言,本书的内容由浅入深且紧贴实践,让读者能够即学即用;对于已经了解Redis的读者,通过本书的大量实例以及细节介绍,也能发现很多新的技巧。

图书摘要

版权信息

书名:Redis入门指南(第3版)

ISBN:978-7-115-56989-9

本书由人民邮电出版社发行数字版。版权所有,侵权必究。

您购买的人民邮电出版社电子书仅供您个人使用,未经授权,不得以任何方式复制和传播本书内容。

我们愿意相信读者具有这样的良知和觉悟,与我们共同保护知识产权。

如果购买者有侵权行为,我们可能对该用户实施包括但不限于关闭该帐号等维权措施,并可能追究法律责任。

编  著 李子骅

责任编辑 刘雅思

人民邮电出版社出版发行  北京市丰台区成寿寺路11号

邮编 100164  电子邮件 315@ptpress.com.cn

网址 http://www.ptpress.com.cn

读者服务热线:(010)81055410

反盗版热线:(010)81055315


本书是一本Redis的入门指导图书,以通俗易懂的方式介绍了Redis基础与实践方面的知识,包括历史与特性,在开发环境和生产环境中部署运行Redis,数据类型与命令,使用Redis实现事务、排序、消息通知、管道、Redis存储空间的优化,持久化等内容,并采用“任务驱动”的方式介绍了PHP、Ruby、Python和Node.js这4种编程语言的Redis客户端库的使用方法。

本书的目标读者不仅包括Redis新手,还包括已经掌握Redis使用方法的读者。对新手而言,本书的内容由浅入深且紧贴实践,让读者真正能够即学即用;对于已经了解Redis的读者,通过本书的大量实例以及细节介绍,也能发现很多新的技巧。


作为数据库领域的后起之秀,Redis如今已经成为Web开发社区中最火热的数据库之一。随着Web 2.0的蓬勃发展,网站数据快速增长,对高性能读写的需求也越来越多,再加上半结构化数据的比重逐渐增大,人们对早已被铺天盖地地运用着的关系数据库能否适应现今的存储需求产生了疑问,而Redis的迅猛发展为这个领域注入了全新的思维。

Redis凭借其全面的功能受到越来越多的公司的青睐,从初创企业到拥有几百台Redis服务器的大公司,都能看到Redis的身影。Redis也是一个名副其实的多面手,无论是存储、队列还是缓存系统,都有它的用武之地。

本书将从Redis的历史讲起,结合基础与实践,带领读者一步步进入Redis的世界。

距离本书第2版出版已经过去了6年,Redis在这期间也发生了巨大的改变。从3.0版到6.0版,Redis的每个重大版本都给日益壮大的开发者群体带来更多激动人心的新功能。从能更好地胜任消息中间件的流类型,到大大丰富Redis使用场景的模块系统,整个Redis的发展过程就是Redis的开发者与用户良好互动的最佳印证。

截至2021年,在Stack Overflow发布的全球开发者调查报告中,Redis连续4年蝉联“最受开发者喜爱的数据库”以及“亚马逊云使用最广泛的数据库”两项殊荣。借此时机,本书第3版对这几年中Redis推出的重要功能以及社区生态的变化进行相应更新,希望能将这些新的信息与广大读者分享。

本书假定读者是Redis新手,甚至可能连Redis是什么都没听说过。本书将详细介绍Redis是什么以及为什么要使用Redis,旨在让读者从零开始,逐步晋级为一个优秀的Redis开发者。

本书还包含很多Redis实践方面的知识,有经验的Redis开发者完全可以直接跳过已经掌握的内容,只阅读感兴趣的部分。每章的引言都简要介绍了这一章要讲解的内容,供读者参考。

本书不需要读者掌握任何Redis的背景知识,不过如果读者有Web后端开发经验或Linux操作系统使用经验,阅读本书将会更加得心应手。

第1章介绍了Redis的历史与特性,主要回答初学者最关心的两个问题,即Redis是什么和为什么要使用Redis。

第2章介绍了如何安装和运行Redis。如果你身旁的计算机没有运行Redis,那么一定不要错过这一章,因为本书后面的部分都希望读者能一边阅读一边实践,以提高学习效率。这一章还会介绍Redis命令行客户端的使用方法等基础知识,这些都是实践前需要掌握的知识。

第3章介绍了Redis的数据类型。这一章讲解的不仅是每个数据类型和命令格式,还会着重讲解每个数据类型在实践中如何使用。这一章会带领读者从零开始,一步步地使用Redis构建一个博客系统。读者在学习完这一章的内容之后可以直接在自己的项目中上手实践Redis。

第4章介绍了一些Redis的进阶知识,例如事务和消息通知等。同样这一章还会继续以博客系统为例,以实践驱动学习。

第5章介绍了如何在各种编程语言中使用Redis,这些语言包括PHP、Ruby、Python和Node.js。其中,讲解每种编程语言时,都会用一个有趣的例子进行演示,即使读者不了解某些编程语言,阅读这些例子也能让你收获颇丰。

第6章介绍了Redis脚本的强大功能。这一章会向读者讲解如何借助脚本扩展Redis,并且会对脚本中一些需要注意的知识(如沙盒、随机结果等)进行着重介绍。

第7章介绍了Redis持久化的知识。Redis持久化包含RDB和AOF两种方式,对持久化的支持是Redis可以用作数据库的必要条件。

第8章介绍了多个Redis实例的维护方法,包括使用复制实现读写分离、借助哨兵来自动完成故障恢复以及通过集群来实现数据分片。

第9章介绍了Redis安全和通信协议相关的内容,并推荐了几个第三方的Redis管理工具。

附录A收录了Redis命令的不同属性以及这些属性的特征。

附录B收录了Redis部分配置参数的章节索引。

附录C收录了Redis使用的CRC16实现代码。

本书排版使用字体遵从以下约定。

$ redis-cli PING
PONG

 Redis命令行客户端的输入和输出以如下格式显示:

redis> SET foo bar
OK

 程序代码以如下格式显示:

var redis = require("redis");
var client = redis.createClient();

// 将两个对象JSON序列化后存入数据库中
client.mset(
    'user:1', JSON.stringify(bob),
    'user:2', JSON.stringify(jeff)
);

本书的部分章节采用伪代码讲解,这种伪代码类似于Ruby和PHP代码,例如:

def hsetnx($key, $field, $value)
    $isExists = HEXISTS $key, $field
    if $isExists is 0
       HSET $key, $field, $value
       return 1
    else
       return 0

其中,变量使用$符号标识,Redis命令使用粗体表示并省略括号,以便于阅读。在命令调用和print等语句中,没有$符号的字符串会被当作字符串字面值。

本书第5章中每一节都包含一个完整的程序,读者最好自己输入这些代码来加深理解,当然,先查看程序的运行结果再开始学习也不失为一个好办法。

这些程序代码都存放在GitHub上(https://github.com/luin/redis-book-v3-code),供读者查看和下载。读者也可以从异步社区(https://www.epubit.com)本书页面下载程序代码。

在写作本书的过程中,我得到了很多朋友的帮助。请允许我在这里占用少许篇幅,向他们致以诚挚的谢意。

感谢人民邮电出版社的杨海玲编辑对本书的支持,没有她的悉心指导,本书就无法顺利完成。

感谢刘亚晨、李欣越、寇祖阳和余尧,他们帮我承担了许多额外的工作,使得我可以全身心地投入写作。

感谢所有浏览本书初稿并提出意见和建议的人:张沈鹏、陈硕实、刘其帅、扈煊、李其超、朱冲宇、王诗吟、黄山月、刘昕、韩重远、李申申、杨海朝、田琪等,感谢你们的支持。

另外,还要感谢“宋老师”,是的,就是书中的主人公之一。几年前我刚创业时,办公场所是和某教育机构合租的。宋老师是该机构的一名老师,同时他也是国内一个知名嘻哈乐团的成员。他平日风趣的谈吐给我们带来了很多欢乐,伴随我们度过了艰苦的创业初期。而我接触Redis,也正是从这段时间开始的。


本书由异步社区出品,社区(https://www.epubit.com/)为您提供相关资源和后续服务。

本书提供源代码下载,要获得相关配套资源,请在异步社区本书页面中点击,跳转到下载界面,按提示进行操作即可。注意:为保证购书读者的权益,该操作会给出相关提示,要求输入提取码进行验证。

作者和编辑尽最大努力来确保书中内容的准确性,但难免会存在疏漏。欢迎您将发现的问题反馈给我们,帮助我们提升图书的质量。

当您发现错误时,请登录异步社区,按书名搜索,进入本书页面,点击“提交勘误”,输入勘误信息,点击“提交”按钮即可(见下图)。本书的作者和编辑会对您提交的勘误信息进行审核,确认并接受您的建议后,您将获赠异步社区的100积分。积分可用于在异步社区兑换优惠券、样书或奖品。

本书责任编辑的联系邮箱是liuyasi@ptpress.com.cn。

如果您对本书有任何疑问或建议,请您发邮件给我们,并请在邮件标题中注明本书书名,以便我们更高效地做出反馈。

如果您有兴趣出版图书、录制教学视频或者参与技术审校等工作,可以直接发邮件给本书的责任编辑。

如果您来自学校、培训机构或企业,想批量购买本书或异步社区出版的其他图书,也可以发邮件给我们。

如果您在网上发现有针对异步社区出品图书的各种形式的盗版行为,包括对图书全部或部分内容的非授权传播,请您将怀疑有侵权行为的链接通过邮件发给我们。您的这一举动是对作者权益的保护,也是我们持续为您提供有价值的内容的动力之源。

“异步社区”是人民邮电出版社旗下IT图书社区,致力于出版精品IT图书和相关学习产品,为作译者提供优质出版服务。异步社区创办于2015年8月,提供大量精品IT图书和电子书,以及高品质技术文章和视频课程。更多详情请访问异步社区官网https://www. epubit.com。

“异步图书”是由异步社区编辑团队策划出版的精品IT图书的品牌,依托于人民邮电出版社近40年的计算机图书出版积累和专业编辑团队,相关图书在封面上印有异步图书的LOGO。异步图书的出版领域包括软件开发、大数据、人工智能、测试、前端和网络技术等。

异步社区

微信服务号


Redis 是一个开源的、高性能的、基于键值对的缓存与存储系统,通过提供多种键值数据类型来适应不同场景下的缓存与存储需求。同时Redis的诸多高层级功能使其可以胜任消息队列、任务队列等不同的角色。除此之外,Redis还支持外部模块扩展,使其在某些场景下可以作为主数据库使用。

本章将分别介绍Redis的历史和特性,以使读者能够快速地对Redis有一个全面的了解。

2008年,意大利的一家创业公司Merzia推出了一款基于MySQL的网站实时统计系统LLOOGG,然而没过多久,该公司的创始人Salvatore Sanfilippo便开始对MySQL的性能感到失望,于是他决定亲自为LLOOGG量身定制一个数据库,并于2009年开发完成,这个数据库就是Redis。不过Salvatore Sanfilippo并不满足将Redis只用于LLOOGG这一款产品,而是希望让更多的人使用它,于是在同一年Salvatore Sanfilippo将Redis开源发布,并开始和Redis的另一名主要的代码贡献者Pieter Noordhuis一起继续着Redis的开发。

Salvatore Sanfilippo自己也没有想到,短短的几年时间,Redis就拥有了庞大的用户群体。截至2021年,在Stack Overflow发布的全球开发者调查报告中,Redis连续4年蝉联“最受开发者喜爱的数据库”以及“亚马逊云使用最广泛的数据库”两项殊荣。Redis的国内用户包括新浪微博、街旁网和知乎等,国外用户包括GitHub、Stack Overflow、Flickr、暴雪和Instagram等。

VMware公司从2010年开始赞助Redis的开发,Salvatore Sanfilippo和Pieter Noordhuis也分别于同年的3月和5月加入VMware,全职开发Redis。

随后在2015年7月15日,Salvatore Sanfilippo加入一家位于美国加利福尼亚州的公司Redis Labs。这家公司专门提供围绕Redis的数据库云服务。从此,Redis Labs正式成为Redis的官方赞助商。

2020年6月30日,Salvatore Sanfilippo决定退居二线,即不再参与Redis的日常维护,而是作为Redis Labs的技术顾问去探索如何让Redis更进一步等更多未知的事情。自此,Redis Labs的首席架构师Yossi Gottlieb和高级软件架构师Oran Arga接替Salvatore Sanfilippo的工作让Redis继续前进。

Redis的代码托管在GitHub上,开发十分活跃。截至本书出版,Redis的最新稳定版本为发布于2020年的Redis 6。本书的内容也是基于此版本编写的。


小背景 

2009年2月25日,有人在Hacker News上发布了一个帖子(如图1-1所示),内容就是“Redis”这五个字母,还有到当时Redis的托管商Google Code的链接。Redis的作者在这个贴子下面发表回复:“Redis(与其他竞品相比)的一个重要目标就是让键值能够支持更多高级复杂的数据类型。”实际上一直到十几年后的今天,Redis仍然在朝着这个方向努力。

图1-1 Redis官网提供了详细的命令文档


作为一款最初由个人开发的系统,Redis究竟有什么魅力经久不衰,吸引了如此多的用户呢?

有脚本语言编程经验的读者对字典(或称映射、关联数组)数据结构一定很熟悉,如代码dict["key"] = "value"dict是一个字典变量,字符串"key"是键名,而"value"是键值,在字典中我们可以获取或设置键名对应的键值,也可以删除一个键。

Redis是REmote DIctionary Server(远程字典服务器)的缩写,它以字典存储数据,并允许其他应用通过TCP读写字典中的内容。同大多数脚本语言中的字典一样,Redis字典中的键值除了可以是字符串,还可以是其他数据类型。到目前为止,Redis支持的键值数据类型如下:

这种字典形式的存储结构与常见的MySQL等关系数据库的二维表形式的存储结构有很大的差异。举个例子,如下所示,我们在程序中使用post变量存储了一篇文章的数据(包括标题、正文、阅读量和标签):

post["title"]  =  "Hello World!"
post["content"] = "Blablabla..."
post["views"] = 0
post["tags"] = ["PHP", "Ruby", "Node.js"]

现在我们希望将这篇文章的数据存储在数据库中,并且要求可以通过标签检索出文章。如果使用关系数据库存储,一般会将其中的标题、正文和阅读量存储在一个表中,而将标签存储在另一个表中,然后使用第三个表连接文章和标签表[1]。需要查询时还得将3个表进行连接,不是很直观。而Redis字典结构的存储方式和对多种键值数据类型的支持使得开发者可以将程序中的数据直接映射到Redis中,数据在Redis中的存储形式和其在程序中的存储方式非常相近。使用Redis的另一个优势是其对不同的数据类型提供了非常方便的操作方式,如使用集合类型存储文章标签,对标签进行如交、并这样的集合运算操作。3.5节会专门介绍如何借助集合运算轻松地实现“找出所有同时属于A标签和B标签且不属于C标签的元素”这样用关系数据库实现起来性能不高且较为烦琐的操作。

Redis数据库中的所有数据都存储在内存中。由于内存的读写速度远快于硬盘,因此Redis在性能上对比其他基于硬盘存储的数据库有非常明显的优势,在一台普通的笔记本计算机上,Redis可以在一秒内读写超过10万个键值。

将数据存储在内存中也有问题,例如程序退出后内存中的数据会丢失。不过Redis提供了对持久化的支持,即可以将内存中的数据异步写入硬盘中,同时不影响继续提供服务。

Redis虽然是作为数据库开发的,但由于其提供了丰富的功能,越来越多的人将其用作缓存、队列系统等。Redis可谓是名副其实的多面手。

Redis可以为每个键设置生存时间(Time To Live,TTL),生存时间到期后键会自动被删除。这一功能配合出色的性能让Redis可以作为缓存系统来使用,而且Redis支持持久化和丰富的数据类型的特性使其成为另一个非常流行的缓存系统Memcached的有力竞争者。


讨论 

关于Redis和Memcached优劣的讨论一直是一个热门的话题。在性能上Redis是单线程模型,而Memcached支持多线程,所以在多核服务器上后者的性能理论上相对更高一些。然而,前面已经介绍过,Redis的性能已经足够优异,在绝大部分场景中其性能不会成为瓶颈,所以在使用时更应该关心的是二者在功能上的区别。Redis 3.0的推出标志着Memcached的几乎所有功能已成为Redis的子集。同时,Redis对集群的支持使得Memcached原有的第三方集群工具不再成为优势。因此,在新项目中使用Redis而不是Memcached将会是更好的选择。


作为缓存系统,Redis还可以限定数据占用的最大内存空间,在数据达到空间限制后可以按照一定的规则自动淘汰不需要的键。

除此之外,Redis的列表类型键可以用来实现队列系统,并且支持阻塞式读取,可以很容易地实现一个高性能的优先级队列。同时在更高层面上,Redis还支持“发布/订阅”的消息模式,可以基于此构建聊天室[2]等系统。

更有趣的是,Redis从4.0版本开始提供对模块(module)的支持。借助模块,用户可以高性能地基于Redis本身的核心能力扩展出更广泛的用途。以下是一些常见的模块:

(1)RediSearch模块提供了全文搜索功能;

(2)RedisGraph模块可以把Redis变成一个图数据库;

(3)RedisJSON为Redis增加了JSON数据类型;

(4)rediSQL可以让Redis运行SQL语句。

即使功能再丰富,如果使用起来太复杂也很难吸引人。Redis直观的存储结构使得通过程序与Redis交互十分简单。在Redis中使用命令来读写数据,命令之于Redis就相当于SQL语言之于关系数据库。例如在关系数据库中要获取posts表内id1的记录的title字段的值,可以使用如下SQL语句实现:

SELECT title FROM posts WHERE id = 1 LIMIT 1

相应地,在Redis中要读取键名为post:1的哈希类型键的title字段的值,可以使用如下命令实现:

HGET post:1 title

其中,HGET就是一条命令。Redis提供了200多条命令(如图1-2所示),听起来很多,但是由于使用场景不同,每个使用场景中需要用到的命令不会很多,而且每条命令都很容易记忆。读完第3章你就会发现Redis的命令比SQL语言要简单很多。

图1-2 Redis官网提供了详细的命令文档

Redis提供了几十种不同编程语言的客户端库,这些库都很好地封装了Redis的命令,使得在程序中与Redis进行交互变得更容易。有些库还提供了可以将编程语言中的数据类型直接以相应的形式存储到Redis中(如将数组以列表类型直接存入Redis)的简单方法,使用起来非常方便。

Redis使用C语言开发,代码量只有几万行。这降低了用户通过修改Redis源代码来使之更适合自己的项目所需要的门槛。对于希望“榨干”数据库性能的开发者,这无疑具有强大的吸引力。

Redis是开源的,所以事实上Redis的开发者并非只有Salvatore Sanfilippo。截至目前,有数百名开发者为Redis贡献了代码。良好的开发氛围和严谨的版本发布机制使得Redis的稳定版本非常可靠,如此多的公司在项目中使用Redis也可以印证这一点。

[1] 这是一种符合第三范式的设计。事实上,还可以使用其他方式来实现标签系统。

[2] Redis的贡献者之一Pieter Noordhuis提供了一个使用该模式开发的聊天室的例子。


相关图书

Redis实战
Redis实战
Redis入门指南(第2版)
Redis入门指南(第2版)
Redis入门指南
Redis入门指南

相关文章

相关课程