PolarDB 卷来卷去 云原生低延迟强一致性读 1 (SCC READ 译 )

开头还是介绍一下群,如果感兴趣PolarDB ,MongoDB ,MySQL ,PostgreSQL ,Redis, Oceanbase, Sql Server等有问题,有需求都可以加群群内有各大数据库行业大咖,CTO,可以解决你的问题。加群请联系 liuaustin3 ,在新加的朋友会分到2群(共1620人左右 1 + 2 + 3 + 4) 3群突破 490已关闭自由申请如需加入请提前说明,新人会进4群(200),另欢迎 OpenGauss 的技术人员加如入。

e9701899ac47544b4a26c94e4971e41e.png

每人感悟,感悟每日,明白道理的人很多,但还是过不好这一辈子的根本的,你明白的道理可能仅仅是看了一眼道理,就告诉自己你明白了,或者你明白了但是那个道理不是道理。

事情是这样的,在我们的MySQL 被 POLARDB 打败了后,我们遇到一个问题,就是强一致读的问题,在一个特殊的应用中,在大批量写后,需要立即进行数据的读,之前在MySQL都是打到主库,但基于想利用PolarDB的double 节点,总不能还强制将读都指定到写节点,所以我们采用了原有的方案,但是发现在大量的写后去马上读的中应用给出的延迟在20ms,也就是在大量UPDATE 几百万的数据后,从库的数据延迟应该在20ms内。虽然我们也解决了这个问题,但是实际上POLARDB 还有一个新的功能我们没有用到,POLARDB-SCC 。

本着卷不死,就往死里卷的态度,今天的继续学习POLARDB-SCC,虽然此时脑子已经给我提示你累了需要休息,下面为白皮书PolarDB-SCC: A Cloud-Native Database Ensuring Low latency for  Strongly Consistent Reads

————————————————————————————

常见的云原生数据库设计中大多采用了一个由读写节点为基本单元的组成架构,在这样的设计中,RW- RO节点的数据通过预写日志(REDO)来进行数据的复制,所以应用的设计人员必须接受一个事实,读写节点之间的数据有延迟,或者将应用程序对于数据库的要求降低,因为数据的传播需要传输和应用,如Aurora 选择了性能而不是强一致,所以对于读写一致性要求的应用,从库都是多余的,哪怕你能进行无限的横向扩展。

本文提出了PolarDB-SCC,(polardb 强一致集群),这是一种云原生的数据库架构,具有非常低的延迟和强一致的数据读取性,核心思想是消除不必要的等待,减少在RO读节点需要等待数据应用在RO节点上的时间,简单的说在三个部分进行了优化, 1 时间戳线性减少时间戳获取的操作的消耗,2 最小化网络开销和CPU 的额外使用  3  使用高速RDMA网络进行数据传输。在实现POLARDB-SCC中我们尽量保证不会产生额外的硬件消耗,做到忽略强一致性带来的硬件消耗的数据库产品。

我们对比其他产品如Aurora, Hyperscale, Socrates , Polardb等,其中这些数据库采用了分散共享存储架构,通常来说就是一个主节点,以及多个从节点,为保持RO节点缓冲数据的最新,RW节点为每个更新生成了相关的日志,并将日志传输给RO,RO节点应用日志来更新其缓冲数据,由于日志应用过程是异步的,RO节点应用日志来更新其缓冲数据,而虽然大多数数据库都提出从节点可以提供读服务,但由于从节点无法提供最新的写节点上的数据,而导致从节点没有被有效的利用。

3372817a51c2b1f5472f5ae190b5b0f8.png

上图中在开启和关闭SCC功能的基础上,在RW节点写入数据,并在从节点立即读取,从上面的显示可以看出只有SCC 功能开启的PolarDB 可以支持RW,RO读写一致性。基于许多应用程序,强一致读中的严格一致性的要求,如果不能保证一致性已经下单的用户会发现订单不存在或支付未显示而产生业务错误的问题,对于强一致的要求在一些应用程序是有体现的。出现这样情况的场景还有可能是微服务,多个微服务共享数据的场景,这样的场景多见于保险公司和金融,支付类的公司。

6a941a1229a382cd16a2ba5b7edb6750.png

当今很多云原生的数据库中,为了支持强一致,应用程序必须将所有的读请求都发到RW节点,无法通过添加RO节点来分散读请求的压力,RW节点就成为整个系统的瓶颈,严重的限制了系统读处理操作中工作负载均衡的能力,实际上很多应用程序都已读作为主要的压力所在,所以在云原生的数据库集群中确保强一致的读取,提高系统的性能是系统真正可扩展是我们要做的。

这里有两种直接设计方案,可以支持RO节点上一致性读取,1 commitwait ,2 readwait,这里两种方案,方案1 需要进行实物COMMIT时等待数据传输到从节点 而方案2 需要读请求等待读节点接受到主节点的时间戳并确认数据事务执行后,在反馈。这两种方案都是以性能作为牺牲而达到的最终一致性。这里我们进行了比较,在开启SCC后RO节点延迟在3.8%,而其他的情况延迟在126% 到128% ,其他的方案中通过使用高速网络RDMA 加速日志传输,或在RO节点更快应用日志,如query fresh,但这样为只能保证最终一致性无法保证强一致。

903a9159de496a19a297084c7ac1aa16.png

许多现有的系统以来与流式日志传输,并在RO节点上线性应用日志,并使用了特定的时间戳来标志事务的时间,RO节点在日志应用到特定的时间戳之前无法进行强一致的读,因为RO节点无法获知数据页面是否更改,在不知道前需要进行等待。

针对这些问题,本篇POLARDB-SCC (POLARDB 强一致集群),可以保证RO节点上进行强一致的读取和低延迟,POLARDB-SCC 基于等待策略设计但消除了读等待中的开销,最小化在从库中读的的等待时间,或者说最小化日志应用的等待时间,我们提出了层次化修改的跟踪思路,在多个层次上如全局,表,页面等各个级别上跟踪RW节点的修改,通过这样的方案当全局时间戳不满足要求的情况下,在RO节点可以做细粒度级别的等待日志应用的做法,减少了应用日志等待的时间。避免等待内存数据完全更新的做法中的缺陷,在RO节点上线性的lamport时间戳,避免频繁的从RW 节点获取时间戳,显著降低了网络和通信的开销,利用快速时间戳,进行日志的传输和时间戳的获取,从而消除了RW节点处理时间戳获取请求和传输日志的CPU开销。

基于这些设计,POLARDB-SCC 在RO节点上实现了低延迟和强一致性读取,为应用程序提供了具有强一致性的保证的代理端点,并以负载均衡的方式将读请求发送给RO节点,通过动态的增加RO节点来实现读写分离的弹性需求,因为他允许系统根据应用程序负载透明地动态增加或减少RO节点的数量,同时PolarDB-SCC在不修改数据库内部数据结构也不依赖特定数据库内部数据结构的基础上很容易在不同的数据库上进行实现。

(跳出翻译,这里简单解释一下什么是 lamport 时间戳)

Lamport时间戳是一种用于逻辑时钟的算法,由Leslie Lamport在1978年提出。它主要用于在分布式系统中对事件顺序进行全局排序。

Lamport时间戳由整数值组成,每个进程都维护一个本地计数器。当一个进程执行一个事件时,它会将本地计数器的值赋给该事件的时间戳,并将本地计数器递增。由于时间戳是由本地计数器确定的,因此每个进程的时间戳会随着事件的执行而递增。

Lamport时间戳遵循以下两个规则:

  1. 如果事件A在事件B之前发生,那么A的时间戳应该小于B的时间戳。

  2. 如果事件A和事件B在同一个进程中发生,并且A在B之前,那么A的时间戳应该小于B的时间戳。

这里跳过一部分英文的内容,对于POLARDB的介绍(SCC是一个独立的文章,这里因为怕读SCC的同学不知道POLARDB的一些内容所以对POLARDB 重复介绍,就这里一并略过,有要获知POALRDB的部分可以参见以前的多篇翻译文章)。

Polardb-SCC 概述

设计原理,PolarDB-SCC 提供低延迟强一致的云原生数据库,只读RO节点始终能返回数据,对于在RW节点上应用的事务在RO上读取应用最小化的等待时间。在RO节点上使用能返回比访问数据时更早的RW上应用的数据,下图是具体的POLARDB-SCC的简易架构图,它包括一个主(RW)节点,一个或多个辅助(RO)节点,以及一个位于RW和RO节点之上的代理节点。RW节点可以同时处理读和写请求,而RO节点只响应读请求。代理节点通过将读请求分发到RO节点并将写请求转发到RW节点,实现透明的负载均衡和高可用性。如果当前的RW节点发生故障,代理节点将升级其中一个RO节点为新的RW节点。代理节点通常有多个成员(通常为2个)以提供高可用性和高性能。RW和RO节点共享分离的云存储,类似于许多云原生数据库。RW和RO节点通过基于RDMA的网络连接,实现快速日志传输和时间戳获取。

0d7a6e5721df95ab31fd269295b1eb99.png

PolarDB-SCC的核心组件是分层修改跟踪器、线性Lamport时间戳和基于RDMA的日志传输协议。分层修改跟踪器维护了RW节点的三个级别的修改发,在工作中,RO节点先检查RW节点的全局级别的时间戳,然后检查表和页面级别的时间戳,一旦满足某个级别的要求,直接处理请求,无序检查下一个级别,如果也级别也无法满足的情况下,会需要等待请求也的日志应用来进行读操作。

这里最新的修改时间戳在RW节点上维护,RO节点必须为每个请求从RW 节点获取时间戳,虽然RDMA网络的速度很快,但如果RO节点负载过重,仍然会有很大的开销,为客服时间戳获取的开销,则使用Lamport时间戳,RO节点从RW 节点获取时间戳后,将其存储在本地,人和早于时间戳的请求到达RO节点直接使用本地的时间戳,不需要在从RW节点获取新的时间戳,RO 节点负载重时,这样节省了获取的时间和消耗,减少网络开销,我们采用了一边式的RDMA来进行日志的传输和时间戳的获取,将RW节点的日志写入RO节点,节省了RDMA远程写入的CPU周期。

线性Lamport时间戳:为提供强一致读操作,读请求需要能看到在主库已经提交的所有事务的数据,在 PolarDB-SCC 中只有RW节点能够更新数据,因此RW节点充当时间戳产生的角色,RO 节点在必须获取RW节点最新的时间戳并等待日志应用后在处理请求,如果RO节点负载很重,会有许多并发的时间戳的获取请求在RW节点上,这会对性能产生负面的影响,同时RO获取时间戳给RO本身也带来额外的开销,为避免并发获取时间戳的行为,POLARDB-SCC设计了一次从RW节点获取时间戳,批量为RO节点提供时间戳服务。

这解决了读等待的问题,传统的解决方案中每个RO读都要获取RW的时间戳,一个请求是否可以读取到数据的决定在于时间戳,这里新的方式为如果一个请求发现在到达时间之后已经有了其他的请求获取了时间戳的情况下,可以直接重新利用该时间戳,无需在获取新的时间戳,同时这样的方案仍然可以满足强一致性。见下图 RO 节点有一个请求

05614dff12df2344389f6abe1663ca28.png

这里我们有两个读库的访问 R1 R2, 当R2 访问数据时请求了时间戳,并在T3 获得结果 TS3RW,这里R1 和 R2 在同一个RO 节点,这里有另一个访问的需求 R1 ,如果R1 对数据进行访问,根据本地时间戳原理,我们可以推测出 E1  E2 都可以采用 TS3RW作为时间戳,根据这个原理可以推出只要,在E3后如果在获取时间戳就需要在次进行获取,而在T3前的都可以使用TS3RW来进行,当在之后的数据访问,会明确之前的获取的时间戳是无效的,需要重新等待新的时间戳到来后,才能继续对读库进行访问,这样的设计就是为了在高并发的数据访问中,可以尽量少的对写库获取时间戳,而尽量复用时间戳的方式来访问读库。

基于这样的理论,我们将RW的时间戳CACHE到RO节点,来进行复用增加POLARDB-SCC在符合条件下的时间戳复用它,为了在Polardb-scc 中实现这一点,每当一个RO节点获取RW节点的时间戳,他会将该时间戳与获取操作的起始时间的时间戳用组合的方式来进行保存,通过这样的设计满足当一个RO节点上请求需要RW节点的时间戳,他将检测RO节点上的元组,如果请求达到时间早于时间戳则可以利用本地的缓存,否则就需要刷新缓存确保读的一致性。这样的方法就减少部分读在获取时间戳比对的时间。

对于可重复的读以及更高隔离级别的事务,事务开始时仅仅一次获取RW节点的时间戳,事务中的所有请求都将使用此时间戳进行强一致读,随后到达RO节点的事务与时间戳比较,检查对于事务强一致读取来说缓存的数据是否是有效的。

待.......

106a4b8aa4f24d0869ed7d6fb9644ee5.png

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/184296.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

python使用pysqlcipher3对sqlite数据库进行加密

python对很多项目都需要对sqlite数据库的数据进行加密,最流行的加密方式是使用pysqlcipher3,当前使用的python版本为3.7,本博文是直接使用pysqlcipher3在项目上的应用,使用的是已编译好的pysqlcipher3包,如果你需要pys…

很多个pdf怎么合并在一起?

很多个pdf怎么合并在一起?作为一个办公室的伙伴,对于PDF格式肯定不会陌生。它强大的功能为我们的工作提供了许多便利。由于PDF文件格式的稳定性和安全性较高,我们通常在工作或学习中使用它来传输文件,很多人都喜欢将办公文件都做成…

【electron】【附排查清单】记录一次逆向过程中,fetch无法请求http的疑难杂症(net::ERR_BLOCKED_BY_CLIENT)

▒ 目录 ▒ 🛫 导读需求开发环境 1️⃣ Adblock等插件拦截2️⃣ 【失败】Content-Security-Policy启动服务器json-serverhtml中的meta字段 3️⃣ 【失败】https vs httpwebPreferences & allowRunningInsecureContent disable-features 4️⃣ 【失败】检测fetch…

Django快速指南

开始构建 Web 应用程序不仅需要对编码和设计原则有深入的了解,还需要对安全性和性能坚定不移的承诺。在数字化存在至关重要的时代,构建强大而高效的在线平台的能力是一项具有不可估量价值的技能。本教程专门面向网络工匠,即那些希望将技术线索…

【Git】Git 学习笔记_操作远程仓库

1. SSH 配置和克隆仓库 ssh-keygen -t rsa -C "xxxqq.com"回车后出现以下内容,直接回车: Generating public/private rsa key pair. Enter file in which to save the key (/Users/your_user_directory/.ssh/id_rsa): (按回车键) Enter pass…

干洗店洗鞋店管理系统app小程序;

干洗店洗鞋店管理系统是一款专业的洗衣店管理软件,集成了前台收费收银系统、会员卡管理系统和财务报表系统等强大功能。界面简洁优美,操作直观简单。这款系统为干洗店和洗衣店提供了成本分析、利润分析、洗衣流程管理等诸多实用功能,用全新的…

全方位监控基础设施,坚实守护您的业务稳定!

前言 基础设施服务是产业数字化转型建设的重要组成部分之一。当我们反复讨论如何实现高效、精确的全局监控,也许能从观测云借助一套方案来探索、检查和监控分布式基础架构中的每个关键部分这一操作中习得一些灵感。 在针对企业的平台中内嵌实时的基础设施监控工具…

An error occurred while filtering resources

Description Path Resource Location Type An error occurred while filtering resources PMS line 1 Maven Java EE Configuration Problem不知道怎么跑出来了,update project 还是不行

MS35229电机驱动器可兼容DRV8833

MS35229N/MS35229TE 是一款 12V 静音步进电机驱动芯片,工作电压最大可以工作到 15V,输出 RMS 电流1A。芯片内置 256 细分的微步进驱动技术,静音与低振动特性适合于各种精微控制系统。 芯片集成通用的 IC 接口以及内部指令缓存器,使…

linux之进程控制

进程创建&fork函数 fork函数之前就已经提到,它从已存在进程中创建一个新进程,新进程为子进程,而原进程为父进程。 调用接口:fork() 头文件:unistd.h 功能:创建一个子进程,给子进程返回0,父进程返回子进程pid …

C语言 指针进阶

目录 数组指针 指针数组访问数组元素 再次讨论数组名 数组指针访问一维数组(但是这样会很别扭) 访问二维数组元素 非数组指针访问 数组指针访问 数组传参Demo 一维数组传参 二维数组传参 指针数组指针 字符指针 函数指针 函数指针调用时可以…

秒懂!用这10款思维导图软件,让头脑风暴如虎添翼!

世界上最糟糕的感觉之一就是忘记了一个伟大的点子。原本你只需把它记下来,但你当时确信自己绝不会忘记如此引人入胜的事物。然而,当这个想法从你的脑海彻底消失时,分分钟会让人崩溃。 如果你的想法有很多组成部分,比如一个大项目…

ARMday02(汇编语法、汇编指令)

汇编语法 汇编文件中的内容 1.伪操作:在汇编程序中不占用存储空间,但是可以在程序编译时起到引导和标识作用 .text .global .glbal .if .else .endif .data .word.... 2.汇编指令:每一条汇编指令都用来标识一个机器码,让计算机做…

深度学习之基于YoloV5的火灾检测系统

欢迎大家点赞、收藏、关注、评论啦 ,由于篇幅有限,只展示了部分核心代码。 文章目录 一项目简介 二、功能三、系统四. 总结 一项目简介 火灾检测系统基于YoloV5的介绍 火灾检测是一项重要的安全任务,它旨在及时发现和报警火灾风险。基于深度…

MyBatis-plus超神用法--一文带你玩转MP

前言 MyBatis-Plus是一个基于MyBatis的增强工具,提供了很多便捷的功能和增强的功能,以下是一些MyBatis-Plus的超神用法: 通用Mapper:MyBatis-Plus提供了通用Mapper的功能,可以通过继承BaseMapper接口,实现…

Gradle笔记 四 Gradle的核心 TASK

文章目录 Task任务入门任务的行为任务的依赖方式任务执行常见的任务(*)项目报告相关任务调试相关选项性能选项守护进程选项日志选项其它(*) 任务定义方式任务类型任务的执行顺序动态分配任务任务的关闭与开启任务的超时任务的查找任务的规则任务的 onlyI…

【RabbitMQ】常用消息模型详解

文章目录 AMQP协议的回顾RabbitMQ支持的消息模型第一种模型(直连)开发生产者开发消费者生产者、消费者开发优化API参数细节 第二种模型(work quene)开发生产者开发消费者消息自动确认机制 第三种模型(fanout)开发生产者开发消费者 第四种模型(Routing)开发生产者开发消费者 第五…

3.2-Docker Image概述

常用docker命令: 查看docker image有哪些 docker image ls Image的获取方式

docker 安装 minio (单体架构)

文字归档:https://www.yuque.com/u27599042/coding_star/qcsmgom7basm6y64 查询 minio 镜像 docker search minio拉取镜像 docker pull minio/minio创建启动 minio 容器 用户名长度至少为 3,密码长度至少为 8 docker run \ -p 9000:9000 \ -p 9090:909…

51单片机-中断

文章目录 前言 前言 #include <reg52.h> #include <intrins.h>sbit key_s2P3^0; sbit flagP3^7;void delay(unsigned int z){unsigned int x,y;for(xz;x>0;x--)for(y114;y>0;y--); }void int_init(){EA1;EX11;IT11;}void main(){int_init();while(1){if (key…