Redis의 마스터-슬레이브 아키텍처의 데이터 일관성 동기화 원칙에 대한 심층적인 이해

青灯夜游
풀어 주다: 2021-09-27 11:46:55
앞으로
2846명이 탐색했습니다.

이 글은 Redis의 마스터-슬레이브 아키텍처에서 데이터 일관성 동기화의 원리를 소개합니다. 도움이 되길 바랍니다!

Redis의 마스터-슬레이브 아키텍처의 데이터 일관성 동기화 원칙에 대한 심층적인 이해

고가용성에는 두 가지 의미가 있습니다. 하나는 데이터 손실을 최대한 방지하는 것이고, 다른 하나는 최대한 서비스를 제공한다는 것입니다. AOF와 RDB는 데이터 지속성이 최대한 손실되지 않도록 하는 반면, 마스터-슬레이브 복제는 복사본을 추가하고 하나의 데이터를 여러 인스턴스에 저장하는 것입니다. 한 인스턴스가 다운되더라도 다른 인스턴스는 계속 서비스를 제공할 수 있습니다.

이 기사에서는 주로 Redis 고가용성 기술 솔루션 중 하나인 마스터-슬레이브 복제 아키텍처에 대해 설명합니다.

이 글은 하드코어해서 천천히 음미해보시길 ​​추천드립니다. 독자와 친구들이 질적으로 향상되리라 믿습니다. 틀린 부분이 있으면 바로잡아주시면 감사하겠습니다. "마게바이트"를 팔로우하시고 "별"을 설정하시면 고품질의 기사를 빠르게 받아보실 수 있습니다.

핵심 지식 포인트

Redis의 마스터-슬레이브 아키텍처의 데이터 일관성 동기화 원칙에 대한 심층적인 이해

오프닝 메시지

질문 = 기회. 문제가 발생하면 실제로 내부적으로 행복해집니다. 문제가 클수록 기회도 커집니다.

모든 것에는 대가가 있고, 득실도 있고, 득실도 있기 마련이므로 우리는 많은 고민을 할 필요 없이 우리가 무엇을 하고 싶은지, 우리가 어떤 가격을 가지고 있는지 파악하면 됩니다. 기꺼이 비용을 지불하고 나서 그냥 해보겠습니다!

1. 마스터-슬레이브 복제 개요

65 Brother: RDB 및 AOF를 사용하면 더 이상 가동 중지 시간으로 인한 데이터 손실을 두려워하지 않지만 Redis 인스턴스가 다운될 때 고가용성을 달성하는 방법은 무엇입니까?

한 기계가 다운되어 서비스를 제공할 수 없으니 다른 기계는 어떻게 되나요? 해결될 수 있나요? Redis는 마스터-슬레이브 복제를 통해 다른 Redis 서버에 데이터의 중복 복사본을 복사하는 마스터-슬레이브 모드를 제공합니다.

전자를 마스터 노드(master), 후자를 슬레이브 노드(slave)라고 합니다. 데이터 복제는 단방향이며 마스터 노드에서 슬레이브 노드로만 가능합니다.

기본적으로 각 Redis 서버는 마스터 노드이며 마스터 노드는 여러 개의 슬레이브 노드를 가질 수 있지만(또는 슬레이브 노드가 없을 수도 있음) 슬레이브 노드는 하나의 마스터 노드만 가질 수 있습니다.

65 형제: 마스터와 슬레이브 간의 데이터 일관성을 어떻게 보장할 수 있나요?

복제 데이터의 일관성을 보장하기 위해 마스터-슬레이브 아키텍처는 읽기-쓰기 분리 방식을 채택합니다.

    읽기 작업: 마스터 및 슬레이브 라이브러리 모두 실행될 수 있습니다.
  • 쓰기 작업: 마스터 라이브러리가 먼저 실행한 다음 쓰기 작업을 슬레이브 라이브러리에 동기화합니다. 읽기-쓰기 분리를 사용해야 할까요?
마스터 라이브러리와 슬레이브 라이브러리 모두 쓰기 명령을 실행할 수 있다고 가정할 수 있습니다. 동일한 데이터가 여러 번 수정되고 각 수정 사항이 다른 마스터-슬레이브 인스턴스로 전송되면 인스턴스의 복사 데이터가 일치하지 않게 됩니다.

Redis의 마스터-슬레이브 아키텍처의 데이터 일관성 동기화 원칙에 대한 심층적인 이해데이터 일관성을 보장하기 위해 Redis가 여러 인스턴스의 수정을 잠그고 조정해야 하는 경우 Redis는 당연히 이를 수행하지 않습니다!

65 형제: 마스터-슬레이브 복제에 다른 기능이 있나요?

실패 복구: 마스터 노드가 다운되더라도 다른 노드는 계속 서비스를 제공할 수 있습니다.

로드 밸런싱: 마스터 노드는 쓰기 서비스를 제공하고 슬레이브 노드는 읽기 서비스를 제공하여 압력을 공유합니다. 고가용성: 센트리와 클러스터의 구현입니다. 기반은 고가용성의 초석입니다.

2. 마스터-슬레이브 복제 설정
  1. 마스터-슬레이브 복제 활성화는 슬레이브 노드에서 완전히 시작되며 마스터 노드에서 아무 작업도 수행할 필요가 없습니다.
  2. 65 Brother: 마스터-슬레이브 복제 아키텍처를 구축하는 방법은 무엇입니까?

master 데이터베이스와 슬레이브 데이터베이스의 관계는 Replicaof(Redis 5.0 이전에는 Slaveof가 사용되었습니다) 명령을 통해 형성할 수 있습니다.

슬레이브 노드에서 마스터-슬레이브 복제를 활성화하는 방법에는 3가지가 있습니다.

구성 파일

구성 파일에 <masterip> 복제본</masterip>

을 추가하세요. 슬레이브 서버

Startup 명령

    redis-server --replicaof <masterip> <masterport></masterport></masterip>
  • Client 명령 추가replicaof <masterip> <masterport></masterport></masterip>

  • 启动命令

    redis-server 启动命令后面加入 --replicaof <masterip> <masterport></masterport></masterip>

  • 客户端命令

    启动多个 Redis 实例后,直接通过客户端执行命令:replicaof <masterip> <masterport></masterport></masterip>

    여러 Redis 인스턴스를 시작한 후 클라이언트를 통해 직접 실행 명령: replicaof <masterip> <masterport></masterport></masterip> 그러면 Redis 인스턴스가 슬레이브 노드가 됩니다.

예를 들어 인스턴스 1(172.16.88.1), 인스턴스 2(172.16.88.2), 인스턴스 3(172.16.88.3)이 있다고 가정합니다. 인스턴스 2와 인스턴스 3에서 각각 다음 명령을 실행합니다. 3은 인스턴스 1의 슬레이브 라이브러리가 되고, 인스턴스 1은 마스터가 됩니다.

replicaof 172.16.88.1 6379复制代码
로그인 후 복사

3. 마스터-슬레이브 복제 원칙

마스터-슬레이브 라이브러리 모드가 읽기-쓰기 분리를 채택하면 모든 데이터 쓰기 작업은 세 인스턴스를 조정할 필요 없이 마스터 라이브러리에서만 수행됩니다.

마스터 데이터베이스에 최신 데이터가 있으면 슬레이브 데이터베이스와 동기화되어 마스터 데이터베이스와 슬레이브 데이터베이스의 데이터가 일치합니다. 🎜

65 형: 마스터-슬레이브 데이터베이스 동기화는 어떻게 완료되나요? 마스터 데이터베이스의 데이터가 슬레이브 데이터베이스로 한꺼번에 전송되나요, 아니면 일괄적으로 동기화되나요? 정상 작동 중에 동기화하는 방법은 무엇입니까? 마스터 데이터베이스와 슬레이브 데이터베이스 간의 네트워크 연결이 끊어지면 다시 연결한 후에도 데이터가 일관성을 유지합니까?

65 형제님, 질문이 너무 많습니다. 동기화는 세 가지 상황으로 나뉩니다.

  1. 마스터-슬레이브 라이브러리의 첫 번째 전체 복사본
  2. 마스터-슬레이브 라이브러리의 정상 작동 중 동기화; 마스터-슬레이브 라이브러리 간의 연결 끊김 및 재시작 심지어 동기화.
  3. 마스터-슬레이브 데이터베이스의 첫 번째 전체 복사본

65 형: 너무 어지러워요. 마스터-슬레이브 데이터베이스 간의 첫 번째 동기화부터 시작하겠습니다.

마스터-슬레이브 라이브러리의 첫 번째 복사 과정은 크게 연결 설정 단계(즉, 준비 단계), 마스터 라이브러리에서 슬레이브 라이브러리로 데이터를 동기화하는 단계, 복사 단계의 3단계로 나눌 수 있습니다. 슬레이브 라이브러리에 동기화하는 동안 새로운 쓰기 명령을 보내는 방법

위의 그림을 보시면 전체적인 모습을 보실 수 있습니다. 자세한 내용은 나중에 소개하겠습니다.

연결 설정Redis의 마스터-슬레이브 아키텍처의 데이터 일관성 동기화 원칙에 대한 심층적인 이해

이 단계의 주요 기능은 마스터 노드와 슬레이브 노드 간의 연결을 설정하여 전체 데이터 동기화를 준비하는 것입니다.

슬레이브 라이브러리는 마스터 라이브러리와 연결을 설정하고, psync 명령을 전송하고, 마스터 라이브러리가 응답을 확인한 후 마스터 라이브러리에 동기화가 이루어짐을 알립니다. 노예 도서관이 시작됩니다

.

65 형: 슬레이브 데이터베이스는 어떻게 메인 데이터베이스 정보를 알고 연결을 맺나요?

슬레이브 노드 구성 파일의 Replicaof 구성 항목에 마스터 노드의 IP와 포트를 구성하면 슬레이브 노드는 어떤 마스터 노드에 연결하려는지 알 수 있습니다.

슬레이브 노드는 마스터 노드의 IP와 포트 정보를 저장하는 데 사용되는 masterhost와 masterport라는 두 개의 필드를 유지 관리합니다.

슬레이브 라이브러리는 replicaof를 실행하고 psync 명령을 보내 데이터 동기화가 수행됨을 나타냅니다. 명령을 받은 후 마스터 라이브러리는 매개변수에 따라 복제를 시작합니다. . 이 명령에는 기본 라이브러리의

runID

복사 진행 오프셋replicaof 并发送 psync 命令,表示要执行数据同步,主库收到命令后根据参数启动复制。命令包含了主库的 runID复制进度 offset 两个参数。

  • runID:每个 Redis 实例启动都会自动生成一个 唯一标识 ID,第一次主从复制,还不知道主库 runID,参数设置为 「?」。
  • offset:第一次复制设置为 -1,表示第一次复制,记录复制进度偏移量。

主库收到 psync 命令后,会用 FULLRESYNC 响应命令带上两个参数:主库 runID 和主库目前的复制进度 offset,返回给从库。从库收到响应后,会记录下这两个参数。

FULLRESYNC 响应表示第一次复制采用的全量复制,也就是说,主库会把当前所有的数据都复制给从库。

主库同步数据给从库

第二阶段

master 执行 bgsave命令生成 RDB 文件,并将文件发送给从库,同时主库为每一个 slave 开辟一块 replication buffer 缓冲区记录从生成 RDB 文件开始收到的所有写命令。

从库收到 RDB 文件后保存到磁盘,并清空当前数据库的数据,再加载 RDB 文件数据到内存中。

发送新写命令到从库

第三阶段

从节点加载 RDB 完成后,主节点将 replication buffer 缓冲区的数据发送到从节点,Slave 接收并执行,从节点同步至主节点相同的状态。

65 哥:主库将数据同步到从库过程中,可以正常接受请求么?

主库不会被阻塞,Redis 作为唯快不破的男人,怎么会动不动就阻塞呢。

在生成 RDB 文件之后的写操作并没有记录到刚刚的 RDB 文件中,为了保证主从库数据的一致性,所以主库会在内存中使用一个叫 replication buffer 记录 RDB 文件生成后的所有写操作。

65 哥:为啥从库收到 RDB 文件后要清空当前数据库?

因为从库在通过 replcaof이라는 두 가지 매개변수가 포함되어 있습니다.

    runID

    : 각 Redis 인스턴스는 시작될 때 자동으로 고유 식별 ID를 생성합니다. 첫 번째 마스터-슬레이브 복제의 경우 기본 데이터베이스 runID는 아직 알려지지 않았으며 매개변수는 "?"로 설정됩니다. .

    offset

    : 첫 번째 복사본은 -1로 설정되어 첫 번째 복사본을 나타내고 복사 진행률 오프셋을 기록합니다.

메인 라이브러리는 pync 명령을 받은 후

FULLRESYNC를 사용하여 두 개의 매개변수(메인 라이브러리 runID와 메인 라이브러리의 현재 복사 진행 오프셋)로 명령에 응답하고 이를 슬레이브에 반환합니다. 도서관

. 라이브러리로부터 응답을 받은 후 이 두 매개변수가 기록됩니다.

FULLRESYNC 응답은 첫 번째 복제에서 전체 복제

를 채택했음을 나타냅니다. 즉, 마스터 데이터베이스가 모든 현재 데이터를 슬레이브 데이터베이스에 복사합니다.

마스터 라이브러리는 데이터를 슬레이브 라이브러리에 동기화합니다. 🎜🎜두 번째 단계🎜🎜마스터는 bgsave 명령을 실행하여 RDB 파일을 생성하고 파일을 슬레이브 라이브러리로 보냅니다. 동시에 🎜메인 라이브러리🎜는 RDB 파일이 생성된 이후 수신된 모든 쓰기 명령을 기록하기 위해 각 슬레이브에 대한 복제 버퍼를 엽니다. 🎜🎜라이브러리에서 RDB 파일을 받은 후 디스크에 저장하고 현재 데이터베이스의 데이터를 지운 다음 RDB 파일 데이터를 메모리에 로드합니다. 🎜

슬레이브 라이브러리에 새 쓰기 명령 보내기🎜🎜세 번째 단계🎜🎜슬레이브 노드가 RDB를 로드한 후 마스터 노드는 복제 버퍼에 있는 데이터를 슬레이브에게 보냅니다. 이를 슬레이브가 수신하고 실행하면 슬레이브 노드는 마스터 노드와 동일한 상태로 동기화된다. 🎜🎜🎜65 형: 마스터 데이터베이스가 슬레이브 데이터베이스에 데이터를 동기화하면 정상적으로 요청을 받아들일 수 있나요? 🎜🎜🎜메인 데이터베이스는 차단되지 않습니다. 빠르고 깨지지 않는 사람으로서 Redis는 어떻게 매번 차단될 수 있습니까? 🎜🎜지금은 RDB 파일 생성 후 쓰기 작업이 RDB 파일에 기록되지 않습니다. 마스터-슬레이브 데이터베이스 데이터의 일관성을 보장하기 위해 마스터 데이터베이스는 메모리의 복제 버퍼를 사용하여 이후의 모든 쓰기를 기록합니다. RDB 파일이 생성됩니다. 🎜🎜🎜65 Brother: 라이브러리에서 RDB 파일을 받은 후 현재 데이터베이스를 지워야 하는 이유는 무엇입니까? 🎜🎜🎜슬레이브 라이브러리는 마스터와 슬레이브 데이터 간의 영향을 방지하기 위해 replcaof 명령을 통해 마스터 라이브러리와 동기화를 시작하기 전에 다른 데이터를 저장할 수 있기 때문입니다. 🎜🎜🎜복제 버퍼란 정확히 무엇인가요? 🎜🎜🎜마스터 측에 생성된 버퍼입니다. 저장되는 데이터는 다음 세 기간의 모든 마스터 데이터 쓰기 작업입니다. 🎜🎜1) 마스터가 RDB를 생성하기 위해 bgsave를 실행할 때의 쓰기 작업 🎜🎜2) 마스터가 네트워크 전송을 위해 RDB를 슬레이브에 보낼 때의 쓰기 작업 🎜🎜3) 슬레이브가 RDB를 로드할 때의 쓰기 작업 파일을 저장하고 데이터를 메모리에 복원합니다. 🎜🎜 Redis가 클라이언트와 통신하든 슬레이브 라이브러리와 통신하든 Redis는 데이터 상호 작용을 위해 메모리 버퍼를 할당하며, 각 클라이언트가 Redis에 연결된 후 슬레이브 라이브러리도 클라이언트입니다. 전용 클라이언트 버퍼를 할당하고 모든 데이터 상호 작용은 이 버퍼를 통해 수행됩니다. 🎜🎜마스터는 먼저 이 버퍼에 데이터를 쓴 다음 네트워크를 통해 전송하여 데이터 상호 작용을 완료합니다. 🎜

不管是主从在增量同步还是全量同步时,master 会为其分配一个 buffer ,只不过这个 buffer 专门用来传播写命令到从库,保证主从数据一致,我们通常把它叫做 replication buffer。

replication buffer 太小会引发的问题

replication buffer 由 client-output-buffer-limit slave 设置,当这个值太小会导致主从复制连接断开

1)当 master-slave 复制连接断开,master 会释放连接相关的数据。replication buffer 中的数据也就丢失了,此时主从之间重新开始复制过程。

2)还有个更严重的问题,主从复制连接断开,导致主从上出现重新执行 bgsave 和 rdb 重传操作无限循环。

当主节点数据量较大,或者主从节点之间网络延迟较大时,可能导致该缓冲区的大小超过了限制,此时主节点会断开与从节点之间的连接;

这种情况可能引起全量复制 -> replication buffer 溢出导致连接中断 -> 重连 -> 全量复制 -> replication buffer 缓冲区溢出导致连接中断……的循环。

具体详情:[top redis headaches for devops – replication buffer] 因而推荐把 replication buffer 的 hard/soft limit 设置成 512M。

config set client-output-buffer-limit "slave 536870912 536870912 0"复制代码
로그인 후 복사

65 哥:主从库复制为何不使用 AOF 呢?相比 RDB 来说,丢失的数据更少。

这个问题问的好,原因如下:

  • RDB 文件是二进制文件,网络传输 RDB 和写入磁盘的 IO 效率都要比 AOF 高。

  • 从库进行数据恢复的时候,RDB 的恢复效率也要高于 AOF。

增量复制

65 哥:主从库间的网络断了咋办?断开后要重新全量复制么?

在 Redis 2.8 之前,如果主从库在命令传播时出现了网络闪断,那么,从库就会和主库重新进行一次全量复制,开销非常大。

从 Redis 2.8 开始,网络断了之后,主从库会采用增量复制的方式继续同步。

增量复制:用于网络中断等情况后的复制,只将中断期间主节点执行的写命令发送给从节点,与全量复制相比更加高效

repl_backlog_buffer

断开重连增量复制的实现奥秘就是 repl_backlog_buffer 缓冲区,不管在什么时候 master 都会将写指令操作记录在 repl_backlog_buffer 中,因为内存有限, repl_backlog_buffer 是一个定长的环形数组,如果数组内容满了,就会从头开始覆盖前面的内容

master 使用 master_repl_offset记录自己写到的位置偏移量,slave 则使用 slave_repl_offset记录已经读取到的偏移量。

master 收到写操作,偏移量则会增加。从库持续执行同步的写指令后,在 repl_backlog_buffer 的已复制的偏移量 slave_repl_offset 也在不断增加。

正常情况下,这两个偏移量基本相等。在网络断连阶段,主库可能会收到新的写操作命令,所以 master_repl_offset会大于 slave_repl_offset

Redis의 마스터-슬레이브 아키텍처의 데이터 일관성 동기화 원칙에 대한 심층적인 이해

当主从断开重连后,slave 会先发送 psync 命令给 master,同时将自己的 runIDslave_repl_offset发送给 master。

master 只需要把 master_repl_offsetslave_repl_offset之间的命令同步给从库即可。

增量复制执行流程如下图:

Redis의 마스터-슬레이브 아키텍처의 데이터 일관성 동기화 원칙에 대한 심층적인 이해

65 哥:repl_backlog_buffer 太小的话从库还没读取到就被 Master 的新写操作覆盖了咋办?

我们要想办法避免这个情况,一旦被覆盖就会执行全量复制。我们可以调整 repl_backlog_size 这个参数用于控制缓冲区大小。计算公式:

repl_backlog_buffer = second * write_size_per_second复制代码
로그인 후 복사
  • second:从服务器断开重连主服务器所需的平均时间;

  • write_size_per_second:master 平均每秒产生的命令数据量大小(写命令和数据大小总和);

例如,如果主服务器平均每秒产生 1 MB 的写数据,而从服务器断线之后平均要 5 秒才能重新连接上主服务器,那么复制积压缓冲区的大小就不能低于 5 MB。

为了安全起见,可以将复制积压缓冲区的大小设为2 * second * write_size_per_second,这样可以保证绝大部分断线情况都能用部分重同步来处理。

基于长连接的命令传播

65 哥:完成全量同步后,正常运行过程如何同步呢?

当主从库完成了全量复制,它们之间就会一直维护一个网络连接,主库会通过这个连接将后续陆续收到的命令操作再同步给从库,这个过程也称为基于长连接的命令传播,使用长连接的目的就是避免频繁建立连接导致的开销。

在命令传播阶段,除了发送写命令,主从节点还维持着心跳机制:PING 和 REPLCONF ACK。

主->从:PING

每隔指定的时间,主节点会向从节点发送 PING 命令,这个 PING 命令的作用,主要是为了让从节点进行超时判断。

从->主:REPLCONF ACK

在命令传播阶段,从服务器默认会以每秒一次的频率,向主服务器发送命令:

REPLCONF ACK <replication_offset>复制代码</replication_offset>
로그인 후 복사

其中 replication_offset 是从服务器当前的复制偏移量。发送 REPLCONF ACK 命令对于主从服务器有三个作用:

  • 检测主从服务器的网络连接状态。

  • 辅助实现 min-slaves 选项。

  • 检测命令丢失, 从节点发送了自身的 slave_replication_offset,主节点会用自己的 master_replication_offset 对比,如果从节点数据缺失,主节点会从 repl_backlog_buffer缓冲区中找到并推送缺失的数据。注意,offset 和 repl_backlog_buffer 缓冲区,不仅可以用于部分复制,也可以用于处理命令丢失等情形;区别在于前者是在断线重连后进行的,而后者是在主从节点没有断线的情况下进行的。

如何确定执行全量同步还是部分同步?

在 Redis 2.8 及以后,从节点可以发送 psync 命令请求同步数据,此时根据主从节点当前状态的不同,同步方式可能是全量复制部分复制。本文以 Redis 2.8 及之后的版本为例。

关键就是 psync的执行:

Redis의 마스터-슬레이브 아키텍처의 데이터 일관성 동기화 원칙에 대한 심층적인 이해

  • 从节点根据当前状态,发送 psync命令给 master:

    • 如果从节点从未执行过 replicaof ,则从节点发送 psync ? -1,向主节点发送全量复制请求;
    • 如果从节点之前执行过 replicaof 则发送 psync <runid> <offset></offset></runid>, runID 是上次复制保存的主节点 runID,offset 是上次复制截至时从节点保存的复制偏移量。
  • 主节点根据接受到的psync命令和当前服务器状态,决定执行全量复制还是部分复制:

    • runID 与从节点发送的 runID 相同,且从节点发送的 slave_repl_offset 之后的数据在 repl_backlog_buffer 缓冲区中都存在,则回复 CONTINUE,表示将进行部分复制,从节点等待主节点发送其缺少的数据即可;
    • runID 与从节点发送的 runID 不同,或者从节点发送的 slave_repl_offset 之后的数据已不在主节点的 repl_backlog_buffer 缓冲区中 (在队列中被挤出了),则回复从节点 FULLRESYNC <runid> <offset></offset></runid>,表示要进行全量复制,其中 runID 表示主节点当前的 runID,offset 表示主节点当前的 offset,从节点保存这两个值,以备使用。

一个从库如果和主库断连时间过长,造成它在主库 repl_backlog_buffer 的 slave_repl_offset 位置上的数据已经被覆盖掉了,此时从库和主库间将进行全量复制。

总结下

每个从库会记录自己的 slave_repl_offset,每个从库的复制进度也不一定相同。

在和主库重连进行恢复时,从库会通过 psync 命令把自己记录的 slave_repl_offset 发给主库,主库会根据从库各自的复制进度,来决定这个从库可以进行增量复制,还是全量复制。

replication buffer 和 repl_backlog

  • 복제 버퍼는 각 슬레이브에 해당하며 config set client-output-buffer-limit 슬레이브를 통해 설정됩니다. config set client-output-buffer-limit slave 设置。

  • repl_backlog_buffer 是一个环形缓冲区,整个 master 进程中只会存在一个,所有的 slave 公用。repl_backlog 的大小通过 repl-backlog-size 参数设置,默认大小是 1M,其大小可以根据每秒产生的命令、(master 执行 rdb bgsave) +( master 发送 rdb 到 slave) + (slave load rdb 文件)时间之和来估算积压缓冲区的大小,repl-backlog-size 值不小于这两者的乘积。

总的来说,replication buffer 是主从库在进行全量复制时,主库上用于和从库连接的客户端的 buffer,而 repl_backlog_buffer 是为了支持从库增量复制,主库上用于持续保存写操作的一块专用 buffer。

repl_backlog_buffer 是一块专用 buffer,在 Redis 服务器启动后,开始一直接收写操作命令,这是所有从库共享的。主库和从库会各自记录自己的复制进度,所以,不同的从库在进行恢复时,会把自己的复制进度(slave_repl_offset

repl_backlog_buffer는 링 버퍼이며 전체 마스터 프로세스에 하나만 있으며 모든 슬레이브에 공통됩니다. repl_backlog의 크기는 repl-backlog-size 매개변수에 의해 설정됩니다. 기본 크기는 1M입니다. 크기는 초당 생성되는 명령을 기반으로 할 수 있습니다. (마스터가 rdb bgsave를 실행함) + (마스터가 슬레이브에 rdb를 전송함) rdb 파일 로드) 시간과 백로그 버퍼의 크기를 추정하기 위해 repl-backlog-size 값은 둘의 곱보다 작지 않습니다.

Redis의 마스터-슬레이브 아키텍처의 데이터 일관성 동기화 원칙에 대한 심층적인 이해

일반적으로 replication buffer는 마스터-슬레이브 라이브러리가 전체 복제를 수행할 때 슬레이브 라이브러리에 연결하기 위해 마스터 라이브러리의 클라이언트에서 사용하는 버퍼이고, repl_backlog_buffer code>는 슬레이브 라이브러리의 증분 복제를 지원하기 위해 쓰기 작업을 지속적으로 저장하는 데 사용되는 메인 라이브러리의 전용 버퍼입니다.

repl_backlog_buffer 는 Redis 서버가 시작된 후 쓰기 작업 명령을 받기 시작합니다. 이는 모든 슬레이브 라이브러리에서 공유됩니다. 마스터 라이브러리와 슬레이브 라이브러리는 각각 자체 복제 진행 상황을 기록합니다. 따라서 서로 다른 슬레이브 라이브러리가 복구될 때 자체 복제 진행 상황(slave_repl_offset)을 마스터 라이브러리와 마스터 라이브러리에 보냅니다. 마스터 라이브러리와 독립적으로 통신할 수 있습니다.

그림과 같습니다:

4. 마스터-슬레이브 응용 문제

4.1 읽기-쓰기 분리 문제

    데이터 만료 문제
  • 65 형제: 마스터-슬레이브 시나리오에서 복제하면 슬레이브 노드가 삭제됩니다. 만료된 데이터?
  • 좋은 질문입니다. 마스터 노드와 슬레이브 노드 간의 데이터 일관성을 위해 슬레이브 노드는 데이터를 적극적으로 삭제하지 않습니다. 우리는 Redis에 두 가지 삭제 전략이 있다는 것을 알고 있습니다.

지연 삭제: 클라이언트가 해당 데이터를 쿼리하면 Redis는 데이터가 만료되었는지 확인하고 만료되면 삭제합니다.

정기 삭제: Redis는 예약된 작업을 통해 만료된 데이터를 삭제합니다.

65 Brother: 클라이언트가 슬레이브 노드에서 데이터를 읽어 만료된 데이터를 읽나요?

Redis 3.2부터는 노드에서 데이터를 읽을 때 먼저 데이터가 만료되었는지 확인합니다. 만료된 경우 클라이언트에 반환되지 않으며 데이터가 삭제됩니다.

4.2 단일 머신 메모리 크기 제한

Redis 단일 머신 메모리가 10GB에 도달하면 슬레이브 노드의 동기화 시간은 몇 분이 되며, 슬레이브 노드가 더 많으면 복구 속도가 느려집니다. 시스템의 읽기 로드가 매우 높고 슬레이브 노드가 이 기간 동안 서비스를 제공할 수 없는 경우 시스템에 많은 부담을 주게 됩니다.
  • 데이터의 양이 너무 많으면 전체 복제 단계에서 마스터 노드가 RDB 파일을 포크하고 저장하는 데 너무 많은 시간이 걸립니다. 슬레이브 노드는 오랫동안 데이터를 수신할 수 없으며 데이터 타임아웃이 발생합니다. 마스터 노드와 슬레이브 노드 간의 동기화도

    전체 복제->타임아웃에 빠질 수 있습니다. 복제 중단->재연결->전체 복제->타임아웃이 발생하는 주기로 인해 복제 중단이 발생합니다

  • 또한, 마스터 노드의 독립형 메모리의 절대량은 너무 커서는 안 되고, 호스트 메모리가 차지하는 비율도 너무 커서는 안 됩니다. 50%~65%만 사용하는 것이 가장 좋습니다. bgsave 명령 실행 및 복사 버퍼 생성 등을 위해 메모리의 30% - 45%를 남겨둡니다.

    요약
  • 마스터-슬레이브 복제의 역할: AOF 및 RDB 바이너리 파일은 다운타임 시 데이터를 빠르게 복구하고 데이터 손실을 최대한 방지합니다. 그러나 다운타임 이후에도 여전히 서비스를 제공할 수 없었기 때문에 마스터-슬레이브 아키텍처와 읽기-쓰기 분리가 발전했습니다.

마스터-슬레이브 복제 원리: 연결 설정 단계, 데이터 동기화 단계, 명령 전파 단계 데이터 동기화 단계는 명령 전파 단계에서 전체 복제와 부분 복제로 구분되며, 두 단계 사이에는 PING 및 REPLCONF ACK 명령이 있습니다. 마스터 및 슬레이브 노드가 서로 감지할 때 하트비트를 수행합니다.

마스터-슬레이브 복제는 데이터 중복성, 오류 복구, 읽기 로드 밸런싱과 같은 문제를 해결하거나 완화하지만 그 결함은 여전히 ​​명백합니다.

오류 복구는 쓰기 작업을 자동화할 수 없으며 스토리지 용량이 제한됩니다. 이러한 문제를 해결하려면 센티넬과 클러스터
의 도움이 필요합니다. 이에 대해서는 후속 기사에서 소개하겠습니다.

🎜원본 주소: https://juejin.cn/post/6973928120332058654🎜🎜저자: Code Brother Byte🎜🎜🎜더 많은 프로그래밍 관련 지식을 보려면 🎜프로그래밍 비디오🎜를 방문하세요! ! 🎜

위 내용은 Redis의 마스터-슬레이브 아키텍처의 데이터 일관성 동기화 원칙에 대한 심층적인 이해의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

관련 라벨:
원천:juejin.cn
본 웹사이트의 성명
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.
인기 튜토리얼
더>
최신 다운로드
더>
웹 효과
웹사이트 소스 코드
웹사이트 자료
프론트엔드 템플릿