支撑 “千万设备日活” 的创米数联 7 年微服务架构演进之路

本文涉及的产品
应用实时监控服务-用户体验监控,每月100OCU免费额度
服务治理 MSE Sentinel/OpenSergo,Agent数量 不受限
应用实时监控服务-应用监控,每月50GB免费额度
简介: 支撑 “千万设备日活” 的创米数联 7 年微服务架构演进之路

作者:金兆旭 上海创米数联智能科技发展股份有限公司云服务开发及 SRE 工程师 负责公司云端基础设施构建及消息网关等研发工作;十眠


创米数联是小米生态链首批亿元俱乐部成员,主营业务为智能家居产品的研发、设计、生产和销售,致力于成为以居家安全为核心的产品和服务提供商,提供多品类的全屋智能家居产品及服务。公司以居家安全为核心,洞察用户在居住环境下的智能化需求,建立物理安全、环境安全、系统安全三类场景及服务体系,主要产品包括智能摄像机、智慧门、智能猫眼、智能门铃、智能插座等。公司旨在实现“看得见的全屋智能”,以智能家庭安全为切入点,提供多品类覆盖的智能家居解决方案。截至 2021 年 12 月 31 日,创米数联已经在全世界 150 多个国家,销售了超过 5500 万台设备,拥有了 1600 万设备和 500 万设备用户日活。


作为小米生态链的一员,创米采用微服务架构支撑其千万日活的 IOT 设备。随着智能家居市场的快速迭代,创米面临着发布和迭代的稳定性挑战,同时需要解决多方 IOT 接入面临的性能和安全挑战。本文将为您一一道来创米是如何应对这些挑战的。


云计算时代的蹒跚学步


创米云服务从 2016 年创始之初就选择了云计算+微服务的技术路线,以应对面临的大量线上用户和设备带来的流量挑战。构建微服务之初,市面上可选用的解决方案并不多,我们自主实现了一些微服务组件,如 frontend 业务网关和配置中心,并在小米生态云上部署容器服务来处理设备消息、设备插件 API 和微信公众号等相关业务,并利用 HPA 及 CronHPA 等容器弹性伸缩策略来应对动态的海量线上流量。


image.png


自此创米数联在云计算时代踏上了探索服务容器化的第一步。


新业务及新挑战

从 2019 年伊始,创米数联提出了研发自有 APP 和适配自有 APP 的智能家居设备的发展战略。云服务部将研发重心转向自有 APP 云端业务,并逐步接入自有品牌设备。为了实现全球业务,创米云服务部将相关服务部署在阿里云的 4 个 Region 的 ACK Pro 专有版 Kubernetes 集群上。阿里云 ACK 为创米云提供了可靠稳定的基础设施,向下封装好的数十款云产品,降低了云端运维人员的运维压力,快速对接其他云产品的能力也对开发人员十分友好,能够让创米云服务在极短的时间内搭建一套线上可用的环境。


在自有业务研发开始阶段,我们选择了 Spring Cloud、Eureka 和 Apollo 等技术栈来搭建我们的微服务基础架构。然而,经过一年半的摸索,我们发现当前的混合架构存在着不稳定、上线部署风险大以及高人力维护成本等问题。


因此,从 2021 年开始,创米云服务决定改变现有的微服务架构,逐步拥抱云原生。我们的目标是在满足稳定性和低维护成本等需求的基础上,实现所有组件的可观测性、全链路的流量治理以及更加便捷高效的 DevOps 流程。


云原生体系探索

首先我们将当前的 Spring Cloud 体系全面转向 Spring Cloud Alibaba,使用 Nacos 替换 Eureka,以解决 Eureka 服务端压力过大的问题,并满足单注册中心多环境分组的需求。由于 Apollo 在某些情况下存在容器磁盘压力大的问题,我们逐步将配置中心从 Apollo 替换为 Nacos。针对之前定制化的 Apollo 配置同步和本地特殊配置缓存,同样我们也对 Nacos 客户端进行了部分定制化改造。


image.png


初版上线时,考虑到注册中心和配置中心的高可用性、热升级、成本、可观测配套等因素,我们没有选择自建有状态的开源 Nacos 服务,而是直接使用了阿里云 MSE Nacos 专业版服务。至今,该服务一直稳定运行,没有出现可用性问题。


全链路流量治理

针对全链路的流量治理,由于创米云服务所处的 AIoT 行业不同于传统互联网行业,我们在南北向流量时不仅需要治理下游用户手机端 APP 及 Web 端的 HTTP 请求,还需要处理来自设备端的 MQTT、第三方 AMQP 和 HTTP 2 长连接 Push 消息的流量治理。这些消息通常经由统一的上游消息网关(消息总线)监听,经过多级过滤器,如消息来源、消息限流和产品或特定设备级别的白名单等,对消息进行分类和打标签,然后对消息 Topic 正则路由并进行 HTTP 异步或 rpc 请求。只有经过这些请求后,我们才能对其进行流量治理。



因此,创米云服务的流量治理整体较为复杂。我们曾考虑过采用侵入式代码和自定义负载均衡器,并开发控制台来实现高度自定义的流量方案。我们还考虑过使用 Istio Service Mesh 的方案治理流量。然而,前者在当前百万级别设备消息的情况下性能严重受限,后者由于设备消息链路较长、打标较多,导致实现全链路灰度时配置文件实现较为复杂,而且 Envoy 代理无法完整拦截消息总线请求等问题,因此我们否定了这两种方案。之后在选型过程中,我们采用了 MSE 微服务治理。


我们传统的 API 业务流量治理选用了多域名、多租户环境、节点隔离加多业务网关的方案配合 MSE 微服务治理来实现多个环境服务的测试开发及线上灰度部署。我们使用多域名加 DNS 流量划分的方式对服务重构后的业务网关新路由进行测试,保证服务重构后的安全上线。我们利用多个 K8s 集群、K8s namespace 以及多个 namespace 的注册配置中心的隔离构建了不同的线上环境,分别用来线上开发、线上测试、灰度以及基线环境部署。对于同一集群不同 namespace 的应用 pod 使用多集群隔离、应用节点亲和性、反亲和性以及节点污点等集群调度手段保证环境的安全性,避免不同环境间出现的资源异常导致基线环境不可用的情况。基线环境和灰度环境同属不同命名空间的相同节点池内,测试和开发环境应用 pod 部署在不同的 K8s 集群或节点池中。我们的整体流程通常是在 feature 及 bug 修复后涉及的服务在开发环境联调完毕,在每次测试流程前将 feature 服务部署至测试环境,通过蓝绿测试将测试人员的流量导向测试环境,在多轮的覆盖及回归测试完成后,将服务部署至灰度环境,再将测试人员及 Beta 测试用户的流量导向灰度环境,经过一定时间的检验后,逐步将线上基线流量导向灰度环境,灰度环境流量完成 100% 灰度后,替换基线环境镜像,最后逐步将灰度流量倒流至基线环境。



在核心业务接入 MSE 微服务治理之后,创米云服务对部分多云部署及老项目通过 DNS 流量切分+全链路灰度的方式进行灰度,逐渐将自有 APP 及自有设备的所有业务重构迁移至新项目中并全部接入 MSE 微服务,实现了云上 API 业务的 100% 安全发布。


在设备消息业务的流量治理的推进过程中,为了解决无法拦截消息请求的问题,我们首先将消息总线拆分为控制器和路由器两部分。控制器监听各个通道的消息后仅对消息进行打标签和分类,然后通过异步 HTTP 请求经由统一的路由器转发到各个服务中。我们将路由器服务定义为流量治理的入口,从而解决了消息无法治理的问题。然后,我们使用统一的全链路灰度对打标签后的 HTTP 请求进行蓝绿和灰度的流量治理,并将其分发到指定的命名空间的指定服务中进行消息处理。


MSE 微服务治理接入非常简单,只需要在 Helm 或组件中心安装 ack-onepilot 组件,重启服务便可自动注入服务,除此之外 MSE 提供了较为友好的全链路灰度配置界面,较 Istio 方案更加易于配置和上手。通过这样的流程,创米云服务成功实现了设备服务的更新、云云设备的对接以及固件 OTA 版本的迭代过程中的安全发布。


无损上下线解决发布扩缩容流量损失问题


无损下线逻辑图


在之前的服务发版部署或 pod 弹性伸缩过程中经常会有部分请求出现超时或不可用的情况,由于创米云服务承载了大量的用户设备请求,这些流量损失轻则导致设备消息重试,严重时会影响部分用户设备的可用性,后续我们了解了 MSE 微服务治理提供了无损上下线及服务预热功能,决定将相关服务全部接入了 MSE 微服务治理的无损上下线,并调整对应服务的就绪检查,在后续的服务上下线过程中经观察再未出现因为流量损失导致的请求不可用的情况,一定程度上避免了由部署发布和服务缩容引起的线上流量损失问题。

image.png

新启动 Pod 的预热流量分布


可观测体系

为了实现可观测性,我们早期就将阿里云 SLS 日志服务集成到自有业务框架中。然而,我们遇到了业务索引不规范、唯一 RequestId 索引异步丢失以及 Spring Cloud Gateway 等 Reactive 框架应用日志异步写入 Location 导致 CPU 占用过高等问题。因此,我们对当前的日志规范进行了改进,并在多个链路追踪方案中选择了 Skywalking。我们将 Skywalking 的 TraceId 写入 SLS 日志索引中,并通过对 ThreadLocal 的改造实现了异步线程的日志索引信息传递。我们的服务挂载了 Skywalking Agent,并自定义了可选插件,然后接入了阿里云链路追踪服务。相比自建 ElasticSearch 集群,阿里云链路追踪服务更经济实惠且免维护,链路追踪服务可以直接将项目关联到指定的 SLS logstore 中,更方便进行链路问题排查。在上线的第一个月里,链路追踪服务帮助我们解决了多个项目中的接口性能问题。


创米云服务的指标信息的观测主要依赖于 ARMS ACK、ARMS ACK Pro、ARMS 云服务等多个开箱可用的 Grafana Dashboard,它们提供了相当完善的集群、Node、Pod 等多个维度的指标信息,除此之外我们依然会使用阿里云云监控或自定义一些 Grafana Dashboard 用来关注其他部分指标。创米云服务为了快速预警,设置了云产品、SLS 日志、K8s 事件等多个维度的告警配置,对报警进行降噪调优,根据告警等级设置了电话、短信、邮件和飞书群多个通道的报警通知,建立了相当全面的服务告警体系,以便相关人员及时发现问题,避免线上损失。


CI/CD 提效

早些时候由于多云部署的问题,我们并没有统一的全自动 CI/CD 解决方案,为了解决云端 DevOps 构建部署和上线安全性等问题,我们将所有的 Devops 流程开始全面转向阿里云云效。首先,我们将云服务代码从自建的 Gitlab 完全同步到阿里云 CodeUp 代码库中,并将之前的 Gitlab CI/CD 和 Jenkins 的 CI/CD 方案全部迁移到阿里云云效流水线。我们建立了单 Region、多 Region、多云项目的多条流水线,实现了从代码提交、手动或自动触发构建,到自动部署到指定的 K8s 集群和命名空间的全流程。每次构建和部署完成后,我们会发送飞书通知并调用 Newman 自动化测试脚本的 WebHook,根据自动化测试结果报告,评估每次服务版本发布是否满足安全规范。


稳定性评估与演练

对于线上环境稳定性评估,创米云服务选用了混沌工程的方式来检验服务的可用性,创米云服务根据自身业务对 Java 应用 OOM、缓存击穿、网络延迟、K8s Pod 资源、K8s 系统组件、关键云服务等多个维度对自身环境的服务进行全方位的演练排查,并检验可观测性中告警配置的灵敏度。我们在没有造成线上损失的情况下发现并修复了部分漏洞、完善了多 AZ 的云服务资源的建设、调整了未触发告警的配置,使自身架构更加健壮。在一定程度上帮助创米云服务在及时弥补了在 HA 方面不足,并在后续的架构设计中提出了高可用优先的原则。


未来展望


未来创米云服务将业务网关逐渐转型为云原生网关+WASM 插件方案,代替繁重的 Spring Cloud Gateway 业务网关,进一步提升网关性能、灵活性和可扩展性,并接入现有可观测体系。我们将继续致力于创新和技术升级,为用户提供更优质的产品体验。

相关实践学习
通过Ingress进行灰度发布
本场景您将运行一个简单的应用,部署一个新的应用用于新的发布,并通过Ingress能力实现灰度发布。
容器应用与集群管理
欢迎来到《容器应用与集群管理》课程,本课程是“云原生容器Clouder认证“系列中的第二阶段。课程将向您介绍与容器集群相关的概念和技术,这些概念和技术可以帮助您了解阿里云容器服务ACK/ACK Serverless的使用。同时,本课程也会向您介绍可以采取的工具、方法和可操作步骤,以帮助您了解如何基于容器服务ACK Serverless构建和管理企业级应用。 学习完本课程后,您将能够: 掌握容器集群、容器编排的基本概念 掌握Kubernetes的基础概念及核心思想 掌握阿里云容器服务ACK/ACK Serverless概念及使用方法 基于容器服务ACK Serverless搭建和管理企业级网站应用
相关文章
|
20天前
|
弹性计算 API 持续交付
后端服务架构的微服务化转型
本文旨在探讨后端服务从单体架构向微服务架构转型的过程,分析微服务架构的优势和面临的挑战。文章首先介绍单体架构的局限性,然后详细阐述微服务架构的核心概念及其在现代软件开发中的应用。通过对比两种架构,指出微服务化转型的必要性和实施策略。最后,讨论了微服务架构实施过程中可能遇到的问题及解决方案。
|
29天前
|
Cloud Native Devops 云计算
云计算的未来:云原生架构与微服务的革命####
【10月更文挑战第21天】 随着企业数字化转型的加速,云原生技术正迅速成为IT行业的新宠。本文深入探讨了云原生架构的核心理念、关键技术如容器化和微服务的优势,以及如何通过这些技术实现高效、灵活且可扩展的现代应用开发。我们将揭示云原生如何重塑软件开发流程,提升业务敏捷性,并探索其对企业IT架构的深远影响。 ####
42 3
|
1月前
|
Cloud Native 安全 数据安全/隐私保护
云原生架构下的微服务治理与挑战####
随着云计算技术的飞速发展,云原生架构以其高效、灵活、可扩展的特性成为现代企业IT架构的首选。本文聚焦于云原生环境下的微服务治理问题,探讨其在促进业务敏捷性的同时所面临的挑战及应对策略。通过分析微服务拆分、服务间通信、故障隔离与恢复等关键环节,本文旨在为读者提供一个关于如何在云原生环境中有效实施微服务治理的全面视角,助力企业在数字化转型的道路上稳健前行。 ####
|
19天前
|
Java 开发者 微服务
从单体到微服务:如何借助 Spring Cloud 实现架构转型
**Spring Cloud** 是一套基于 Spring 框架的**微服务架构解决方案**,它提供了一系列的工具和组件,帮助开发者快速构建分布式系统,尤其是微服务架构。
138 68
从单体到微服务:如何借助 Spring Cloud 实现架构转型
|
18天前
|
运维 监控 持续交付
微服务架构解析:跨越传统架构的技术革命
微服务架构(Microservices Architecture)是一种软件架构风格,它将一个大型的单体应用拆分为多个小而独立的服务,每个服务都可以独立开发、部署和扩展。
149 36
微服务架构解析:跨越传统架构的技术革命
|
21天前
|
设计模式 负载均衡 监控
探索微服务架构下的API网关设计
在微服务的大潮中,API网关如同一座桥梁,连接着服务的提供者与消费者。本文将深入探讨API网关的核心功能、设计原则及实现策略,旨在为读者揭示如何构建一个高效、可靠的API网关。通过分析API网关在微服务架构中的作用和挑战,我们将了解到,一个优秀的API网关不仅要处理服务路由、负载均衡、认证授权等基础问题,还需考虑如何提升系统的可扩展性、安全性和可维护性。文章最后将提供实用的代码示例,帮助读者更好地理解和应用API网关的设计概念。
49 8
|
1月前
|
Dubbo Java 应用服务中间件
服务架构的演进:从单体到微服务的探索之旅
随着企业业务的不断拓展和复杂度的提升,对软件系统架构的要求也日益严苛。传统的架构模式在应对现代业务场景时逐渐暴露出诸多局限性,于是服务架构开启了持续演变之路。从单体架构的简易便捷,到分布式架构的模块化解耦,再到微服务架构的精细化管理,企业对技术的选择变得至关重要,尤其是 Spring Cloud 和 Dubbo 等微服务技术的对比和应用,直接影响着项目的成败。 本篇文章会从服务架构的演进开始分析,探索从单体项目到微服务项目的演变过程。然后也会对目前常见的微服务技术进行对比,找到目前市面上所常用的技术给大家进行讲解。
53 1
服务架构的演进:从单体到微服务的探索之旅
|
26天前
|
消息中间件 运维 Kubernetes
后端架构演进:从单体到微服务####
本文将探讨后端架构的演变过程,重点分析从传统的单体架构向现代微服务架构的转变。通过实际案例和理论解析,揭示这一转变背后的技术驱动力、挑战及最佳实践。文章还将讨论在采用微服务架构时需考虑的关键因素,包括服务划分、通信机制、数据管理以及部署策略,旨在为读者提供一个全面的架构转型视角。 ####
35 1
|
28天前
|
弹性计算 运维 开发者
后端架构优化:微服务与容器化的协同进化
在现代软件开发中,后端架构的优化是提高系统性能和可维护性的关键。本文探讨了微服务架构与容器化技术如何相辅相成,共同推动后端系统的高效运行。通过分析两者的优势和挑战,我们提出了一系列最佳实践策略,旨在帮助开发者构建更加灵活、可扩展的后端服务。
|
28天前
|
消息中间件 运维 Cloud Native
云原生架构下的微服务优化策略####
本文深入探讨了云原生环境下微服务架构的优化路径,针对服务拆分、通信效率、资源管理及自动化运维等核心环节提出了具体的优化策略。通过案例分析与最佳实践分享,旨在为开发者提供一套系统性的解决方案,以应对日益复杂的业务需求和快速变化的技术挑战,助力企业在云端实现更高效、更稳定的服务部署与运营。 ####