Apache Skywalking 实战 阅读笔记 第三章

Apache Skywalking 实战 阅读笔记 第三章

一、参考资料

二、笔记总结

第3章 Apache SkyWalking实战

  • 本章首先介绍后端技术栈的两种技术路线选择,并介绍SkyWalking针对它们所采取的不同应对方式;而后将通过一个具体示例,展示如何使用SkyWalking来监控系统,在该示例的基础上,详细介绍多种监控指标的含义,读者可以对照示例加深对这些指标的理解;最后介绍如何配置监控模块、设置监控目标等内容。

3.1 SkyWalking与单体应用架构

  • 现在通过具体例子为读者展示一个典型的单体应用架构,如图3-1所示。使用Apache或者Nginx作为前端的负载均衡器,服务层是Java的Web应用,数据层是一个关系型数据库,这里我们用MySQL来演示。

3.1.2 单体应用架构的优缺点

  • 这个方案的优点包含以下三点
    • 第一,开发简便 。当前开发的目标工具和IDE都对这种开发模式有较好的支持
    • 第二,易于本地部署 。你可以很容易地用War包将它部署到一个比较适合的应用程序,包括Tomcat、Weblogin和Websphere等。这些容器的部署流程都非常简单
    • 第三,易于扩展 。在Nginx和Apache等前端负载均衡器的协助下 ,或使用F5追求更高性能,可以很容易地将流量均匀分发在启动的多个实例上。
  • 这种架构的弊端
    • 第一,由于单体应用的代码库非常庞大 ,开发人员修改代码会非常困难,而且也给新人员理解整个代码结构带来了非常大的挑战。这导致整个开发节奏变得非常缓慢,而且模块之间的边界不清楚,也很难构建一个统一的开发库来支持所有的项目。
    • 第二,为本地的IDE带来非常大的负担。大的代码结构对编译、启动都会有非常高的要求。如果开发人员的本地开发机配置较低,会增加无法启动或者启动失败的风险。
    • 第三,对于Web容器的负担也比较大。由于构建包体量巨大(经常超过500MB),有些开源Web容器就没法载入这些应用了。通常这时我们会转向一些商业项目,但它所需的机器规格更高,且有一些许可证购买需求,会让你花费更多的金钱在庞大的应用部署上。
    • 第四,持续构建比较困难。因为代码库比较大,每一次编译重新发布都会花费非常多的时间。有的时候整个CI流程中的某一环节失败,而这并不是由运行该CI的开发人员所引入的,会更加拖慢流程的进度。
    • 第五,所谓的系统扩展性好,也仅是针对于流量的横向扩展。应用程序的流量可以扩展,但背后的数据是不能扩展的。图3-1中有一个单一的MySQL节点,所有应用程序均需访问这个单一的数据中心。如果你的数据成几何倍数地增加,单一的数据节点往往是不能扩展的,最终导致整个应用无法扩展。

3.1.3 SkyWalking对单体应用架构的适用性

  • 那么对于SkyWalking这种分布式的追踪系统,单体应用是不是可以借助它来解决问题呢?
  • 首先我们要明确的一点是,像SkyWalking这种追踪应用是可以应用于单体应用的。但这么做的性价比不高 ,原因如下。
    • 第一,资源的性价比。
    • 第二,追踪系统的对手远比它的功能强大。
  • 基于以上两点,SkyWalking这种追踪系统可以用但是不太适合于单体应用

3.2 SkyWalking与微服务架构

  • 由于传统数据交换格式与移动应用程序不兼容,而移动应用需求的增加迫使后端架构发生变化,这是将单体架构迁移到微服务架构的主要原因。
  • 如图3-2所示,微服务架构是用多个被称为服务的小单元去构建大型企业级应用集群的架构方法。举例来说,一个电商微服务架构集群会包含商品展示、购物车、订单、支付和库存等服务。
  • 这些服务都可以单独部署和测试,这样这些服务就可以交给不同的团队进行独立维护了。服务之间往往都使用统一的协议进行交互,比如Dubbo、gRPC和REST等。
  • 它们可以在一台主机或不同的主机上运行,并且这些服务都运行在自己独立的进程内部。每个服务可以有自己的数据库或存储层,也可以共享公共数据存储。
  • 如前所述,传统单体架构会逐步产生代码臃肿、维护困难和难以扩展等问题。而针对以上问题,微服务架构带来了如下的好处
    • 每个微服务都很小,并且专注于特定的功能/业务需求;
    • 微服务可以由小型开发团队(通常是2~5个开发人员)独立开发;
    • 微服务是松散耦合的,这意味着服务在开发和部署方面都是独立的;
    • 微服务可以用不同的编程语言开发,微服务允许利用新兴的和最新的技术(框架、编程语言、编程实践等);
    • 微服务允许使用持续集成工具轻松灵活地集成自动部署;
    • 微服务很容易根据需求扩展。
  • 微服务也有一些不足之处 ,如增加了大量的操作开销,需要DevOps技能,因分布式系统而导致的管理复杂、bug追踪变得具有挑战性。其中比较重要的问题是系统观察性问题 ,请试着回答如下问题:
    • 一次调用到底穿越了几个服务?
    • 在处理这次请求的时候,每个服务到底做了什么操作?
    • 如果请求变慢了,瓶颈在哪里?
    • 如果请求失败了,到底是哪个服务或服务中的哪个部分出了问题?
    • 异常请求与正常请求的区别是什么?
    • 一次请求中,有些经常调用的服务为什么不调用了?或者,有些不常见的服务为什么被调用了?
    • 调用的关键路径是什么?

3.2.1 远程过程调用

  • 远程过程调用(RPC)是一类服务之间数据交互模式的统称。通俗来讲,RPC通过把网络通信抽象为远程的过程调用使调用远程的过程就像调用本地的子程序一样方便,从而屏蔽了通信复杂性,使开发人员可以无须关注网络编程的细节,将更多的时间和精力放在业务逻辑本身的实现上,提高了工作效率。
  • SkyWalking对远程过程调用框架支持的范围是最广的。国内及国际知名的框架,如Apache Dubbo、gRPC和Spring Cloud等都是该领域的佼佼者,而SkyWalking对这些框架都有比较成熟的解决方案。

3.2.2 外部服务

  • 外部服务通常包括这几种类型:中间件、数据存储和API服务。
1. 中间件
  • 常见的中间件一般包括以下两种类型。
    • 首先是消息队列。Kafka、RocketMQ这些常见的队列都是高性能数据处理的重要手段。SkyWalking对于这种消息队列中间件也有较好的支持,可以追踪到数据是如何写入到队列中,又是如何被消费掉的。数据在消息队列中是异步处理的,这是定位队列问题的难点,也是运维消息队列的痛点,针对这一点,SkyWalking给出了很好的解决方案。
    • 其次是与数据存储相关联的,也就是数据库中间件。常见的一种使用模式就是分库分表中间件,如Apache ShardingSphere。使用SkyWalking,可以看到一些数据库中间件是如何将一个请求拆分写入到多个数据库实例中的;并能追踪到一次数据库查询是如何在数据实例之间进行执行,哪个数据实例的响应是缓慢的,哪个数据库实例的执行产生了错误。
2. 数据库
  • 数据库是一种数据存储服务。SkyWalking的发布版本对主流开源的关系型数据库进行了支持,包括常见的H2、MySQL和PG数据库等。对于Oracle等商业数据库,SkyWalking借助社区的力量进行了支持,相关代码与构建物均放入社区库中,这主要是因为具有商业协议的组件是不允许包含在开源项目中。
  • 同时对于一些新型的数据库,如内存型数据库Redis文档型数据库MongoDB等,SkyWalking也进行了支持。
  • 目前SkyWalking均是在数据库驱动内植入相关插件来检查客户端对数据库的访问,并没有侵入数据库服务端。
3. API服务
  • 最后一种外部服务是API服务。通过SkyWalking,可以看到调用第三方API的过程,并观测到这些服务的质量和对系统关键路径的影响。SkyWalking在插件层面支持了多种API访问,通过客户端的自动数据埋点,支持HTTP协议、gRPC协议。通过这些插件,用户能够很容易地追踪这些外部API服务。
  • 最后需要强调的是,由于SkyWalking高效且便捷的定制能力,用户可以根据自己的系统建设情况,扩充已有的开源插件库,将企业内部大部分关键组件纳入其追踪范围之内。
  • 目前社区内部除核心的Java语言探针之外,同时有多种语言探针的实现,如.Net、PHP、Node.js和Go。这些探针都是由社区孵化的,并拥有广泛的用户群。

3.3 实战环境搭建

3.3.1 SkyWalking后台搭建

3.3.2 实战集群搭建

3.4 实战操作

  • 这一节将详细解读SkyWalking产生的各种监控指标的含义。
  • 本节首先会介绍监控指标的各种维度,这些维度是SkyWalking的内置概念,了解它们是掌握监控指标的基础。之后会介绍相关监控的核心功能,这部分包括一般的查看监控指标和使用拓扑图观察系统架构。最后将介绍生产系统中常见问题的定位,包括提取关键路径、查找失败服务或请求,以及查找慢服务或请求

3.4.1 观察微服务中的各个维度

  • 我们从UI上看一个具体的例子。如图3-4所示,projectA就是服务,/projectA/{name}是端点,{name}表示的是这个端点是个具有路径参数的URL。projectA-pid:23536@remote-worker-hk就是服务实例,其中remote-worker-hk是机器的主机的hostname, 23536为该实例的进程号。

3.4.2 观察指标

  • 监控系统的核心功能就是对于监控指标的观察。
  • 图3-5展示了服务监控指标的Dashboard,如服务数量、平均延迟、吞吐量、服务质量、延迟等高线、服务依赖关系和TopN指标等 。UI同时提供对于数据库相关指标展示的Dashboard,如图3-6所示。除了与服务监控Dashboard相同的指标外,慢SQL查询 是一个非常吸引人的功能,可以帮助用户快速定位数据库访问类的问题。未来将会有更多中间件(包括队列和缓存等)指标的展示

  • 另外,指标Dashboard是可以进行定制化的。

3.4.3 观察系统架构

  • 图3-8展示了该实战环境的拓扑关系,用户通过projectA服务访问集群,其为一个Spring MVC服务。projectA访问projectB和projectC两个Spring MVC服务。projectB访问本地的H2数据库。projectC访问www.baidu.com并同时向一台Kafka消息队列写入数据。projectD从该Kafka消费数据。projectA、projectB和projectC同时访问:8761服务,从我们的安装过程可知这是Eureka服务。
1. User点的产生
  • 把User理解为一个进入监测目标系统的入口
2. 访问外部服务
  • 可以通过访问服务的Client驱动程序来识别这些外部服务
  • SkyWalking的Agent探针有大量的插件用于识别这些外部服务,目前主流的中间件和数据库均涵盖其中。
3. 受监控服务的直接访问
  • 那么如果是受SkyWalking监控的两个服务直接调用呢?答案是Detect Point会同时产生Server和Client两套数据。
  • 读者会发现这里大部分指标都类似,只有响应时间出现略微的差异:Client端的延迟率高一些。这一点很好解释,那就是从客户端角度看,响应时间还包含网络的延迟,故其值要略高于Server端。

3.4.4 提取关键路径

  • 由于系统是动态变化的,SkyWalking的关键路径分析均是与时间相关联的,分为对于单次请求的路径分析和对于一段时间内的路径分析。它们分别使用如下两个工具。
1. 使用追踪查询
  • 图3-14最右侧为延迟时间条形图。通过这个条形图可以很容易发现延迟高的部分,同时对链路内各个追踪片的延迟有总体上的印象。故列表视图对观测延迟很有帮助。
  • 让我们使用如图3-15所示的表格视图(Table)来定位关键路径。
  • 我们可以看到该请求有两个入口,分别是projectA和Kafka的consumer。由于Kafka消费不会对用户体验产生影响,故我们只关注进入projectA的请求。
  • projectA分别访问了projectB和projectC,从Exec(%)列可以看到,这两个请求分别大约占到了projectA总延迟的一半,故我们可以说projectB和projectC都是关键路径上的点。
2. 使用拓扑图
  • 如果要观测一段时间内的关键路径,拓扑图是一个很好的辅助工具。图3-16和图3-17分别是projectA→projectB和projectA→projectC的调用详情。我们可以使用Avg Latency = Avg Response Time × Avg Throughput 来计算请求的流量分布,从图中的数据可以推导出projectB和projectC平分了projectA的响应时间。

3.4.5 查找失败服务或请求

  • 首先最直观的体现就是如图3-19中所示的变化。从图中可以看到不仅projectB变了颜色,projectA受其影响也变了颜色。
  • 如果你配置了告警的Webhook,将会收到相关告警信息,从而知道错误的产生。
  • 选择状态为Error的追踪数据,如图3-23所示。从追踪列表可得,主要原因或者说根本原因是projectB报错导致请求失败。我们可以接着点击projectB,获得如图3-24所示的具体错误原因。

3.4.6 查找慢服务或请求

  • SkyWalking推荐使用如图3-25所示的响应时间百分比图来观测延迟情况,该图使用50%、75%、90%、95%和99%请求响应线 (图中左侧从下往上排列)来衡量延迟对于整体的影响,帮助用户对当前系统延迟有更精确的把握。
  • 我们可以通过拓扑图来查找延迟的根源。这里我们以图3-27中的projectC举例。
  • 其平均延迟在1.7s左右。它有两个依赖的外部服务,让我们通过图3-28和图3-29分别看一下每个服务的延迟。两个外部服务合计占用了约0.5s, projectC本身消耗了约1.2s,那么主要延迟出现在projectC的内部逻辑中。

  • 也可以通过追踪数据进一步印证我们的观点,如图3-30所示,外部服务的延迟确实比较小。
  • 最后,另外一种常见的慢请求来自慢SQL 。如图3-31所示,Database的指标页面会列出来最主要的慢SQL,以方便用户快速解决主要的慢查询。

3.4.7 处理告警

  • SLO(Service-Level Objective,服务级别目标)
    • SLO是从Google的SRE体系发展而来的。在谈SLO之前,一般用户应该对SLA(Service-Level Agreement,服务级别协议)有所了解。
  • SLA 分为
    • SLI(Service-Level Indicator,服务级别指标),大多数服务将请求等待时间(返回对请求的响应需要多长时间)视为关键SLI。其他常见的SLI包括错误率和系统吞吐量(常以每秒请求数衡量)。
    • SLO,它是由SLI衡量的服务级别的目标值或值范围。因此,SLO的结构是SLI≤目标值,或下限值≤SLI≤上限值。例如,我们可能决定采用这样的SLO:平均查询请求延迟时间应小于100ms。
1. SLO设定
  • 选择适当的SLO是一件很难的事情。
    • 第一,你不一定能知道选择什么样的值。对于从互联网而来的HTTP请求,每秒查询(QPS)指标基本上由用户的需求决定,你不能以此为凭据设置SLO。
    • 第二,你希望每个请求的平均延迟小于200ms,而设置这样的目标可能反过来会激发开发人员去实现更低的延迟 ,或者加大投入购买更多的设备。这样虽然看起来是好事,但随着时间的推移,原有SLO会变得毫无意义
    • 第三,这点是比较微妙的。这两个SLI(QPS和延迟)可能有一定关联性,更高的QPS通常会导致更大的延迟,并且服务的性能在超出某些阈值后会出现大范围波动。
    • 设置SLO时要充分与用户积极沟通,设置合理的目标。用户对性能往往存在过于理想化的需求,如果没有设置目标的过程,非常容易得到一个不切实际的性能目标,甚至性能目标会与系统的设计和维护目标背道而驰。
2. 告警阈值设置
  • SLI对应为metrics-name和include-names。如果没有后者,该监控指标的所有服务均会被设置上此告警规则。告警阈值只支持数字类型。其中period和count需组合在一起使用。如"period=10, count=3"表示每10分钟内出现3次满足告警条件的情况,告警即被触发。silence-period表示告警触发后,如果有持续告警,必须超过该时间。默认它与period保持一致。这个参数是为了防止因频繁产生告警而影响维护人员的判断。
3. 告警结果通知
  • SkyWalking并没有插件化告警通知机制,而是使用Webhook将告警信息推送给一个HTTP服务,而后由该HTTP服务决定如何处理信息,可以选择发送到各种通知渠道,如邮件、微信和手机短信等,也可以触发多样的自动故障恢复机制。这些策略完全由用户控制。
  • SkyWalking从6.5.0版本开始,可以通过动态配置模块去配置告警规则和结果通知。由于是动态生效,规则会在一个时间窗口后才生效。
4. 消除告警结果
  • 获得通知或者主动发现告警信息后,可以通过如图3-32所示的告警页面进行查找。
  • 重新打包并部署projectB服务,现在我们发现相关告警信息已经消除了。

3.5 本章小结

  • 下一章,我们将开始深入到SkyWalking的实现、模型和设计层面,进一步了解SkyWalking如何实现本章介绍的各种特性。
相关推荐
AOwhisky2 小时前
Linux(CentOS)系统管理入门笔记(第一期)——从 Multics 到主流发行版
linux·运维·笔记·centos·云计算
逸模2 小时前
逸模智造・BIM 效能专栏一|极速土建翻模,2D 一键跨越 3D
笔记·3d·bim·土建·翻模
Piko61413 小时前
H3C IRF2 堆叠实战:打造高可靠核心交换网络
运维·网络·笔记
dexi.Chi 攻城狮18 小时前
SQL层次查询语法
经验分享·笔记·sql
HERR_QQ19 小时前
强化学习的数学原理 学习笔记
人工智能·笔记·学习·自动驾驶
liuyicenysabel1 天前
多服务上线日记二:
服务器·笔记·学习
辰海Coding1 天前
MiniSpring框架学习笔记-动态代理:如何在运行时插入逻辑?
java·笔记·学习·spring·动态代理
凉、介1 天前
ARMv8 架构下的刷 Cache 操作
c语言·笔记·学习·架构·嵌入式·arm