阿里云-云小站(无限量代金券发放中)
【腾讯云】云服务器、云数据库、COS、CDN、短信等热卖云产品特惠抢购

Heartbeat基础知识详细总结

230次阅读
没有评论

共计 10427 个字符,预计需要花费 27 分钟才能阅读完成。

在日常的集群系统架构中,一般用到 Heartbeat 的主要就 2 种:
1)高可用 (High Availability)HA 集群, 使用 Heartbeat 实现,也称为”双机热备”,“双机互备”,“双机”;
2)负载均衡群集(Load Balance Cluster),使用 Linux Virtual Server(LVS) 实现;

Heartbeat 的介绍
Heartbeat 是 Linux-HA 项目中的一个组件,它实现了一个高可用集群系统。 心跳服务和集群通信是高可用集群的两个关键组件,在 Heartbeat 项目里,由 heartbeat 模块实现了这两个功能 。Heartbeat 是目前开源 HA 项目中十分成功的一个例子,它提供了所有 HA 软件所需要的基本功能,比如 心跳检测和资源接管、监测群集中的系统服务、在群集中的节点间转移共享 IP 地址的所有者 等,自 1999 年开始到现在,Heartbeat 在行业内得到了广泛的应用。heartbeat 最核心的功能包括两个部分,心跳监测和资源接管。心跳监测可以通过网络链路和串口进行,而且支持冗 余链路,它们之间相互发送报文来告诉对方自己当前的状态,如果在指定的时间内未收到对方发送的报文,那么就认为对方失效,这时需启动资源接管模块来接管运行在对方主机上的资源或者服务。

Hearbeat 和 Keepalived 区别
1) Keepalived 使用的 VRRP 协议方式,虚拟路由冗余协议 (Virtual Router Redundancy Protocol,简称 VRRP);
2) Heartbeat 是基于主机或网络的服务的高可用方式;
3) Keepalived 的目的是模拟路由器的双机;
4) Heartbeat 的目的是用户 Service 的双机;
5) LVS 的高可用建议用 Keepavlived;
6) 业务的高可用用 Heartbeat;

Keepalived 主要控制 IP 飘移,配置应用简单,而且分层,layer3,4,5,各自配置极为简单
Heartbeat 不但可以控制 IP 飘移,更擅长对资源服务的控制,配置,应用比较复杂;

HA 集群中的相关术语

.节点(node)
运行 heartbeat 进程的一个独立主机,称为节点,节点是 HA 的核心组成部分,每个节点上运行着操作系统和 heartbeat 软件服务,在 heartbeat 集群中,节点有主次之分,分别称为主节点和备用 / 备份节点,每个节点拥有唯一的主机名,并且拥有属于自己的一组资源,例如,磁盘、文件系统、网络地址和应用服务等。主节点上一般运行着一个或多个应用服务。而备用节点一般处于监控状态。

.资源(resource)
资源是一个节点可以控制的实体,并且当节点发生故障时,这些资源能够被其它节点接管,heartbeat 中,可以当做资源的实体有:
–  磁盘分区、文件系统
–  IP 地址
–  应用程序服务
–  NFS 文件系统

.事件(event)
集群中可能发生的事情,例如节点系统故障、网络连通故障、网卡故障、应用程序故障等。这些事件都会导致节点的资源发生转移,HA 的测试也是基于这些事件来进行的。

.动作(action)
 事件发生时 HA 的响应方式,动作是由 shell 脚步控制的,例如当某个节点发生故障后,备份节点将通过事先设定好的执行脚本进行服务关闭或启动, 进而接管故障节点的资源。

HeartBeat 的组成

Heartbeat 提供了高可用集群最基本的功能,例如,节点间的内部通信方式、集群合作管理机制、监控工具和失效切换功能等等,目前的最新版本是 Heartbeat2.x,下面讲述也是以 Heartbeat2.x 为主,主要介绍 Heartbeat2.0 的内部组成,主要分为以下几大部分:
heartbeat:节点间通信检测模块
ha-logd:集群事件日志服务
CCM(Consensus Cluster Membership):集群成员一致性管理模块
LRM(Local Resource Manager):本地资源管理模块
Stonith Daemon:使出现问题的节点从集群环境中脱离
CRM(Cluster resource management):集群资源管理模块
Cluster policy engine:集群策略引擎
Cluster transition engine:集群转移引擎

   下图显示的是 Heartbeat2.0 内部结构组成

Heartbeat 基础知识详细总结

Heartbeat 仅仅是个 HA 软件,它仅能完成心跳监控和资源接管,不会监视它控制的资源或应用程序,要监控资源和应用程序是否运行正常,必须使用第三方的插件,例如 ipfail、Mon、Ldirector 等Heartbeat 自身包含了几个插件,分别是 ipfail、Stonith 和 Ldirectord,介绍如下:

ipfail 插件 的功能直接包含在 Heartbeat 里面,主要用于检测网络故障,并作出合理的反应,为了实现这个功能,ipfail 使用 ping 节点或者 ping 节点组来检测网络连接是否出现故障,从而及时的做出转移措施。

Stonith插件 可以在一个没有响应的节点恢复后,合理接管集群服务资源,防止数据冲突,当一个节点失效后,会从集群中删除,如果不使用 Stonith 插件,那么失效的节点可能会导致集群服务在多于一个节点运行,从而造成数据冲突甚至是系统崩溃。因此,使用 Stonith 插件可以保证共享存储环境中的数据完整性。

Ldirector 插件 是一个监控集群服务节点运行状态的插件。Ldirector 如果监控到集群节点中某个服务出现故障,就屏蔽此节点的对外连接功能,同时将后续请求转移到正常的节点提供服务,这个插件经常用在 LVS 负载均衡集群中,关于 Ldirector 插件的使用,将在后面详细讲述。

同样,对于操作系统自身出现的问题,Heartbeat 也无法监控,如果主节点操作系统挂起,一方面可能导致服务中断,另一方面由于主节点资源无法释放,而备份节点却接管了主节点的资源,此时就 发生了两个节点同时争用一个资源的状况 针对这个问题,就需要在 linux 内核中启用一个叫 watchdog 的模块,watchdog 是一个 Linux 内核模块,它通过定时向 /dev/watchdog 设备文件执行写操作,从而确定系统是否正常运行,如果 watchdog 认为内核挂起,就会重新启动系统,进而释放节点资源。

在 linux 中完成 watchdog 功能的软件叫 softdog,softdog 维护一个内部计时器,此计时器在一个进程写入 /dev/watchdog 设备文件时更新,如果 softdog 没有看到进程写入 /dev/watchdog 文件,就认为内核可能出了故障。watchdog 超时周期默认是一分钟,可以通过将 watchdog 集成到 Heartbeat 中,从而通过 Heartbeat 来监控系统是否正常运行。

HeartBeat 的作用
通过 HeartBeat,可以将资源(IP 以及程序服务等资源)从一台已经故障的计算机快速转移到另一台正常运转的机器上继续提供服务,一般称之为高可用的服务。在实际的生产应用场景中,heartbeat 的功能和另一个高可用的开源软件 keepalived 有很多的相同之处,在我们实际的生产业务中也是有区别的。

HeartBeat 的工作原理
heartbeat 最核心的包括两个部分,心跳监测部分和资源接管部分,心跳监测可以通过网络链路和串口进行,而且支持冗 余链路,它们之间相互发送报文来告诉对方自己当前的状态,如果在指定的时间内未收到对方发送的报文,那么就认为对方失效,这时需启动资源接管模块来接管运行在对方主机上的资源或者服务。

Heartbeat: (心跳检测)本身是整个集群的基础(cluster messaging layer),负责维护集群各节点的信息以及它们之前通信;只提供主从备份功能,并不能对各个节点进行监控,需要安装 ldirectord。
Resource-agent: (资源代理)就是各种的资源的 ocf 脚本,这些脚本将被 LRM 调用从而实现各种资源启动、停止、监控等等。
Cluster-glue: 相当于一个中间层,可以将 heartbeat 和 crm(pacemaker)联系起来,主要包含 2 个部分,LRM 和 STONITH;
Ldirectord: 负责 realserver 的健康检查,可以自动将 realserver 中宕机的机器移除,不再分配请求。

通过修改 Heartbeat 的软件的配置文件,可以制定那一台 Heartbeat 服务器作为主服务器,则另一台将自动成为热备服务器。然后在热备服务器上配置 Heartbeat 守护程序来监听来自主服务器的心跳消息。如果热备服务器在指定时间内为监听到来自主服务器的心跳,就会启动故障转义程序,并取得主服务器上的相关资源服务的所有权,接替主服务器继续不间断的提供服务,从而达到资源以及服务高可用的目的。

以上的描述 heartbeat 的主备模式,heartbeat 还支持主主模式,即两台服务器互为主备,这是他们之间还会互相发送报文来告诉对方自己的当前的状态,如果在指定的时间内未收到对方发送的心跳报文,那么,一方就会认为对方失效或者是已经宕机了,这时每个运行正常的主机就会启动自身的资源接管模块来接管运行在对方主机上的资源或者是服务,继续为用户提供服务。一般情况下,可以较好的实现一台主机故障后,企业业务能够不间断的持续的提供服务(注意:所谓的业务不间断)。在故障转移期间也是需要切换时间的,heartbeat 的切换时间是 5 -20 秒。(服务器宕机的切换比人工切换要快).

另外,和keepalived 高可用软件一样,heartbeat 高可用是操作系统级别的,不是服务(软件)级别的,可以通过简单的脚本控制,实现服务级别的高可用! 

故障切换的常见条件:
1)主机服务器物理宕机(硬件损坏,操作系统故障)
2)Heartbeat 服务本身故障
3)两台主备服务器之间的连接线路故障
应用服务故障则不会产生切换,可以通过服务宕机把 heartbeat 服务停掉。

heartbeat 内部结构有三大部分组成
集群成员一致性管理模块(CCM用于管理集群节点成员,同时管理成员之间的关系和节点间资源的分配,heartbeat 模块负责检测主次节点的运行状态,以决定节点是否失效。ha-logd 模块用于记录集群中所有模块和服务的运行信息。

本地资源管理器(LRM)负责本地资源的启动,停止和监控,一般由 LRM 守护进程 lrmd 和节点监控进程(Stonith Daemon)组成,lrmd 守护进程负责节点间的通信,Stonith Daemon 通常是一个 Fence 设备,主要用于监控节点状态,当一个节点出现问题时处于正常状态的节点会通过 Fence 设备将其重启或关机以释放 IP、磁盘等资源,始终保持资源被一个节点拥有,防止资源争用的发生。

集群资源管理模块(CRM)用于处理节点和资源之间的依赖关系,同时,管理节点对资源的使用,一般由 CRM 守护进程 crmd、集群策略引擎和集群转移引擎三个部分组成,集群策略引擎(Cluster policy engine)具体实施这些管理和依赖,集群转移引擎(Cluster transition engine)监控 CRM 模块的状态,当一个节点出现故障时,负责协调另一个节点上的进程进行合理的资源接管。

在 Heartbeat 集群中,最核心的是 heartbeat 模块的心跳监测部分和集群资源管理模块的资源接管部分,心跳监测一般由串行接口通过串口线来实现,两个节点之间通过串口线相互发送报文来告诉对方自己当前的状态,如果在指定时间内未收到对方发送的报文,则就认为对方失效,这时资源接管模块将启动,用来接管运行在对方主机上的资源或者服务。

HeartBeat 的心跳连接
高可用集群是指一组通过硬件和软件连接起来的独立计算机,它们在用户面前表现为一个单一系统,在这样的一组计算机系统内部的一个或者多个节点停止工作,服务会从故障节点切换到正常工作的节点上运行,不会引起服务中断。从这个定义可以看出,集群必须检测节点和服务何时失效,何时恢复为可用。这个任务通常由一组被称为“心跳”的代码完成。在 Linux-HA 里这个功能由一个叫做 heartbeat 的程序完成。
通过上面的描述,要部署 heartbeat 服务,至少需要两台主机才能完成。那么,要实现高可用服务,这两台主机之间,是如何做到互相通信互相监控的呢?
下面是 两台 heartbeat 主机之间通信的一些常用的可行方法
1)串行电缆,即所谓的串口(首选,缺点是距离不能太远)
2)一根以太网电缆量网口直连(生产环境中常用的方式)
3)以太网电缆,通过交换机等网络设备连接(次选,原因是增加了故障点,不好排查故障,同时线路不是专用的心跳线,容易受其他数据传输的影响,导致心跳报文发送问题)

Heartbeat 的裂脑
什么是裂脑?
由于两台高可用服务器之间在指定的时间内,无法互相检测到对方心跳而各自启动故障转移功能,取得了资源以及服务的所有权,而此时的两台高可用服务器对都还活着并作正常运行,这样就会导致同一个 IP 湖综合服务在两端同时启动而发生冲突的严重问题,最严重的就是两台主机同时占用一个 VIP 的地址,当用户写入数据的时候可能会分别写入到两端,这样可能会导致服务器两端的数据不一致或造成数据的丢失,这种情况就本成为裂脑,也有的人称之为分区集群或者大脑垂直分隔!

简单来说,Hearbeat 脑裂说的就是 两台服务都正常,但是就是检测不到对方的心跳信息(心跳通信出现故障),两台 heartbeat 都绑定 VIP,这就是脑裂,由于相互失去联系,两台服务器本能的争取接管资源,最严重的后果:共享资源被瓜分,服务都起不起来了,又或者服务都起来,但是共享资源同时写,最后数据就被破坏了!

导致裂脑发生的原因:
一般来说,裂脑的发生,主要是由以下的几个原因导致的:
1)高可用服务器对之间心跳线路故障,导致无法正常的通信。原因比如:
    1– 心跳线本身就坏了(包括断了,老化);
    2– 网卡以及相关驱动坏了,IP 配置及冲突问题;
    3– 心跳线间连接的设备故障(交换机的故障或者是网卡的故障);
    4– 仲裁的服务器出现问题。
2)高可用服务器对上开启了防火墙阻挡了心跳消息的传输;
3)高可用服务器对上的心跳网卡地址等信息配置的不正确,导致发送心跳失败;
4)其他服务配置不当等原因,如心跳的方式不同,心跳广播冲突,软件出现了 BUG 等。

简单来说,Heartbeat 脑裂的原因可能就是:
1) 心跳线断了,无法通讯(老鼠咬了,线材老化);
2) 使用网路直连时,网卡驱动坏了,局域网 IP 冲突;
3) 心跳线之间的中转设备坏了(仲裁设备坏了);
4) iptables 防火墙;
5) 地址信息不对(掩码……),配置丢失;
6) 网线误拔;

防止脑裂发生的方法:
发生脑裂的时候,对业务的影响是及其严重的,有的时候甚至是致命的。
比如:两台高可用的服务器对之间发生脑裂,导致互相竞争同一个 IP 资源,就如同我们局域网内常见的 IP 地址冲突一样,两个机器就会有一个或者两个不正常,影响用户正常访问服务器。如果是应用在数据库或者是存储服务这种极重要的高可用上,那就导致用户发布的数据间断的写在两台服务器上的恶果,最终数据恢复及困难或者是难已恢复
实际的生产环境中,我们可以从以下几个方面来防止裂脑的发生:
1)同时使用串行电缆和以太网电缆连接,同时用两条心跳线路,这样一条线路坏了,另一个线路还是好的,依然能传送消息(推荐的)
2)检测到裂脑的时候强行的关闭一个心跳节点(需要特殊的节点支持,如 stonith,fence),相当于程序上备节点发现心跳线故障,发送关机命令到主节点。
3)做好对裂脑的监控报警(如邮件以及手机短信等),在问题发生的时候能够人为的介入到仲裁,降低损失。当然,在实施高可用方案的时候,要根据业务的实际需求确定是否能够容忍这样的损失。对于一般的网站业务,这个损失是可控的(公司使用)
4)启用磁盘锁。正在服务一方锁住共享磁盘,脑裂发生的时候,让对方完全抢不走共享的磁盘资源。但使用锁磁盘也会有一个不小的问题,如果占用共享盘的乙方不主动解锁,另一方就永远得不到共享磁盘。现实中介入服务节点突然死机或者崩溃,另一方就永远不可能执行解锁命令。后备节点也就截关不了共享的资源和应用服务。于是有人在 HA 中涉及了“智能”锁,正在服务的一方只在发现心跳线全部断开时才启用磁盘锁,平时就不上锁了
5)报警报在服务器接管之前,给人员处理留足够的时间就是 1 分钟内报警了,但是服务器不接管,而是 5 分钟之后接管,接管的时间较长。数据不会丢失,但就是会导致用户无法写数据。
6)报警后,不直接自动服务器接管,而是由人员接管。
7)增加仲裁的机制,确定谁该获得资源,这里面有几个参考的思路:
    1– 增加一个仲裁机制。例如设置参考的 IP,当心跳完全断开的时候,2 个节点各自都 ping 一下参考的 IP,不同则表明断点就出现在本段,这样就主动放弃竞争,让能够 ping 通参考 IP 的一端去接管服务。
    2– 通过第三方软件仲裁谁该获得资源,这个在阿里有类似的软件应用

简单来说,解决 Heartbeat 脑裂的办法:
1) 做冗余;
2) 做好脑裂监控报警(在仲裁设备上做),仲裁方式停服;
3) 多个仲裁机制(仲裁设备,第三方仲裁软件);
4) 一旦报警,短信电话通知运维人员,服务不要自动接管服务,有人员操作;

HeartBeat 的配置文件
heartbeat 主要的配置文件有 3 个:
1)认证文件 authkeys
2)主配置文件 ha.cf
3)资源文件 haresources

接下来就重点说一下这 3 个文件的具体功能以及配置:
1)heartbeat 的认证配置文件 authkeys,内容如下
    auth 1
    1 crc
    2 sha1 HI!
    3 md5 Hello!
该文件主要是用于集群中两个节点的认证,采用的算法和密钥 (如果有的话) 在集群中节点上必须相同,目前提供了 3 种算法:md5,sha1 和 crc。
其中 crc 不能够提供认证,它只能够用于校验数据包是否损坏 而 sha1,md5 需要一个密钥来进行认证,从资源消耗的角度来讲,md5 消耗的比较多,sha1 次之,因此建议一般使用 sha1 算法
如果要采用 sha1 算法,只需要将 authkeys 中的 auth 指令 (去掉注释符) 改为 2,而对应的 2 sha1 行则需要去掉注释符 (#),后面的密钥自己改变(两节点上必须相同)。改完之后,保存, 同时需要改变该文件的属性为 600,否则 heartbeat 启动将失败

2)heartbeat 的主要配置文件 ha.cf
第一个是 ha.cf 该文件位于在安装后创建的 /etc/ha.d 目录中。该文件中包括为 Heartbeat 使用何种介质通路和如何配置他们的信息。在源代码目录中的 ha.cf 文件包含了您可以使用的全部选项,详述如下:

debugfile /var/log/ha-debug     用于记录 heartbeat 的调试信息
logfile /var/log/ha-log        用于记录 heartbeat 的日志信息
如果未定义上述的日志文件,那么日志信息将送往 local0(对应的 #/var/log/messages),如果这 3 个日志文件都未定义,那么 heartbeat 默认情况下
将在 /var/log 下建立 ha-debug 和 ha-log 来记录相应的日志信息。

keepalive 2        发送心跳报文的间隔,默认单位为秒,如果你毫秒为单位,那么需要在后面跟 ms 单位,如 1500ms 即代表 1.5s
deadtime 30      用于配置认为对方节点菪掉的间隔
warntime 10      发出最后的心跳警告报文的间隔
initdead 120      网络启动的时间
udpport 694       广播 / 单播通讯使用的 udp 端口
bcast eth0 Linux      心跳所使用的网络接口

baud 19200      波特率,串口通信的速度。
udpport 694     使用端口 694 进行 bcast 和 ucast 通信。这是默认的,并且在 IANA 官方注册的端口号。

mcast eth0 225.0.0.1 694 1 0
如果采用组播通讯,在这里可以设置组播通讯所使用的接口,绑定的组播 ip 地 #址 (在 224.0.0.0 – 239.255.255.255 间),通讯端口,ttl(time to live) 所能经过路由的 #跳数,是否允许环回(也就是本地发出的数据包时候还接收)

ucast eth0 192.168.1.2       如果采用单播,那么可以配置其网络接口以及所使用的 ip 地址
auto_failback on        该选项是必须配置的!用于决定当拥有该资源的属主恢复之后,资源是否变迁:是迁移到属主上,还是在当前节点上继续运行,直到当前节点出现故障。
stonith baytech /etc/ha.d/conf/stonith.baytech        用于共享资源的集群环境中,采用 stonith 防御技术来保证数据的一致性

watchdog /dev/watchdog       该指令是用于设置看门狗定时器,如果节点一分钟内都没有心跳,那么节点将重新启动
node ken3      设置集群中的节点,注意:节点名必须与 uname –n 相匹配

node primary.mydomain.com    该选项是必须配置的。集群中机器的主机名,与“uname –n”的输出相同。
node backup.mydomain.com    该选项是必须配置的。同上。
respawn     该选项是可选配置的:列出将要执行和监控的命令。例如:要执行 ccm 守护进程,则要添加如下的内容:

ping 10.10.10.254
ping 指令以及下面的 ping_group 指令是用于建立伪集群成员,它们必须与下述 #的 ipfail 指令一起使用,它们的作用是监测物理链路,也就是说如果集群节点与上述伪设备不相通,那么该节点也将无权接管资源或服务,它将释放掉资源。

respawn hacluster /usr/lib/heartbeat/ccm
使得 Heartbeat 以 userid(在本例中为 hacluster)的身份来执行该进程并监视该进程的执行情况,如果其死亡便重启之。
对于 ipfail,则应该是:
respawn hacluster /usr/lib/heartbeat/ipfail
对于 pingd 则应该是:
respawn hacluster /usr/lib64/heartbeat/pingd -m 100 -d 5s

注意:如果结束进程的退出代码为 100,则不会重启该进程。
apiauth pingd gid=haclient uid=hacluster

apiauth client-name gid=gidlist uid=uidlist
apiauth ipfail gid=haclient uid=hacluster 设置你所指定的启动进程的权限

3)heartbeat 的资源配置文件 haresources
配置好 ha.cf 文���之后,便是 haresources 文件。
该文件列出集群所提供的服务以及服务的默认所有者,该文件主要是为部署的集群配置资源或者服务。
注意:两个集群节点上的该文件必须相同。集群的 IP 地址是该选项是必须配置的,不能在 haresources 文件以外配置该地址, haresources 文件用于指定双机系统的主节点、集群 IP、子网掩码、广播地址以及启动的服务等。

它的每一有效行的格式如下:
node-name resource1 resource2 … resourceN
其中 node-name 即为集群中某一节点的名称,必须与 uname –n 相同,
后面的资源组 resource1 resource2 …resourceN 中每一个资源都是一个 shell 脚本,它们的搜索路径为 /etc/init.d/ 和 /usr/local/etc/ha.d/resource.d(该路径根据你所安装 heartbeat 的路径有所不同),heartbeat 为我们提供了一个非常好的资源扩展框架,如果我们需要控制一种自己的资源,只需要实现一个支持 start 和 stop 参数的 shell 脚本就可以了,目前 heartbeat 所支持的资源脚本可以在我提供的上述路径中去查看。

如下配置进行说明:
node-name network-config
其中 node-name 指定双机系统的主节点,取值必须匹配 ha.cf 文件中 node 选项设置的主机名中的一个,node 选项设置的另一个主机名成为从节点。network-config 用于网络设置,包括指定集群 IP、子网掩码、广播地址等。resource-group 用于设置 heartbeat 启动的服务,该服务最终由双机系统通过集群 IP 对外提供。在本文中我们假设要配置的 HA 服务为 Apache 和 Samba。
在 haresources 文件中需要如下内容:
primary.mydomain.com 192.168.85.3 httpd smb
该行指定在启动时,节点 linuxha1 得到 IP 地址 192.168.85.3,并启动 Apache 和 Samba。在停止时,Heartbeat 将首先停止 smb,然后停止 Apache,最后释放 IP 地址 192.168.85.3。这里假设命令“uname –n”的输出为“primary.mydomain.com”-如果输出为“primary”,便应使用“primary”。
primary.mydomain.com IPaddr::192.168.21.107/24/eth0 drbddisk::r0 Filesystem::/dev/drbd1::/data::ext4 nfs
正确配置好 haresources 文件之后,将 ha.cf 和 haresource 拷贝到 /etc/ha.d 目录。
注意:资源文件中能执行的命令必须在 /etc/ha.d/resource.d/ 中可见!

正文完
星哥玩云-微信公众号
post-qrcode
 0
星锅
版权声明:本站原创文章,由 星锅 于2022-01-21发表,共计10427字。
转载说明:除特殊说明外本站文章皆由CC-4.0协议发布,转载请注明出处。
【腾讯云】推广者专属福利,新客户无门槛领取总价值高达2860元代金券,每种代金券限量500张,先到先得。
阿里云-最新活动爆款每日限量供应
评论(没有评论)
验证码
【腾讯云】云服务器、云数据库、COS、CDN、短信等云产品特惠热卖中