架构10-可观测性

零、文章目录

架构10-可观测性

1、可观测性

(1)可观测性的背景
  • **历史沿革:**可观测性最初由匈牙利数学家鲁道夫·卡尔曼提出,用于线性动态控制系统。后来,该概念被引入到计算机科学中。
  • **现代意义:**在分布式系统和云原生时代,可观测性成为不可或缺的属性,与可并发性、可用性、安全性等并列,成为系统的非功能属性之一。
(2)可观测性的定义与特征
  • **定义:**可观测性是指"可以由系统的外部输出推断其内部状态的程度"。
  • 三个方向:
    • **日志收集:**记录离散事件,通过这些记录事后分析出程序的行为。
    • **链路追踪:**主要用于排查故障,分析调用链的哪一部分、哪个方法出现错误或阻塞,输入输出是否符合预期。
    • **聚合度量:**对系统中某一类信息的统计聚合,主要用于监控和预警,当某些度量指标达到风险阈值时触发事件。
(3)工业界的遥测产品
  • 日志领域:
    • Elastic Stack (ELK):目前主导日志收集和分析的技术栈。
    • Fluentd:有取代Logstash的趋势,形成EFK技术栈。
  • 度量领域:
    • Prometheus:在云原生时代成为度量监控的事实标准,社区活跃度高。
  • 追踪领域:
    • **特性:**与具体网络协议、程序语言密切相关,具有较强的侵入性。
    • 主流产品:
      • Datadog:一揽子商业方案。
      • AWS X-Ray 和 Google Stackdriver Trace:云计算厂商产品。
      • SkyWalking、Zipkin、Jaeger:开源社区产品。
    • 发展趋势:
      • OpenTelemetry:融合日志、追踪、度量三者所长,有望成为统一可观测性的解决方案。

2、日志收集

(1)日志的基本概念
  • **定义: **日志主要用于记录系统运行期间发生的离散事件。
  • **普遍性: **几乎所有的生产系统都会有日志功能,但往往不被重视。
(2)日志的重要性
  • **记录信息: **日志能够记录系统运行的关键信息,帮助诊断问题。
  • **复杂性: **随着系统复杂度的增加,日志的管理和分析变得越来越重要。
(3)日志的输出
  • **概念 **
    • 输出是日志处理的第一步,也是最基础的步骤。良好的日志输出不仅能够帮助开发者和运维人员快速定位问题,还能为后续的分析和监控提供可靠的数据源。
  • 输出的基本原则
    • 格式统一
      • **格式一致:**日志的格式应该统一,便于后续的解析和处理。常见的格式包括 JSON、CSV 等。
      • **字段规范:**日志中应该包含必要的字段,如时间戳、日志级别、服务名、请求 ID 等。
    • 内容恰当
      • **内容适当:**日志内容应该既不过多也不过少,关键在于"恰当"。
  • 不该出现的内容不要有:
    • 敏感信息:避免将密码、银行账号、身份证号等敏感信息记录到日志中。这些信息一旦泄露,将带来严重的安全风险。
    • **调试信息:**避免在生产环境中输出大量的调试信息,如方法输入参数、输出结果、方法执行时长等。这些信息不仅占用大量存储空间,还可能暴露敏感数据。
    • **堆栈信息:**除非必要,否则不要在日志中输出完整的堆栈信息。这可能会导致误判,增加问题排查的难度。
  • 该出现的内容不要少:
    • **TraceID:**在分布式系统中,每个请求应该有一个唯一的 TraceID,用于追踪请求在各个服务节点中的执行情况。
    • **重要事件:**系统进行的操作、异常情况、未处理的异常或警告、定期任务等重要事件都应该记录在日志中。
    • **配置信息:**系统启动时或配置发生变化时,应将非敏感的配置信息输出到日志中,便于后续的诊断和复现。
  • 日志级别
    • **合理选择日志级别:**根据事件的重要程度,选择合适的日志级别(如 DEBUG、INFO、WARNING、ERROR、FATAL)。这有助于在日志量较大时,快速定位关键信息。
    • **动态调整日志级别:**在生产环境中,可以根据需要动态调整日志级别,以减少对性能的影响。
  • 性能考虑
    • **避免过度输出:**虽然日志记录很重要,但过度输出会影响系统性能。可以通过采样、限流等手段,控制日志输出的数量。
    • **异步输出:**使用异步日志框架(如 Logback 的 AsyncAppender),减少日志输出对主业务流程的影响。
  • 工具和框架
    • **日志框架:**选择合适的日志框架,如 SLF4J、Log4j、Logback 等,这些框架提供了丰富的功能和良好的扩展性。
    • **MDC:**使用 Mapped Diagnostic Context(MDC)机制,可以在日志中自动添加上下文信息,如用户 ID、请求 ID 等。
  • 示例:假设我们正在开发一个 Web 应用,以下是一个合理的日志输出示例:
    • timestamp:记录日志的时间戳。
    • level:日志级别,这里是 INFO。
    • service:服务名,便于区分不同的服务。
    • traceId:唯一的请求 ID,用于追踪请求。
    • userId:用户 ID,便于后续分析。
    • message:日志的具体内容。
json 复制代码
{
  "timestamp": "2023-10-01T12:34:56.789Z",
  "level": "INFO",
  "service": "user-service",
  "traceId": "1234567890abcdef",
  "userId": "user123",
  "message": "User login successful"
}
(4)日志的收集与缓冲
  • 收集
    • **目的:**将分布在各个服务节点上的日志文件统一收集起来,集中存储和索引,以便进行全局查询和分析。
    • **背景:**在分布式系统中,一个请求可能会跨越多个服务节点,因此需要一个全局的日志系统来覆盖整个调用链路。
    • 工具:
      • **Logstash:**最初 ELK(Elastic Stack)中的日志收集和加工聚合工作都是由 Logstash 承担的。Logstash 既可以作为收集的客户端(Shipper)部署在各个节点上,也可以作为服务端(Master)独立部署。
      • **Filebeat:**后来,Elastic.co 公司推出了基于 Libbeat 框架的 Filebeat,使用 Golang 重写,更加轻量高效,适合在每个服务节点上部署。
      • **Community Beats:**社区维护的大量 Beats 插件,可以收集各种不同类型的数据,使得 ELK 在一定程度上可以替代度量和追踪系统。
  • 缓冲
    • **目的:**缓解日志收集和处理过程中可能出现的性能瓶颈,保证日志数据的连续性和完整性。
    • **挑战:**在大型分布式系统中,日志量非常大,例如淘宝每天的日志量超过 10PB,日志收集器的部署实例数达到百万量级,保持日志数据的绝对一致性非常困难。
    • 解决方案:
      • **队列缓存:**在 Logstash 和 Elasticsearch 之前,架设一个抗压能力更强的队列缓存,如 Kafka 或 Redis。
      • 作用:
        • **削峰填谷:**当 Logstash 或 Elasticsearch 处理能力出现瓶颈时,队列缓存可以暂时存储日志数据,防止数据丢失。
        • **提高可靠性:**即使 Logstash 或 Elasticsearch 短时间停顿,也不会丢失日志数据。
  • 关键点
    • **数据覆盖:**日志收集器必须覆盖所有数据来源,确保日志数据的完整性和连续性。
    • **性能优化:**通过轻量级的收集器(如 Filebeat)和抗压能力强的队列缓存(如 Kafka),优化日志处理的性能。
    • **数据质量:**在可承受的代价范围内,尽可能保证较高的数据质量,而不是追求绝对的完整精确。
(5)日志的加工与聚合
  • 加工
    • 目的:
      • **结构化数据:**将非结构化的日志数据转换为结构化数据,以便于后续的查询、统计和聚合。
      • **数据清洗:**去除无效或无关的信息,确保数据的质量。
      • **数据增强:**添加额外的元数据或信息,使数据更加丰富和有用。
    • 工具:
      • **Logstash:**Elastic Stack 中的核心组件之一,主要用于日志数据的加工和转换。
      • **Grok 表达式:**Logstash 使用 Grok 表达式来解析和提取日志中的字段。
    • 具体步骤:
      • **解析日志行:**使用 Grok 表达式将日志行中的各个字段解析出来。
      • **数据清洗:**去除无效或无关的信息,例如删除不必要的日志行或字段。
      • **数据转换:**将解析出的字段转换为合适的格式,例如将时间戳转换为统一的时间格式。
      • **数据增强:**添加额外的元数据,例如将 IP 地址转换为地理位置信息。
    • **示例:**假设有一行 Nginx 服务器的 Access Log:
plain 复制代码
14.123.255.234 - - [19/Feb/2020:00:12:11 +0800] "GET /index.html HTTP/1.1" 200 1314 "https://icyfenix.cn" "Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/80.0.3987.163 Safari/537.36"
    * 使用 Grok 表达式可以将其解析为以下结构化数据:
json 复制代码
{
  "ip": "14.123.255.234",
  "timestamp": "19/Feb/2020:00:12:11 +0800",
  "request": "GET /index.html HTTP/1.1",
  "status": 200,
  "size": 1314,
  "referrer": "https://icyfenix.cn",
  "user_agent": "Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/80.0.3987.163 Safari/537.36"
}
  • 聚合
    • 目的:
      • **统计分析:**从大量的日志数据中提取有用的统计信息。
      • **数据可视化:**将统计结果以图表等形式展示,便于观察和分析。
    • 工具:
      • **Elasticsearch:**提供强大的聚合功能,可以进行实时的统计分析。
      • **Logstash:**可以在数据处理过程中生成固定的聚合指标。
    • 具体步骤:
      • **实时聚合:**使用 Elasticsearch 的聚合功能进行实时的统计分析。
      • **固定聚合:**在 Logstash 中通过聚合插件生成固定的聚合指标。
    • **示例:**假设我们想从 Nginx 的 Access Log 中统计每小时的请求数量和响应状态码的分布。
      • **实时聚合:**使用 Elasticsearch 的聚合查询:
json 复制代码
GET /nginx_access_logs/_search
{
  "size": 0,
  "aggs": {
    "requests_per_hour": {
      "date_histogram": {
        "field": "timestamp",
        "calendar_interval": "hour"
      }
    },
    "status_codes": {
      "terms": {
        "field": "status"
      }
    }
  }
}
- **固定聚合:**在 Logstash 中配置聚合插件,生成固定的聚合指标:
yaml 复制代码
input {
  file {
    path => "/var/log/nginx/access.log"
  }
}
 
filter {
  grok {
    match => { "message" => "%{COMBINEDAPACHELOG}" }
  }
  date {
    match => [ "timestamp", "dd/MMM/yyyy:HH:mm:ss Z" ]
  }
  aggregate {
    task_id => "%{[@metadata][aggregate_id]}"
    code => "map['requests'] ||= 0; map['requests'] += 1"
    timeout => 3600
    timeout_code => "event.set('requests', event.get('requests'))"
    timeout_tags => ["aggregated"]
  }
}
 
output {
  elasticsearch {
    hosts => ["localhost:9200"]
    index => "nginx_aggregated_logs"
  }
}
(6)日志的存储与查询
  • Elasticsearch 的核心地位
    • Elasticsearch 是 Elastic Stack 技术栈的核心组件,专门用于日志分析。
    • 优势:
      • **优秀的全文检索能力:**适合处理非结构化的日志数据。
      • **近实时性:**日志数据可以在生成后不久即可被查询,满足实时监控的需求。
      • **高扩展性:**支持水平扩展,可以处理大规模的日志数据。
  • 时间范围索引
    • **时间特性:**日志数据是基于时间的数据流,已写入的数据很少会变动。
    • 索引策略:
      • **按时间范围索引:**通常按日、周、月等时间单位创建索引。
      • **预创建索引:**可以提前创建未来的索引,避免动态创建带来的开销。
      • **索引别名:**使用 logs_current 这样的别名指向当前索引,方便管理和查询。
  • 冷热数据分离
    • **数据价值:**日志数据的价值随着时间的推移逐渐降低。
    • 硬件策略:
      • **热数据:**使用高性能的 SSD 磁盘和强大的处理器。
      • **冷数据:**使用低成本的 HDD 磁盘和较弱的处理器,甚至可以归档到对象存储(如阿里云的 OSS、腾讯云的 COS、AWS 的 S3)中。
  • 查询能力
    • **API 层面:**Elasticsearch 提供了丰富的 API,支持复杂的查询和聚合操作。
    • Kibana 集成:
      • **图形界面:**Kibana 是 Elastic Stack 的 GUI 部分,提供友好的操作界面。
      • **数据探索与可视化:**Kibana 支持数据的探索、可视化,帮助用户快速发现系统中的问题和趋势。
  • 应用场景
    • **可观测性:**日志在系统可观测性方面的作用,主要用于监控和故障排查。
    • **大数据挖掘:**虽然日志也可以用于业务热点分析、用户习惯分析等大数据挖掘场景,但这些场景更可能采用 HBase 与 Spark 的组合,而不是 Elastic Stack。

3、链路追踪

(1)追踪与跨度
  • **追踪 (Trace):**从客户端发起请求抵达系统的边界开始,记录请求流经的每一个服务,直到向客户端返回响应为止,这整个过程称为一次 追踪(Trace)。
  • **跨度 (Span):**每次开始调用服务前,系统都会先埋入一个调用记录,这个记录称为一个 跨度(Span)。Span 用于记录具体调用了哪些服务,以及调用的顺序、开始时点、执行时长等信息。
  • Span 的数据结构应该具备以下特点:
    • **简单性:**足够简单,以便于能放在日志或者网络协议的报文头里。
    • **完备性:**至少包含时间戳、起止时间、Trace 的 ID、当前 Span 的 ID、父 Span 的 ID 等信息。
  • 追踪树 (Trace Tree)
    • 每次 Trace 都是由若干个有顺序、有层级关系的 Span 组成的一颗 追踪树(Trace Tree)。
    • 追踪树的结构如下图所示:
plain 复制代码
Trace 
├── Span 1
│   ├── Span 1.1
│   └── Span 1.2
└── Span 2 
    └── Span 2.1
(2)追踪的目标与实现
  • 目的
    • **故障排查:**通过追踪记录的时间信息和响应结果(正常或异常返回),可以定位到缓慢或者出错的服务。
    • **性能分析:**将 Trace 与历史记录进行对比统计,可以从系统整体层面分析服务性能,定位性能优化的目标。
  • 实现
    • **低性能损耗:**分布式追踪不能对服务本身产生明显的性能负担。
    • **对应用透明:**追踪系统通常是运维期才事后加入的系统,应尽量以非侵入或者少侵入的方式来实现追踪,对开发人员做到透明化。
    • **随应用扩缩:**现代的分布式服务集群有根据流量压力自动扩缩的能力,追踪系统也应能自动跟随。
    • **持续的监控:**追踪系统必须能够 7x24 小时工作,以定位系统偶尔抖动的行为。
(3)数据收集
  • 基于日志的追踪 (Log-Based Tracing)
    • 优点:
      • **低侵入性:**对网络消息完全没有侵入性,对应用程序只有少量的侵入性。
      • **低性能损耗:**对性能的影响非常低。
    • 缺点:
      • **依赖日志归集:**直接依赖于日志归集过程,日志本身不追求绝对的连续与一致,可能导致追踪不够精准。
      • **延迟和缺失:**业务服务的调用与日志的归集不是同时完成的,可能导致日志出现延迟或缺失记录,从而产生追踪失真。
    • 应用场景:
      • 适用于中小型应用,尤其是对性能敏感的应用。
      • 适合对追踪精度要求不高的场景。
    • 代表产品:Spring Cloud Sleuth
      • 示例日志:
plain 复制代码
调用端日志输出:
Created new Feign span [Trace: cbe97e67ce162943, Span: bb1798f7a7c9c142, Parent: cbe97e67ce162943, exportable: false ]
2019 -06 -30 09 : 43 : 24.022 [http - nio -9010 - exec -8 ] DEBUG o.s.c.s.i.web.client.feign.TraceFeignClient - The modified request equals GET http: / / localhost: 9001 / product / findAll HTTP / 1.1 X - B3 - ParentSpanId: cbe97e67ce162943 X - B3 - Sampled: 0 X - B3 - TraceId: cbe97e67ce162943 X - Span - Name: http: / product / findAll X - B3 - SpanId: bb1798f7a7c9c142 
 
服务端日志输出:
[findAll] to a span [Trace: cbe97e67ce162943, Span: bb1798f7a7c9c142, Parent: cbe97e67ce162943, exportable: false ]
Adding a class tag with value [ProductController] to a span [Trace: cbe97e67ce162943, Span: bb1798f7a7c9c142, Parent: cbe97e67ce162943, exportable: false ]
  • 基于服务的追踪 (Service-Based Tracing)
    • 优点:
      • 高精确性:追踪的精确性与稳定性都有所保证,不必再依靠日志归集来传输追踪数据。
      • 详细信息:可以获取详细的调用信息,如参数、变量等方法级调用信息。
    • 缺点:
      • **资源消耗:**会比基于日志的追踪消耗更多的资源,具有较强的侵入性。
      • **性能压力:**对应用系统的性能压力较大,一般仅在除错时开启。
    • 应用场景:
      • 适用于需要高精度追踪的场景。
      • 适合大型系统,尤其是在除错和性能分析时。
    • 代表产品:
      • Zipkin
      • SkyWalking
      • Pinpoint
    • 示例截图:
      • Pinpoint 的追踪效果截图展示了详细的调用信息,包括参数、变量等。
  • 基于边车代理的追踪 (Sidecar-Based Tracing)
    • 优点:
      • 完全透明:对应用完全透明,无论是日志还是服务本身都不会有任何变化。
      • 语言无关:与程序语言无关,无论应用采用什么编程语言实现,只要通过网络访问服务,就可以被追踪到。
    • **独立数据通道:**有自己独立的数据通道,避免了追踪对程序通信或日志归集的依赖和干扰,保证了最佳的精确性。
    • 缺点:
      • **服务网格普及度:**目前服务网格还不够普及,限制了其广泛应用。
      • **服务调用层面:**只能实现服务调用层面的追踪,无法实现本地方法调用级别的追踪诊断。
    • 应用场景:
      • 适用于云原生环境,尤其是使用服务网格的场景。
      • 适合对追踪透明度和精确性要求极高的场景。
    • 代表产品:
      • Envoy
      • SkyWalking
      • Zipkin
      • Jaeger
      • LightStep Tracing
    • 示例集成:
      • Envoy 作为边车代理,可以与 SkyWalking、Zipkin 等系统集成,充当数据收集端。
(4)追踪规范化
  • 追踪规范化的背景与重要性
    • 背景
      • **Dapper 论文的影响力:**Google 发表的 Dapper 论文为分布式追踪系统提供了基础思路,但并未形成有约束力的标准。这导致市场上出现了多种追踪系统,如 Zipkin、SkyWalking、Pinpoint 等,它们虽然功能相似,但互不兼容。
      • **市场竞争激烈:**追踪领域的竞争比日志和度量更为激烈,没有一家公司或产品占据主导地位。各家公司都在努力推出自己的追踪系统,导致市场碎片化。
    • 重要性
      • **互操作性:**规范化可以确保不同厂商的追踪系统能够互相通信和协作,减少用户的迁移成本。
      • **标准化:**规范化的标准可以为追踪系统的开发和集成提供统一的指导,促进技术的发展和创新。
      • **生态系统建设:**通过规范化,可以吸引更多开发者和企业参与到追踪系统的生态建设中,推动整个行业的进步。
  • **主要的追踪规范 **
    • OpenTracing
      • **概述:**OpenTracing 是一套与平台无关、与厂商无关、与语言无关的追踪协议规范。它旨在提供一个标准化的层,位于应用程序与追踪系统之间,使得不同的追踪系统可以互相通信。
      • 特点:
        • **标准化层:**提供了一个薄的标准化层,使得探针和追踪系统可以互相通信。
        • **跨语言支持:**支持多种编程语言,确保不同语言的应用程序可以使用相同的追踪标准。
        • **API 规范:**定义了微服务之间在发生调用时如何传递 Span 信息(OpenTracing Payload)。
    • OpenCensus
      • **概述:**OpenCensus 是由 Google 提出的另一套追踪和度量规范。它不仅涉及追踪,还涵盖了指标度量,并提供了数据采集的探针和收集器。
      • 特点:
        • **综合性:**不仅包括追踪,还涵盖了度量,提供了一个更全面的可观测性解决方案。
        • **SDK 支持:**提供了多种语言的 SDK,方便开发者集成。
        • **数据采集:**不仅定义了规范,还提供了数据采集的工具和库。
    • OpenTelemetry
      • **概述:**OpenTelemetry 是 OpenTracing 和 OpenCensus 合并后的产物,旨在统一追踪、度量和日志三大领域的规范。
      • 特点:
        • **统一性:**整合了 OpenTracing 和 OpenCensus 的优势,提供了一个更全面的可观测性解决方案。
        • **广泛支持:**得到了众多厂商的支持,包括 Google、Microsoft 等。
        • **模块化:**包括了追踪规范、度量规范、日志规范、各种语言的 SDK 以及采集系统的参考实现。
        • **社区活跃:**作为一个 CNCF 孵化项目,OpenTelemetry 拥有活跃的社区和丰富的资源。
  • 追踪规范化的发展趋势
    • 统一标准
      • **OpenTelemetry 的崛起:**OpenTelemetry 的出现标志着追踪规范化的一个重要里程碑。它不仅整合了 OpenTracing 和 OpenCensus 的优势,还得到了广泛的行业支持,有望成为未来的标准。
      • **厂商支持:**越来越多的厂商和项目开始支持 OpenTelemetry,包括 Zipkin、Jaeger、SkyWalking 等。
    • 生态系统扩展
      • **工具和库的丰富:**随着 OpenTelemetry 的普及,相关的工具和库也在不断丰富,为开发者提供了更多的选择。
      • **社区贡献:**活跃的社区贡献使得 OpenTelemetry 不断完善,新的功能和改进持续推出。
    • 未来展望
      • **标准化的推进:**随着 OpenTelemetry 的发展,追踪系统的标准化将进一步推进,互操作性和生态系统的建设将更加完善。
      • **技术创新:**规范化为技术创新提供了基础,未来可能会出现更多创新的追踪技术和解决方案。

4、聚合度量

(1)度量的定义
  • **计数度量器(Counter):**对有相同量纲、可加减数值的合计量,例如销售额、服务调用次数等。
  • **瞬态度量器(Gauge):**表示某个指标在某个时点的数值,例如当前内存使用量、网站在线人数等。
  • **吞吐率度量器(Meter):**统计单位时间的吞吐量,例如TPS(每秒事务数)、港口的货运吞吐率等。
  • **直方图度量器(Histogram):**记录具体数值的二维统计图,例如GDP变化情况。
  • **采样点分位图度量器(Quantile Summary):**评估理论值与实际值之间的拟合度,例如高考成绩分布。
(2)指标收集
  • 核心思想
    • **如何定义指标:**确定需要收集哪些指标及其数据类型。
    • **如何将这些指标告诉服务端:**选择合适的采集方式将指标数据传递给服务端。
  • **如何定义指标:**定义指标时,需要考虑以下几种常见的度量器类型:
    • 计数度量器(Counter):
      • **定义:**对有相同量纲、可加减数值的合计量。
      • **示例:**销售额、货物库存量、职工人数、服务调用次数、网站访问人数等。
    • 瞬态度量器(Gauge):
      • **定义:**表示某个指标在某个时点的数值,不需要进行加减统计。
      • **示例:**Java 虚拟机堆内存的使用量、网站在线人数等。
    • 吞吐率度量器(Meter):
      • **定义:**用于统计单位时间内的吞吐量,即单位时间内某个事件的发生次数。
      • **示例:**交易系统的 TPS(每秒事务交易数)、港口的货运吞吐率(吨/每天)等。
    • 直方图度量器(Histogram):
      • **定义:**常见的二维统计图,记录具体数值。
      • **示例:**经济报告中,以 GDP 为纵坐标、时间为横坐标构成的直方图。
    • 采样点分位图度量器(Quantile Summary):
      • **定义:**通过比较各分位数的分布情况,评估理论值与实际值之间的拟合度。
      • **示例:**高考成绩的正态分布情况。
    • 除了上述常见的度量器之外,还有 Timer、Set、Fast Compass、Cluster Histogram 等其他类型的度量器。不同的度量系统支持的度量器类型可能会有所不同,例如 Prometheus 支持 Counter、Gauge、Histogram 和 Summary 四种度量器。
  • 将指标传递给服务端通常有两种解决方案:
    • 拉取式采集(Pull-Based Metrics Collection):
      • **定义:**度量系统主动从目标系统中拉取指标。
      • **优点:**简化了目标系统的实现,减少了目标系统的负担。
      • **缺点:**目标系统需要对外提供可访问的端点,适用于目标系统较为稳定的情况。
      • **示例:**Prometheus 默认采用 Pull 方式。
    • 推送式采集(Push-Based Metrics Collection):
      • **定义:**目标系统主动向度量系统推送指标。
      • **优点:**适用于目标系统位于内网或生命周期较短的情况。
      • **缺点:**增加了目标系统的实现复杂度。
      • **示例:**Ganglia、Graphite、StatsD 等。
  • 兼容性解决方案Push Gateway:
    • **定义:**位于 Prometheus Server 外部的中介模块,用于暂存目标系统推送的指标。
    • **作用:**解决 Pull 的一些固有缺陷,如目标系统位于内网、短生命周期服务等。
    • **工作原理:**目标系统将指标推送到 Push Gateway,Prometheus Server 从 Push Gateway 中拉取指标。
  • 网络访问协议和数据结构
    • **标准协议:**虽然定义标准协议(如 SNMP、WMI、JMX)在特定领域内有应用,但缺乏广泛适用性。
    • **HTTP 访问:**Prometheus 采用 HTTP 访问度量端点的方式,目标系统需要提供符合 Prometheus 格式的 HTTP 端点。
    • **Exporter:**对于不支持 HTTP 端点的目标系统,可以使用 Exporter 作为中介,将指标转换为 Prometheus 格式。
(3)存储查询
  • 存储挑战
    • **数据量巨大:**在一个中等规模的微服务系统中,每天生成的度量数据量可能达到数十亿条记录。
    • **写多读少:**度量数据通常是频繁写入,但读取相对较少。
    • **数据不可变:**度量数据一旦写入,很少会被修改或删除。
    • **数据有序:**度量数据按时间顺序生成,需要高效的时间范围查询能力。
  • 存储解决方案
    • 时序数据库的特点
      • **数据结构简单:**每个度量指标由时间戳、名称、值和一组标签构成。
      • **写操作为主:**数据通常是追加写入,很少进行修改或删除。
      • **时间索引:**数据按时间顺序存储,支持高效的时间范围查询。
      • **数据压缩:**通过压缩技术减少存储空间占用。
      • **数据保留策略:**根据数据的重要性和查询需求,设置数据保留时间,过期数据自动删除。
    • 典型的时序数据库
      • **Prometheus:**内置了一个强大的时序数据库,使用 LSM-Tree 结构,支持高效的写操作和查询。
      • **InfluxDB:**提供类 SQL 风格的查询语言,广泛用于物联网和监控场景。
      • **OpenTSDB:**基于 HBase 构建,适用于大规模集群环境。
      • **TimescaleDB:**基于 PostgreSQL 的扩展,支持 SQL 查询,适合需要复杂查询的场景。
  • 存储优化技术
    • **LSM-Tree:**Log Structured Merge Tree 是一种专门为写多读少场景设计的存储结构,能够高效处理大量的写操作。
    • **数据保留策略:**根据数据的重要性和查询需求,设置合理的数据保留时间,过期数据自动删除,节省存储空间。
    • **数据重采样:**对历史数据进行重采样,减少存储空间占用。例如,最近几天的数据精确到秒,而几个月前的数据精确到天。
    • **轮替型数据库(RRD):**以环形缓冲的方式存储固定数量的最新数据,超期数据被轮替覆盖,适用于需要持续监控的场景。
  • 查询语言
    • **PromQL:**Prometheus 提供的查询语言,支持丰富的查询、聚合和逻辑运算。PromQL 的语法类似于带运算与函数支持的 CSS 选择器。
    • **InfluxQL:**InfluxDB 提供的类 SQL 风格的查询语言,支持复杂的查询操作。
    • **SQL:**某些时序数据库(如 TimescaleDB)支持标准的 SQL 查询,便于用户使用熟悉的查询语言进行数据分析。
  • 实际应用示例
    • 假设我们要查询某个网站的访问人数,可以使用 PromQL 进行如下查询:
plain 复制代码
total_website_visitors{host="icyfenix.cn", job="prometheus"}
- 这条查询语句会返回 `icyfenix.cn` 网站的访问人数,其中 `host` 和 `job` 是标签,用于过滤特定的数据。
(4)监控预警
  • 监控预警的目的
    • **及时发现系统异常:**通过实时监控系统的关键指标,可以在问题发生初期就及时发现并处理。
    • **预防潜在问题:**通过对历史数据的分析,可以预测未来的趋势,从而提前采取措施避免问题发生。
    • **提高系统性能:**通过对系统性能指标的监控,可以优化系统配置,提升整体性能。
    • **快速故障定位:**在系统出现故障时,可以通过监控数据快速定位问题所在,减少故障恢复时间。
  • 监控预警的组成部分
    • 客户端指标收集
      • 如何定义指标:常见的度量器类型包括:
        • **计数度量器(Counter):**累计某个量纲的数值,如销售额、服务调用次数等。
        • **瞬态度量器(Gauge):**表示某个指标在某个时点的数值,如当前内存使用量、在线人数等。
        • **吞吐率度量器(Meter):**统计单位时间内的吞吐量,如TPS、货运吞吐率等。
        • **直方图度量器(Histogram):**记录统计样本及其属性的分布,如GDP变化情况。
        • **采样点分位图度量器(Quantile Summary):**评估实际值与理论值的拟合度,如高考成绩分布。
      • 如何将这些指标告诉服务端:常见的采集方式包括:
        • **拉取式采集(Pull-Based Metrics Collection):**度量系统主动从目标系统中拉取指标。
        • **推送式采集(Push-Based Metrics Collection):**目标系统主动向度量系统推送指标。
    • 服务端存储查询
      • 服务端负责存储和查询度量指标,通常使用时序数据库来存储大量的度量数据。时序数据库的特点包括:
        • **数据结构简单:**每个度量指标由时间戳、名称、值和一组标签构成。
        • **写多读少:**时序数据通常是追加写入,很少删除或修改。
        • **数据保留策略:**可以根据过期时间自动删除相关数据,节省存储空间。
        • **数据再采样:**对历史数据进行再采样,以节省存储空间。
      • Prometheus 服务端内置了一个强大的时序数据库,并提供了一个名为 PromQL 的数据查询语言,可以对时序数据进行丰富的查询、聚合和逻辑运算。
    • 终端监控预警
      • **Grafana:**一个开源的度量分析和可视化套件,可以与 Prometheus 等度量系统集成,提供丰富的图表和仪表板。
      • **Alert Manager:**Prometheus 提供的专门用于预警的组件,可以根据预设的规则触发预警,并通过多种渠道通知管理员。
  • 监控预警的具体实现(以 Prometheus 为例)
    • **定义指标:**在目标系统中定义需要收集的度量指标,并使用 Prometheus 的 Client Library 或 Exporter 将指标暴露给 Prometheus。
    • **配置采集方式:**选择合适的采集方式(Pull 或 Push),配置 Prometheus Server 从目标系统中拉取或接收指标。
    • **存储数据:**Prometheus 服务端将收集到的指标存储在内置的时序数据库中。
    • **配置查询:**使用 PromQL 编写查询语句,从时序数据库中提取所需的度量数据。
    • **展示数据:**通过 Grafana 等工具将度量数据可视化,生成图表和仪表板。
    • **设置预警:**在 Prometheus 中配置 Alert Manager,设置预警规则和通知渠道,当指标达到预设条件时触发预警。
  • 监控预警的工具和最佳实践
    • 工具:
      • **Prometheus:**强大的度量系统,支持多种度量器类型和数据查询语言。
      • **Grafana:**开源的度量分析和可视化工具,与 Prometheus 集成度高。
      • **Alert Manager:**Prometheus 的预警组件,支持多种通知渠道。
      • **Zabbix:**老牌的度量系统,支持多种度量协议。
    • 最佳实践:
      • **定义关键指标:**选择对系统稳定性影响最大的指标进行监控。
      • **合理配置采集频率:**根据系统负载和需求,合理设置采集频率,避免过度采集导致性能下降。
      • **使用时序数据库:**选择适合度量数据存储的时序数据库,如 Prometheus 内置的时序数据库。
      • **定期审查和优化:**定期审查监控数据和预警规则,优化配置以提高监控效果。
      • **多渠道通知:**配置多种通知渠道,确保在紧急情况下能够及时收到预警信息。
相关推荐
快乐非自愿3 小时前
分布式系统架构2:服务发现
架构·服务发现
2401_854391083 小时前
SSM 架构中 JAVA 网络直播带货查询系统设计与 JSP 有效实现方法
java·开发语言·架构
264玫瑰资源库3 小时前
从零开始C++棋牌游戏开发之第二篇:初识 C++ 游戏开发的基本架构
开发语言·c++·架构
神一样的老师3 小时前
面向高精度网络的时间同步安全管理架构
网络·安全·架构
2401_857026233 小时前
基于 SSM 架构的 JAVA 网络直播带货查询系统设计与 JSP 实践成果
java·开发语言·架构
9527华安3 小时前
FPGA实现MIPI转FPD-Link车载同轴视频传输方案,基于IMX327+FPD953架构,提供工程源码和技术支持
fpga开发·架构·mipi·imx327·fpd-link·fpd953
DT辰白3 小时前
如何解决基于 Redis 的网关鉴权导致的 RESTful API 拦截问题?
后端·微服务·架构
老猿讲编程5 小时前
技术发展历程:从 CORBA 到微服务
微服务·云原生·架构
碳学长6 小时前
2025系统架构师(一考就过):案例题之一:嵌入式架构、大数据架构、ISA
大数据·架构·系统架构
brzhang8 小时前
十年磨一剑:那些关于长期软件开发的思考,架构设计中如何做好技术选型
前端·后端·架构