ZStack--可拓展性的秘密武器1:异步架构

ZStack通过异步架构解决了IaaS软件在处理大量并发任务时的效率问题,实现了99%任务的异步执行,使得单一管理节点能轻松应对数千台物理服务器及上万台虚拟机的管理,有效提升系统可拓展性和响应速度。

ZStack的架构使得其中99%的任务能被异步执行。基于这点,ZStack中单一的管理节点可以管理几千台物理服务器,上万台虚拟机,处理成千上万个并发任务。

动机

对于管理大量硬件和虚拟机的公有云而言,可拓展性是一个IaaS软件必须解决的关键问题之一。对于一个大概拥有5万台物理服务器的中型数据中心,预计可能有150万台虚拟机,1万名用户。虽然用户开关虚拟机的频率不会像刷朋友圈一样频繁,但是在某一时刻,IaaS系统可能有成千上万个任务要处理,这些任务可能来自API也可能来自内部组件。在糟糕的情况下,用户为了创建一台新的虚拟机可能需要等待一个小时,因为系统同时被5000个任务阻塞,然而线程池仅有1000条线程。

问题

首先,我们非常不赞同一些文章里面描写的关于“一些基础配套设施,尤其是数据库和消息代理(message brokers)限制了IaaS的可拓展性”的观点。首先,对于数据库而言,IaaS软件的数据量相比facebook和twitter而言只能勉强算中小型,facebook和twitter的数据量是万亿级别,IaaS软件只处于百万级别(对于一些非常大型的数据中心),而facebook和twitter依旧坚强的使用Mysql作为他们主要的数据库。其次,对于消息代理而言,ZStack使用的rabbitmq相对Apache Kafka或ZeroMQ是一个中型的消息代理,但是它依然可以维持平均每秒5万条消息的吞吐量,对于IaaS软件内部通信而言这不就足够了么?我们认为足够了。

限制IaaS可拓展性的主要原因在于:任务执行缓慢。IaaS软件上的任务运行非常缓慢,通常一项任务完成需要花费几秒甚至几分钟。所以当整个系统被缓慢的任务填满的时候,新任务的延迟非常大是很正常的。执行缓慢的任务通常是由一个很长的任务路径组成的,比如,创建一个虚拟机,需要经过身份验证服务à调度器à镜像服务à存储服务à网络服务à虚拟机管理程序,每一个服务可能会花费几秒甚至几分钟去引导外部硬件完成一些操作,这极大的延长了任务执行的时间。

同步和异步

传统的IaaS软件使用同步的方式执行任务,他们通常给每一个任务安排一个线程,这个线程只有在之前的任务执行完毕时才会开始执行下一个任务。因为任务执行缓慢,当达到一个任务并发的高峰时,系统会因为线程池容量不足,运行非常缓慢,新来的任务只能被放在队列中等待被执行。

为了解决这个问题,一个直观的想法是提高线程池容量,但是这个想法在实际中是不可行的,即使现代操作系统允许一个应用程序拥有成千上万条线程,没有操作系统可以非常有效率的调度他们。随后有一个想法是把线程分发出去,让不同的操作系统上相似的软件分布式的处理线程,因为每一个软件都有它自己的线程池,这样最终增加了整个系统的线程容量。然而,分发会带来一定的开销,它增加了管理的复杂度,同时集群软件在软件设计层面依旧是一个挑战。最后,IaaS软件自身变成云的瓶颈,而其他的基础设施包括数据库,消息代理和外部的系统(比如成千台物理服务器)都足够去处理更多的并发任务。

ZStack通过异步架构来解决这个问题,如果我们把目光投向IaaS软件和数据中心的设备之间的关系,我们会发现IaaS软件实际上扮演着一个协调者的角色,它负责协调外部系统但并不做任何真正耗时的操作。举个例子,存储系统可以分配磁盘容量,镜像系统可以下载镜像模板,虚拟机管理程序可以创建虚拟机。IaaS软件所做的工作是做决策然后把子任务分配给不同的外部系统。比如,对于KVM,KVM主机需要执行诸如准备磁盘、准备网络、创建虚拟机等子任务。创建一台虚拟机可能需要花费5s,IaaS软件花费时间为0.5s,剩下的4.5s被KVM主机占用,ZStack的异步架构使IaaS管理软件不用等待4.5s,它只需要花费0.5s的时间选择让哪一台主机处理这个任务,然后把任务分派给那个主机。一旦主机完成了它的任务,它将结果通知给IaaS软件。通过异步架构,一个只有100条线程容量的线程池可以处理上千数的并发任务。

ZStack的异步方法

异步操作在计算机科学中是非常常见的操作,异步I/O,AJAX等都是一些众所周知的例子。然而,把所有的业务逻辑都建立在异步操作的基础上,尤其是对于IaaS这种非常典型的集成软件,是存在很多挑战的。

最大的挑战是必须让所有组件都异步,并不只是一部分组件异步。举个例子,如果你在其他服务都是同步的条件下,建立一个异步的存储服务,整个系统性能并不会提升。因为在异步的调用存储服务时,调用的服务自身如果是同步的,那么调用的服务必须等待存储服务完成,才能进行下一步操作,这会使得整个工作流依旧是处于同步状态。

(一个执行业务流程服务的线程同步调用了存储服务,然而存储服务和外部存储系统是异步通信的,因此它依旧需要等到存储服务返回之后,才能往下执行,这里的异步就等同于同步了。)

ZStack的异步架构包含了三个模块:异步消息,异步方法,异步HTTP调用。

在这里插入图片描述

1. 异步消息

ZStack使用rabbitmq作为一个消息总线连接各类服务,当一个服务调用另一个服务时,源服务发送一条消息给目标服务并注册一个回调函数,然后立即返回。一旦目标服务完成了任务,它返回一条消息触发源服务注册的回调函数。代码如下:

AttachNicToVmOnHypervisorMsg amsg = new AttachNicToVmOnHypervisorMsg();

amsg.setVmUuid(self.getUuid());

amsg.setHostUuid(self.getHostUuid());

amsg.setNics(msg.getNics());

bus.makeTargetServiceIdByResourceUuid(amsg, HostConstant.SERVICE_ID, self.getHostUuid());

bus.send(amsg, new CloudBusCallBack(msg) {

@Override

public void run(MessageReply

reply) {

    AttachNicToVmReply

r = new AttachNicToVmReply();

    if (!reply.isSuccess()) {

        r.setError(errf.instantiateErrorCode(VmErrors.ATTACH_NETWORK_ERROR, r.getError()));

    }

    bus.reply(msg, r);

}

});

一个服务也可以同时发送一列消息给其它服务,然后异步的等待回复。

final
ImageInventory inv = ImageInventory.valueOf(ivo);

final List dmsgs =
CollectionUtils.transformToList(msg.getBackupStorageUuids(), new Function<DownloadImageMsg, String>() {

@Override

public DownloadImageMsg

call(String arg) {

DownloadImageMsg dmsg = new DownloadImageMsg(inv);

    dmsg.setBackupStorageUuid(arg);

    bus.makeTargetServiceIdByResourceUuid(dmsg,

BackupStorageConstant.SERVICE_ID, arg);

    return dmsg;

}

});

bus.send(dmsgs, new CloudBusListCallBack(msg) {

@Override

public void run(List<MessageReply> replies) {

    /* do something */

}

}

更甚,以设定的并行度发送一列消息也是可以实现的。也就是说,含有10条消息的消息列表,可以每次发送2条消息,也就是说第3、4条消息可以在第1、2条消息的回复收到后被发送。

final List msgs = new ArrayList(hostsToLoad.size());for (String uuid : hostsToLoad) { ConnectHostMsg connectMsg = new ConnectHostMsg(uuid); connectMsg.setNewAdd(false); connectMsg.setServiceId(serviceId); connectMsg.setStartPingTaskOnFailure(true); msgs.add(connectMsg);} bus.send(msgs, HostGlobalConfig.HOST_LOAD_PARALLELISM_DEGREE.value(Integer.class), new CloudBusSteppingCallback() { @Override public void run(NeedReplyMessage msg, MessageReply reply) { /* do something */ }});

2.异步的方法

服务在ZStack中是一等公民,他们通过异步消息进行通信。在服务的内部,有非常多的组件、插件使用方法调用的方式来进行交互,这种方式也是异步的。

protected void startVm(final
APIStartVmInstanceMsg msg, final SyncTaskChain taskChain) {

startVm(msg, new Completion(taskChain) {

    @Override

    public void success() {

VmInstanceInventory inv = VmInstanceInventory.valueOf(self);

APIStartVmInstanceEvent evt = new APIStartVmInstanceEvent(msg.getId());

        evt.setInventory(inv);

        bus.publish(evt);

taskChain.next();

    }



    @Override

    public void fail(ErrorCode errorCode) {

APIStartVmInstanceEvent evt = new APIStartVmInstanceEvent(msg.getId());

        evt.setErrorCode(errf.instantiateErrorCode(VmErrors.START_ERROR, errorCode));

        bus.publish(evt);

taskChain.next();

    }

});

}

回调函数也可以有返回值:

public void createApplianceVm(ApplianceVmSpec spec, final ReturnValueCompletion completion) { CreateApplianceVmJob job = new CreateApplianceVmJob(); job.setSpec(spec); if (!spec.isSyncCreate()) { job.run(new ReturnValueCompletion(completion) { @Override public void success(Object returnValue) { completion.success((ApplianceVmInventory) returnValue); } @Override public void fail(ErrorCode errorCode) { completion.fail(errorCode); } }); } else { jobf.execute(spec.getName(), OWNER, job, completion, ApplianceVmInventory.class); }}

3.HTTP异步调用

ZStack使用一组agent去管理外部系统,比如:管理KVM主机的agent,管理控制台代理的agent,管理虚拟路由的agent等,这些agents全部都是搭建在Python CherryPy上的轻量级web服务器。因为如果没有HTML5技术,如websockets技术,是没有办法进行双向通信的,ZStack每个请求的HTTP头部嵌入一个回调的URL,因此,在任务完成后,agents可以发送回复给调用者的URL。

RefreshFirewallCmd cmd = new RefreshFirewallCmd();

List tos = new RuleCombiner().merge();

cmd.setRules(tos);

resf.asyncJsonPost(buildUrl(ApplianceVmConstant.REFRESH_FIREWALL_PATH), cmd, new
JsonAsyncRESTCallback(msg, completion) {

@Override

public void fail(ErrorCode err) {

    /* handle failures */

}



@Override

public void success(RefreshFirewallRsp ret) {

    /* do something */

}



@Override

public Class<RefreshFirewallRsp> getReturnClass() {

    return

RefreshFirewallRsp.class;

}

});

通过以上三种方法,ZStack已经建立了一个可以使所有组件都异步进行操作的全局架构。

总结

为了解决由缓慢且并发的任务引起的IaaS软件可拓展性受限的问题,我们演示了ZStack的异步架构。我们使用模拟器进行测试后发现,一个具有1000条线程的ZStack管理节点可以轻松处理创建100万台虚拟机时产生的10000个并发任务。虽然单一管理节点的拓展性已经可以满足大多数云的负载需要,考虑到系统需要高可用性以及承受巨大的负载量(10万个并发任务),我们需要一组管理节点来满足这些需求,如需了解ZStack的无状态服务,请阅读下一篇“ZStack可拓展性秘密武器2:无状态服务”。

<think>我们参考用户提供的引用资料,发现用户提到的"zsdeck"可能是"ZStack"的拼写错误。根据引用[1][2][3][4]可知,ZStack是一款开源的IaaS(基础设施即服务)软件,用于云计算平台的管理。因此,我们将围绕ZStack展开技术文档、教程、配置和错误解决方面的回答。###一、ZStack技术文档与教程1.**官方文档**ZStack提供详细的官方文档,涵盖安装、配置、管理等内容:-功能列表与特性矩阵:http://zstack.org/documentation/features-matrix.html[^2]-快速安装指南(单节点):http://zstack.org/installation/[^2]-多控制节点安装指南:http://zstack.org/installation/multi-node.html[^2]2.**核心教程****安装部署**(引用[1]):-选择安装模式时,建议选择`ZStackEnterpriseManagementNode`(企业版管理节点模式),该模式免费测试且功能完整[^1]。-安装步骤示例:```bash#下载安装脚本wgethttp://download.zstack.org/releases/0.9/0.9.0/zstack-installer.sh#执行安装bashzstack-installer.sh```**存储集成**(引用[2]):-支持分布式存储Ceph,通过API查询存储详情:```bashzstack-cliQueryCephPrimaryStorage#查询Ceph主存储信息[^2]```**插件开发**(引用[3]):-利用插件架构扩展功能,通过XML组装插件,使用自研消息队列接入事件[^3]。---###二、常见配置与错误解决####场景1:安装失败-**问题现象**:安装过程中断或报错。-**解决方案**:1.检查系统要求:需CentOS7.x或Ubuntu16.04+,内存≥4GB。2.关闭防火墙和SELinux:```bashsystemctlstopfirewalldsetenforce0```3.确保网络连通(特别是NTP时间同步)。####场景2:Ceph存储集成异常-**问题现象**:虚拟机无法挂载Ceph卷。-**排查步骤**:1.验证Ceph集群状态:```bashceph-s#在Ceph主节点执行```2.检查ZStack存储配置:-确认CephMonitors的IP和端口正确。-确保ZStack管理节点能访问Ceph公共网络。####场景3:插件加载失败-**问题现象**:自定义插件未生效。-**解决要点**:-检查插件XML描述文件的hook点名称是否匹配[^3]。-查看管理节点日志:```bashtail-f/var/log/zstack/zstack.log|grepPlugin```---###三、高级功能配置1.**超融合一体机(ZStackCube)**-引用[4]提到ZStackCube支持应用市场,可部署多管理平台(CMP)[^4]。-启用CMP步骤:1.在ZStackUI导航至“应用市场”。2.选择“ZStackCMP”,点击“免费试用”。3.配置异构资源(如vCenter/AWS账号)。2.**多管理**CMP提供以下功能配置:-**混合云计费**:设置费率模板,关联资源账单。-**流程审批**:定义虚拟机申请的审批流程。-**监控大屏**:集成Prometheus数据源定制监控视图。---###四、错误日志分析指南ZStack日志位于`/var/log/zstack/`,关键文件:|日志文件|用途||-------------------------|-----------------------||`zstack.log`|管理节点主日志||`zstack-api.log`|API请求日志||`zstack-ui.log`|Web控制台操作日志|**典型错误处理**:-**错误码`SYS_ERROR`**:系统级异常,检查数据库连接(MySQL状态)。-**错误码`NETWORK_NO_ROUTE`**:网络路由配置错误,验证路由表[^1]。>示例:定位存储错误>```bash>grep"StorageException"/var/log/zstack/zstack.log-A10>```---###五、学习资源推荐1.**视频教程**-[ZStack官方B站频道](https://space.bilibili.com/509008267):提供安装演示与功能讲解。2.**社区支持**-中文论坛:https://bbs.zstack.io-GitHub仓库:https://github.com/zstackio/zstack---###相关问题1.ZStack与OpenStack的主要架构差异是什么?2.如何扩展ZStack插件实现自定义工作流?3.ZStackCube超融合集群的灾备方案有哪些?>若需进一步协助,请提供具体错误日志或配置截图。建议优先查阅官方文档[^2],多数基础问题可通过文档快速解决。</think>基于您提供的ZStack引用资料和技术需求,我将从技术文档、配置指南和错误解决三方面进行系统化整理: ### 一、ZStack技术文档与教程 1. **核心架构文档** ZStack采用分布式微服务架构,核心组件包括: - 管理节点(Management Node):控制中心[^1] - 计算节点(Compute Node):虚拟机资源池 - 自研消息队列:实现组件间通信[^3] ```mermaid graph TD A[管理节点] -->|消息队列| B(计算节点) A --> C(Ceph存储) A --> D(网络服务) ``` 2. **安装教程** 引用[1][2]提供的安装路径: - **单节点部署**(5分钟快速安装): ```bash wget http://download.zstack.org/releases/installer/zstack-installer.sh bash zstack-installer.sh -R aliyun -a ``` - **多节点集群部署**(企业版): ```bash # 选择安装模式时使用: zstack-installer --deploy-type enterprise ``` 3. **API开发文档** 通过自研消息队列实现插件开发(引用[3]): ```xml <!-- 插件XML组装示例 --> <extension> <hook point="vm.pre.create" class="com.zstack.plugin.CustomVMHook"/> </extension> ``` --- ### 二、关键配置指南 #### 1. 存储配置(引用[2]) **Ceph存储集成命令**: ```bash # 创建Ceph主存储 zstack-cli AddCephPrimaryStorage --name=ceph-store --url=ceph://192.168.1.100/ --poolName=zstack-pool ``` #### 2. 网络配置 **安全组规则示例**: ```json { "rules": [ { "type": "Ingress", "startPort": 22, "endPort": 22, "protocol": "TCP", "allowedCidr": "0.0.0.0/0" } ] } ``` #### 3. 超融合配置(引用[4]) **启用多管理平台**: 1. 在ZStack Cube控制台进入"应用市场" 2. 选择"ZStack CMP"并启用3个月试用版 3. 配置异构资源接入点(AWS/Azure/vCenter) --- ### 三、常见错误解决方案 #### 错误1:部署时节点注册失败 **现象**:`ERROR: Compute node registration timeout` **解决**: 1. 检查网络连通性: ```bash ping <管理节点IP> telnet <管理节点IP> 8080 ``` 2. 验证防火墙规则: ```bash firewall-cmd --list-ports | grep 8080 ``` #### 错误2:Ceph存储连接异常 **现象**:`StorageConnectionRefusedException` **解决**: 1. 验证Ceph集群状态: ```bash ceph -s # 在Ceph节点执行 ``` 2. 检查ZStack存储配置: ```bash zstack-cli QueryCephPrimaryStorage # 引用[2] API ``` #### 错误3:插件加载失败(引用[3]) **现象**:`PluginInitializationError` **解决**: 1. 检查hook点兼容性: ```bash grep "hook point" /usr/lib/zstack/plugin/*.xml ``` 2. 验证SystemTag状态: ```sql SELECT * FROM SystemTagVO WHERE tag LIKE '%plugin%'; ``` --- ### 四、运维监控命令 ```bash # 查看服务状态 systemctl status zstack.service # 实时日志监控 tail -f /var/log/zstack/zstack.log # 资源使用统计 zstack-cli GetResourceUsage --resourceType=VM --zoneUuid=your_zone_uuid ``` --- ### 五、进阶学习资源 1. **官方文档**: - [功能矩阵](http://zstack.org/documentation/features-matrix.html) [^2] - [多节点部署手册](http://zstack.org/installation/multi-node.html) [^2] 2. **API参考**: - `QueryCephPrimaryStorage` 存储查询API [^2] - `AddCephPrimaryStorage` 存储添加API > 建议优先查阅`/usr/share/zstack/apidoc`下的本地API文档 ### 相关问题 1. 如何实现ZStack与VMware的混合云迁移?[^1] 2. ZStack Cube超融合集群的灾备方案有哪些?[^4] 3. 如何通过SystemTag机制扩展数据库表结构?[^3] 4. ZStack消息队列与传统MQ(如RabbitMQ)的性能对比? > 遇到具体错误时,请提供日志片段(隐藏敏感信息),可进一步精准定位问题。日常运维建议启用管理节点的SNMP监控[^4]。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值