redis

redis

开源高性能内存数据结构存储系统

Redis是一个开源的高性能内存数据结构存储系统。它支持字符串、哈希、列表、集合等多种数据结构,并提供持久化、复制和集群功能。Redis将数据存储在内存中以实现高速访问,同时支持数据持久化到磁盘。其高效的内存使用机制使其比传统数据库占用更少内存。Redis广泛应用于缓存、消息队列和实时分析等场景,是现代互联网应用的重要基础设施。

Redis数据结构服务器内存效率持久化命令集Github开源项目

这个README只是一份快速入门文档。您可以在redis.io找到更详细的文档。

什么是Redis?

Redis通常被称为数据结构服务器。这意味着Redis通过一组命令提供对可变数据结构的访问,这些命令使用基于TCP套接字和简单协议的服务器-客户端模型发送。因此,不同的进程可以以共享方式查询和修改相同的数据结构。

Redis中实现的数据结构有一些特殊属性:

  • Redis会将它们存储在磁盘上,即使它们始终在服务器内存中提供和修改。这意味着Redis既快速又非易失。
  • 数据结构的实现强调内存效率,因此Redis内部的数据结构与使用高级编程语言建模的相同数据结构相比可能使用更少的内存。
  • Redis提供了许多在数据库中自然存在的功能,如复制、可调节的持久性级别、集群和高可用性。

另一个很好的例子是将Redis视为memcached的更复杂版本,其中操作不仅仅是SET和GET,还包括使用列表、集合、有序数据结构等复杂数据类型的操作。

如果您想了解更多,以下是一些精选的起点:

什么是Redis社区版?

Redis OSS在v7.4版本中更名为Redis社区版(CE)。

Redis Ltd.还提供Redis软件,这是一个自管理软件,具有额外的合规性、可靠性和弹性,适用于企业级扩展, 以及Redis Cloud,一个与Google Cloud、Azure和AWS集成的全托管服务,适用于生产就绪的应用程序。

此处阅读有关Redis社区版和Redis之间差异的更多信息。

构建Redis

Redis可以在Linux、OSX、OpenBSD、NetBSD、FreeBSD上编译和使用。 我们支持大端和小端架构,以及32位和64位系统。

它可能可以在Solaris派生系统(例如SmartOS)上编译,但我们对这个平台的 支持是尽力而为的,Redis不能保证像在Linux、OSX和*BSD上那样运行良好。

它非常简单:

% make

要构建TLS支持,您需要OpenSSL开发库(例如 Debian/Ubuntu上的libssl-dev)并运行:

% make BUILD_TLS=yes

要构建systemd支持,您需要systemd开发库(如 Debian/Ubuntu上的libsystemd-dev或CentOS上的systemd-devel)并运行:

% make USE_SYSTEMD=yes

要为Redis程序名称添加后缀,请使用:

% make PROG_SUFFIX="-alt"

您可以使用以下命令构建32位Redis二进制文件:

% make 32bit

构建Redis后,最好使用以下命令进行测试:

% make test

如果构建了TLS,请使用TLS运行测试(您需要安装tcl-tls):

% ./utils/gen-test-certs.sh
% ./runtest --tls

修复依赖项或缓存的构建选项的构建问题

Redis有一些包含在deps目录中的依赖项。 即使依赖项的源代码发生变化,make也不会自动重新构建依赖项。

当您使用git pull更新源代码或以任何其他方式修改依赖项树中的代码时, 请确保使用以下命令真正清理所有内容并从头开始重新构建:

% make distclean

这将清理:jemalloc、lua、hiredis、linenoise和其他依赖项。

此外,如果您强制某些构建选项,如32位目标、无C编译器 优化(用于调试目的)以及其他类似的构建时选项, 这些选项将无限期缓存,直到您发出make distclean 命令。

修复构建32位二进制文件的问题

如果在构建Redis的32位目标后需要重新构建64位目标, 或者相反,您需要在Redis发行版的根目录中执行 make distclean

如果在尝试构建Redis的32位二进制文件时出现构建错误,请尝试 以下步骤:

  • 安装libc6-dev-i386包(也可以尝试g++-multilib)。
  • 尝试使用以下命令行代替make 32bit: make CFLAGS="-m32 -march=native" LDFLAGS="-m32"

分配器

在构建Redis时选择非默认内存分配器是通过设置 MALLOC环境变量来完成的。默认情况下,Redis编译并链接到libc malloc,但在Linux系统上默认使用jemalloc。之所以选择这个默认值, 是因为jemalloc已被证明比libc malloc具有更少的碎片问题。

要强制编译使用libc malloc,请使用:

% make MALLOC=libc

要在Mac OS X系统上编译使用jemalloc,请使用:

% make MALLOC=jemalloc

单调时钟

默认情况下,Redis将使用POSIX clock_gettime函数作为 单调时钟源来构建。在大多数现代系统上,可以使用内部处理器时钟 来提高性能。注意事项可以在这里找到: http://oliveryang.net/2015/09/pitfalls-of-TSC-usage/

要构建支持处理器的内部指令时钟,请使用:

% make CFLAGS="-DUSE_PROCESSOR_CLOCK"

详细构建

默认情况下,Redis将以用户友好的彩色输出进行构建。 如果您想看到更详细的输出,请使用以下内容:

% make V=1

运行Redis

要使用默认配置运行Redis,只需输入:

% cd src
% ./redis-server

如果您想提供自己的redis.conf,您必须使用额外的 参数(配置文件的路径)运行它:

% cd src
% ./redis-server /path/to/redis.conf

可以通过直接传递参数作为命令行选项来更改Redis配置。例如:

% ./redis-server --port 9999 --replicaof 127.0.0.1 6379
% ./redis-server /etc/redis/6379.conf --loglevel debug

redis.conf中的所有选项也都支持作为命令行选项使用, 名称完全相同。

使用TLS运行Redis

请查阅TLS.md文件以获取有关如何使用TLS运行Redis的更多信息。

使用Redis

您可以使用redis-cli来使用Redis。启动一个redis-server实例, 然后在另一个终端中尝试以下操作:

% cd src
% ./redis-cli
redis> ping
PONG
redis> set foo bar
OK
redis> get foo
"bar"
redis> incr mycounter
(integer) 1
redis> incr mycounter
(integer) 2
redis>

您可以在https://redis.io/commands找到所有可用命令的列表。

安装Redis

要将Redis二进制文件安装到/usr/local/bin,只需使用:

% make install

如果您希望使用不同的目标目录,可以使用make PREFIX=/some/other/directory install

make install只会将二进制文件安装到您的系统中,但不会在适当的位置配置 初始化脚本和配置文件。如果您只想稍微玩一下Redis,这不是必需的,但如果您正在 为生产系统进行适当的安装,我们有一个脚本可以为Ubuntu和Debian系统执行此操作:

% cd utils
% ./install_server.sh

注意:install_server.sh在Mac OSX上不起作用;它仅为Linux构建。

该脚本将询问您一些问题,并设置您需要的一切 以将Redis正确作为后台守护进程运行,该守护进程将在系统重新启动时再次启动。

您将能够使用名为/etc/init.d/redis_<portnumber>的脚本停止和启动Redis, 例如/etc/init.d/redis_6379

代码贡献

通过以任何形式向Redis项目贡献代码,包括通过GitHub发送拉取请求、 通过私人电子邮件或公共讨论组发送代码片段或补丁,您同意根据 Redis软件授权和贡献者许可协议的条款发布您的代码。Redis软件 包含对原始Redis核心项目的贡献,这些贡献由其贡献者拥有并根据3BSD许可证 获得许可。此存储库中该许可证的任何副本仅适用于这些贡献。Redis将所有Redis社区版7.4.x及以后版本 根据LICENSE.txt文件中描述的RSALv2/SSPL双重许可发布,该文件包含在Redis社区版源代码分发中。

请参阅本源代码分发中的CONTRIBUTING.md文件以获取更多信息。对于 安全漏洞和漏洞,请参阅SECURITY.md

Redis商标

商标的目的是识别个人或公司的商品和服务而不引起混淆。作为其名称和标志的 注册所有者,Redis接受其商标的某些有限使用,但必须遵守其商标 指南中描述的要求,可在以下网址获取:https://redis.com/legal/trademark-guidelines/。

Redis内部

如果您正在阅读此README,您可能正在GitHub页面上或者刚刚解压了Redis分发tar包。 在这两种情况下,您基本上离源代码只有一步之遥,因此在这里我们解释 Redis源代码布局,每个文件中大致包含什么内容,Redis服务器内部 最重要的函数和结构等。我们将所有讨论保持在高层次,不深入细节, 因为否则这份文档会非常庞大,而且我们的代码库不断变化,但一个总体概念 应该是理解更多内容的良好起点。此外,大部分代码都有大量注释,易于 理解。

源代码布局

Redis根目录只包含此README、调用src目录中真正的Makefile的Makefile、 以及Redis和Redis Sentinel的示例配置。您可以找到一些shell 脚本,用于执行Redis、Redis Cluster和Redis Sentinel单元测试, 这些测试在tests目录中实现。

根目录中有以下重要目录:

  • src:包含用C语言编写的Redis实现。
  • tests:包含用Tcl实现的单元测试。
  • deps:包含Redis使用的库。编译Redis所需的一切都在这个目录中;您的系统只需提供libc、POSIX兼容接口和C编译器。值得注意的是,deps包含jemalloc的副本,这是Linux下Redis的默认分配器。请注意,在deps下还有一些东西是从Redis项目开始的,但主要存储库不是redis/redis

还有一些其他目录,但对我们这里的目标不太重要。我们将主要关注src, 其中包含Redis实现,探索每个文件中的内容。文件暴露的顺序 是逐步披露不同复杂层的逻辑顺序。

注意:最近Redis进行了相当大的重构。函数名称和文件 名称已更改,因此您可能会发现此文档更接近unstable分支。 例如,在Redis 3.0中,server.cserver.h文件名为redis.credis.h。 但整体结构是相同的。请记住,所有新的开发和拉取请求 都应针对unstable分支执行。

server.h

理解程序如何工作的最简单方法是理解 它使用的数据结构。因此,我们将从Redis的主头文件开始, 即server.h

所有服务器配置以及一般所有共享状态都 定义在一个名为server的全局结构中,类型为struct redisServer。 该结构中的一些重要字段是:

  • server.db是Redis数据库的数组,存储数据。
  • server.commands是命令表。
  • server.clients是连接到服务器的客户端的链表。
  • server.master是一个特殊客户端,如果实例是副本,则为主服务器。

还有许多其他字段。大多数字段直接在 结构定义内注释。

另一个重要的Redis数据结构是定义客户端的结构。 过去它被称为redisClient,现在只是client。该结构 有许多字段,这里我们只展示主要字段:

struct client { int fd; sds querybuf; int argc commands.c --- 此文件由utils/generate-command-code.py自动生成,内容基于src/commands文件夹中的JSON文件。这些JSON文件旨在作为Redis命令及其所有元数据的单一真实来源。这些JSON文件并不意味着供任何人直接使用,相关元数据可以通过`COMMAND`命令获取。 networking.c --- 此文件定义了与客户端、主服务器和从服务器(在Redis中只是特殊的客户端)进行I/O操作的所有函数: * `createClient()`分配并初始化一个新客户端。 * `addReply*()`系列函数由命令实现使用,用于向客户端结构附加数据,这些数据将作为对特定执行命令的回复传输给客户端。 * `writeToClient()`将输出缓冲区中待处理的数据传输给客户端,由可写事件处理程序`sendReplyToClient()`调用。 * `readQueryFromClient()`是可读事件处理程序,将从客户端读取的数据累积到查询缓冲区中。 * `processInputBuffer()`是根据Redis协议解析客户端查询缓冲区的入口点。一旦命令准备好处理,它会调用`server.c`中定义的`processCommand()`来实际执行命令。 * `freeClient()`释放、断开连接并移除客户端。 aof.c和rdb.c --- 顾名思义,这些文件实现了Redis的RDB和AOF持久化。Redis使用基于`fork()`系统调用的持久化模型,创建一个与主Redis进程具有相同(共享)内存内容的进程。这个辅助进程将内存内容转储到磁盘上。`rdb.c`使用这种方式在磁盘上创建快照,而`aof.c`在追加只写文件变得过大时用于执行AOF重写。 `aof.c`中的实现还有额外的函数,用于实现一个API,允许命令在客户端执行时将新命令附加到AOF文件中。 `server.c`中定义的`call()`函数负责调用将命令写入AOF的函数。 db.c --- 某些Redis命令操作特定数据类型;其他是通用的。通用命令的例子有`DEL`和`EXPIRE`。它们操作键而不是特定的值。所有这些通用命令都定义在`db.c`中。 此外,`db.c`实现了一个API,用于在不直接访问内部数据结构的情况下对Redis数据集执行某些操作。 `db.c`中最重要的、在许多命令实现中使用的函数包括: * `lookupKeyRead()`和`lookupKeyWrite()`用于获取与给定键关联的值的指针,如果键不存在则返回`NULL`。 * `dbAdd()`及其高级对应函数`setKey()`在Redis数据库中创建新键。 * `dbDelete()`移除键及其关联值。 * `emptyData()`移除整个单一数据库或所有定义的数据库。 文件的其余部分实现了暴露给客户端的通用命令。 object.c --- 定义Redis对象的`robj`结构已经描述过了。`object.c`中包含所有在基本级别操作Redis对象的函数,如分配新对象、处理引用计数等函数。此文件中的重要函数包括: * `incrRefCount()`和`decrRefCount()`用于增加或减少对象的引用计数。当计数降至0时,对象最终被释放。 * `createObject()`分配一个新对象。还有一些专门用于分配具有特定内容的字符串对象的函数,如`createStringObjectFromLongLong()`等类似函数。 该文件还实现了`OBJECT`命令。 replication.c --- 这是Redis中最复杂的文件之一,建议在熟悉其他代码库后再approach它。此文件实现了Redis的主从角色。 该文件中最重要的函数之一是`replicationFeedSlaves()`,它将命令写入代表连接到我们主服务器的从实例的客户端,这样从服务器就可以获取客户端执行的写操作:通过这种方式,它们的数据集将与主服务器保持同步。 该文件还实现了`SYNC`和`PSYNC`命令,用于执行主从服务器之间的首次同步,或在断开连接后继续复制。 脚本 --- 脚本单元由3个单元组成: * `script.c` - 脚本与Redis的集成(命令执行、设置复制/resp等) * `script_lua.c` - 负责执行Lua代码,使用`script.c`从Lua代码中与Redis交互。 * `function_lua.c` - 包含Lua引擎实现,使用`script_lua.c`执行Lua代码。 * `functions.c` - 包含Redis函数实现(`FUNCTION`命令),如果要调用的函数需要Lua引擎,则使用`functions_lua.c`。 * `eval.c` - 包含`eval`实现,使用`script_lua.c`调用Lua代码。 其他C文件 --- * `t_hash.c`、`t_list.c`、`t_set.c`、`t_string.c`、`t_zset.c`和`t_stream.c`包含Redis数据类型的实现。它们既实现了访问给定数据类型的API,也实现了这些数据类型的客户端命令。 * `ae.c`实现了Redis事件循环,它是一个简单易读易懂的自包含库。 * `sds.c`是Redis字符串库,更多信息请查看https://github.com/antirez/sds。 * `anet.c`是一个库,用于以比内核暴露的原始接口更简单的方式使用POSIX网络。 * `dict.c`是一个非阻塞哈希表的实现,它可以增量式重哈希。 * `cluster.c`实现了Redis集群。可能只有在非常熟悉Redis代码库的其他部分后才适合阅读。如果你想阅读`cluster.c`,请确保阅读[Redis集群规范][4] [4]: https://redis.io/topics/cluster-spec Redis命令剖析 --- 所有Redis命令都以以下方式定义: ```c void foobarCommand(client *c) { printf("%s",c->argv[1]->ptr); /* 对参数做些处理。 */ addReply(c,shared.ok); /* 向客户端回复一些内容。 */ }

命令函数由JSON文件引用,连同其元数据一起,详情见上述commands.c的描述。命令标志在server.hstruct redisCommand上方的注释中有文档说明。其他细节,请参考COMMAND命令。https://redis.io/commands/command/

命令以某种方式操作后,会使用addReply()networking.c中定义的类似函数向客户端返回回复。

Redis源代码中有大量命令实现可以作为实际命令实现的例子(如pingCommand)。编写一些玩具命令可能是熟悉代码库的好练习。

还有许多其他未在此描述的文件,但没必要涵盖所有内容。我们只是想帮助你迈出第一步。最终你会在Redis代码库中找到自己的方向:-)

祝你愉快!

编辑推荐精选

即梦AI

即梦AI

一站式AI创作平台

提供 AI 驱动的图片、视频生成及数字人等功能,助力创意创作

扣子-AI办公

扣子-AI办公

AI办公助手,复杂任务高效处理

AI办公助手,复杂任务高效处理。办公效率低?扣子空间AI助手支持播客生成、PPT制作、网页开发及报告写作,覆盖科研、商业、舆情等领域的专家Agent 7x24小时响应,生活工作无缝切换,提升50%效率!

Keevx

Keevx

AI数字人视频创作平台

Keevx 一款开箱即用的AI数字人视频创作平台,广泛适用于电商广告、企业培训与社媒宣传,让全球企业与个人创作者无需拍摄剪辑,就能快速生成多语言、高质量的专业视频。

TRAE编程

TRAE编程

AI辅助编程,代码自动修复

Trae是一种自适应的集成开发环境(IDE),通过自动化和多元协作改变开发流程。利用Trae,团队能够更快速、精确地编写和部署代码,从而提高编程效率和项目交付速度。Trae具备上下文感知和代码自动完成功能,是提升开发效率的理想工具。

热门AI工具生产力协作转型TraeAI IDE
蛙蛙写作

蛙蛙写作

AI小说写作助手,一站式润色、改写、扩写

蛙蛙写作—国内先进的AI写作平台,涵盖小说、学术、社交媒体等多场景。提供续写、改写、润色等功能,助力创作者高效优化写作流程。界面简洁,功能全面,适合各类写作者提升内容品质和工作效率。

AI助手AI工具AI写作工具AI辅助写作蛙蛙写作学术助手办公助手营销助手
问小白

问小白

全能AI智能助手,随时解答生活与工作的多样问题

问小白,由元石科技研发的AI智能助手,快速准确地解答各种生活和工作问题,包括但不限于搜索、规划和社交互动,帮助用户在日常生活中提高效率,轻松管理个人事务。

聊天机器人AI助手热门AI工具AI对话
Transly

Transly

实时语音翻译/同声传译工具

Transly是一个多场景的AI大语言模型驱动的同声传译、专业翻译助手,它拥有超精准的音频识别翻译能力,几乎零延迟的使用体验和支持多国语言可以让你带它走遍全球,无论你是留学生、商务人士、韩剧美剧爱好者,还是出国游玩、多国会议、跨国追星等等,都可以满足你所有需要同传的场景需求,线上线下通用,扫除语言障碍,让全世界的语言交流不再有国界。

讯飞智文

讯飞智文

一键生成PPT和Word,让学习生活更轻松

讯飞智文是一个利用 AI 技术的项目,能够帮助用户生成 PPT 以及各类文档。无论是商业领域的市场分析报告、年度目标制定,还是学生群体的职业生涯规划、实习避坑指南,亦或是活动策划、旅游攻略等内容,它都能提供支持,帮助用户精准表达,轻松呈现各种信息。

热门AI工具AI办公办公工具讯飞智文AI在线生成PPTAI撰写助手多语种文档生成AI自动配图
讯飞星火

讯飞星火

深度推理能力全新升级,全面对标OpenAI o1

科大讯飞的星火大模型,支持语言理解、知识问答和文本创作等多功能,适用于多种文件和业务场景,提升办公和日常生活的效率。讯飞星火是一个提供丰富智能服务的平台,涵盖科技资讯、图像创作、写作辅助、编程解答、科研文献解读等功能,能为不同需求的用户提供便捷高效的帮助,助力用户轻松获取信息、解决问题,满足多样化使用场景。

模型训练热门AI工具内容创作智能问答AI开发讯飞星火大模型多语种支持智慧生活
Spark-TTS

Spark-TTS

一种基于大语言模型的高效单流解耦语音令牌文本到语音合成模型

Spark-TTS 是一个基于 PyTorch 的开源文本到语音合成项目,由多个知名机构联合参与。该项目提供了高效的 LLM(大语言模型)驱动的语音合成方案,支持语音克隆和语音创建功能,可通过命令行界面(CLI)和 Web UI 两种方式使用。用户可以根据需求调整语音的性别、音高、速度等参数,生成高质量的语音。该项目适用于多种场景,如有声读物制作、智能语音助手开发等。

下拉加载更多