目录

    Phoenix监控平台技术解析(一):全景概览与架构设计


    Phoenix监控平台技术解析(一):全景概览与架构设计

    这是 Phoenix监控平台技术解析 系列博客的第一篇。本系列将从宏观到微观,由浅入深地拆解Phoenix这个开源监控平台的设计思路、技术选型与核心实现。本篇作为开篇,带你建立对整个项目的全局认知。


    一、为什么需要一个监控平台?

    在分布式系统日益普及的今天,一个中等规模的项目可能同时运行着数十个应用实例、若干台服务器、多种数据库、容器化服务以及各类网络设备。面对如此复杂的运行环境,以下痛点几乎无法回避:

    • 黑盒运行:服务是否健康?CPU、内存是否即将耗尽?磁盘还剩多少?如果没有监控,一切只能靠猜。
    • 故障后知后觉:用户反馈"系统挂了",你才开始排查——此时损失已经造成。
    • 排查效率低:日志散落在各台机器上,JVM状态需要逐个连接jconsole查看,数据库慢SQL更是无从追溯。
    • 告警能力缺失:即使发现了问题指标,也没有统一的通道把告警推送给相关人员。

    Phoenix 就是为了解决这些问题而生的。它不是一个"大而全"的 APM 平台,而是一个实用、轻量、灵活可配置 的监控系统——既能监控基础设施(服务器、网络、Docker),也能监控应用程序(Java进程、JVM、线程池),还能对接多种告警通道。

    二、Phoenix 能做什么?

    在深入技术细节之前,先梳理 Phoenix 的监控能力边界:

    监控维度 监控对象 具体内容
    应用程序 Java应用(默认) 在线状态、JVM内存/线程/GC/类加载、线程池、业务告警、异常日志
    服务器 Linux/Windows/macOS/Unix CPU、GPU、内存、磁盘、网卡、进程、平均负载、电池、传感器
    网络设备 交换机/路由器(SNMP协议) 在线状态、系统信息、接口信息
    Docker Docker服务 服务概况、容器、镜像、事件、资源统计(CPU/内存/网络IO/磁盘IO)
    数据库 MySQL/Oracle/Redis/Mongo 会话、表空间、慢SQL、连接状态、数据库全量信息
    网络 ICMP Ping 网络连通性、平均响应时间
    TCP TCP端口 端口存活状态、响应时间
    HTTP HTTP接口 接口可用性、响应时间、状态码
    告警 多通道 电子邮件、钉钉、企业微信、飞书

    值得注意的是,Phoenix 支持 HTTPWebSocket 双通道通信。HTTP 是传统的请求-响应模式,WebSocket 则基于 Netty 实现长连接,适用于实时性要求更高的场景。由于对外暴露的是标准化接口协议,虽然默认客户端是 Java 实现,但只要遵循协议规范,任何语言都可以接入。

    三、系统架构:四端协作

    Phoenix 采用经典的四端分离架构,每个端各司其职:

    系统架构图

    3.1 phoenix-client:轻量级的应用监控SDK

    客户端是需要集成到你的 Java 应用程序中的监控 SDK,接入成本极低——SpringBoot 项目只需引入一个 starter 依赖并加上 @EnableMonitoring 注解,并配置服务端地址即可,无需修改任何业务代码。它的职责是:

    • 定时发送心跳包:默认每 30 秒一次,让服务端知道"我还活着"
    • 采集JVM信息:内存使用、线程状态、GC情况、类加载数据
    • 采集线程池信息:核心线程数、活跃线程、队列大小、拒绝策略等
    • 上报服务器信息(可选):CPU、内存、磁盘等操作系统级指标
    • 业务埋点:支持在代码中主动发送告警和异常信息

    客户端提供了三种集成方式:

    • phoenix-client-core:适用于普通 Java 程序
    • phoenix-client-spring-boot-starter:SpringBoot 项目一个注解即可接入
    • phoenix-client-spring-mvc-integrator:适用于传统 SpringMVC 项目

    3.2 phoenix-agent:基础设施的信息采集者

    代理端部署在需要监控的服务器上,它承担着双重角色:

    1. 信息采集者:利用 oshi/Sigar 采集服务器硬件信息,利用 docker-java 采集 Docker 信息,利用 snmp4j 采集网络设备信息
    2. 信息中转站:汇聚并转发来自客户端的监控数据。如果部署在跳板机上,可以打通网络壁垒,让内网应用的监控数据也能抵达服务端

    3.3 phoenix-server:监控平台的大脑

    服务端是整个平台的核心枢纽,接收来自客户端和代理端的所有监控数据,并进行:

    1. 数据持久化:将各类监控信息写入 MySQL 数据库(当前+历史记录双表设计)
    2. 状态判定:基于心跳超时、Ping 不通、端口不可达等条件判定在线/离线
    3. 告警触发:通过 Quartz 定时任务周期性检测,发现异常时通过邮件、钉钉、企业微信、飞书推送告警
    4. 告警收敛:防止告警风暴,控制故障/恢复告警的发送频率

    3.4 phoenix-ui:可视化操作台

    UI 端是面向运维人员的 Web 管理界面,基于 SpringBoot + Thymeleaf + Layui 构建,提供:

    1. 首页仪表盘:总览所有监控对象的健康状态
    2. 各类监控详情页:服务器、应用、数据库、Docker、网络等
    3. 拓扑图:展示服务之间的链路关系
    4. 告警管理:告警记录查询、告警定义配置
    5. 监控配置:灵活配置监控频率、告警阈值、告警通道
    6. 用户管理:基于 SpringSecurity 的权限控制,支持自有认证和 CAS 第三方认证

    四、工程模块结构

    从 Maven 工程的角度看,Phoenix 采用多模块父子工程结构:

    phoenix(父工程,统一管理依赖版本与构建配置)
    ├── phoenix-common(公共模块父工程)
    │ ├── phoenix-common-core(核心公共模块:DTO、Domain、工具类、加解密、配置属性)
    │ ├── phoenix-common-netty(Netty公共模块:WebSocket客户端/服务端封装)
    │ └── phoenix-common-web(WEB公共模块:HTTP加解密切面、通用Web配置)
    ├── phoenix-client(客户端父工程)
    │ ├── phoenix-client-core(客户端核心:Monitor入口、心跳/JVM/线程池定时任务)
    │ ├── phoenix-client-spring-boot-starter(SpringBoot自动配置的Starter)
    │ └── phoenix-client-spring-mvc-integrator(SpringMVC集成适配器)
    ├── phoenix-agent(代理端:服务器/Docker/网络设备信息采集、数据转发)
    ├── phoenix-server(服务端:数据接收、持久化、状态监测、告警引擎)
    ├── phoenix-ui(UI端:Web管理界面、SpringSecurity认证、ECharts图表)
    ├── doc(文档)
    └── mvn(Maven打包脚本)
    

    这种分层结构有几个明显的好处:

    • 关注点分离:公共代码在 common 中复用,各端只关注自身业务
    • 独立部署:agent、server、ui 分别打成可执行 JAR,支持独立扩缩容
    • 客户端轻量:client 模块仅包含必要的上报逻辑,不引入服务端的重量级依赖

    五、技术选型一览

    层面 技术 说明
    核心框架 SpringBoot 2.3.x 所有端的基座
    通信层 Netty (WebSocket) + HTTP 双通道数据传输,WebSocket用于长连接实时通信
    安全框架 SpringSecurity + SpringSession UI端认证鉴权,支持CAS单点登录
    任务调度 JUC + Quartz 客户端用JUC线程池,服务端用Quartz做定时监测
    持久层 MyBatis-Plus + Druid ORM + 数据库连接池
    数据库 MySQL 5.7+ 约45张业务表,涵盖监控数据的实时态与历史态
    前端 Layui + ECharts + jtopo + xterm 管理界面 + 图表展示 + 拓扑图 + Web终端
    数据安全 AES / DES / SM4 + Gzip 传输数据先压缩再加密,支持国密算法
    服务器采集 oshi / Sigar 跨平台硬件信息采集
    Docker采集 docker-java Docker API 交互
    网络设备采集 snmp4j SNMP 协议通信
    诊断工具 Alibaba Arthas 在线Java诊断

    六、数据流转:一个心跳包的生命周期

    以最基础的心跳机制为例,来看数据在 Phoenix 中是怎样流转的:

    1. 客户端构造心跳包

    客户端的 HeartbeatTaskScheduler 以固定频率(默认30秒)构造 HeartbeatPackage,包含应用实例ID、IP、端点类型等基本信息。

    2. 数据加密与压缩

    心跳包序列化为 JSON 后,经过 MsgPayloadUtils.encryptPayloadTo() 处理:

    • 判断是否需要 Gzip 压缩(数据量较大时自动压缩)
    • 使用配置的加密算法(AES/DES/SM4)对数据加密
    • 封装为 CiphertextPackage(密文数据包)

    3. 传输到服务端

    根据通信协议配置,通过 HTTP POST 或 WebSocket 发送到 phoenix-server(也可通过 phoenix-agent 中转)。

    4. 服务端解密与处理

    服务端的 RequestPackageDecryptAdvice 拦截请求,自动完成解密和解压,还原出原始的 HeartbeatPackage

    5. 业务处理

    HeartbeatServiceImpl.dealHeartbeatPackage() 将应用实例信息写入/更新到 MONITOR_INSTANCE 表。

    6. 状态监测与告警

    Quartz 定时任务 InstanceMonitorJob 周期性扫描实例表,发现心跳超时的实例后:

    • 判断是否已开启告警
    • 构造告警信息(包含应用ID、名称、IP、环境、分组等)
    • 通过 TemplateMsgSendFacadeServiceImpl 发送到对应的告警通道

    这个流程体现了 Phoenix 的核心设计理念:采集 → 加密传输 → 持久化 → 异步监测 → 智能告警

    七、数据库设计概览

    Phoenix 的数据库采用 MySQL,设计了约 45 张业务表,大致可以分为以下几个域:

    数据域 核心表 说明
    告警 MONITOR_ALARM_DEFINITIONMONITOR_ALARM_RECORDMONITOR_ALARM_RECORD_DETAIL 告警定义、记录与发送详情
    应用实例 MONITOR_INSTANCE 通过心跳上报的Java应用实例
    JVM MONITOR_JVM_MEMORYMONITOR_JVM_THREADMONITOR_JVM_RUNTIMEMONITOR_JVM_CLASS_LOADINGMONITOR_JVM_GARBAGE_COLLECTOR JVM各维度的实时数据
    线程池 MONITOR_JAVA_THREAD_POOLMONITOR_JAVA_THREAD_POOL_HISTORY 应用Java线程池的实时和历史数据
    服务器 MONITOR_SERVERMONITOR_SERVER_CPUMONITOR_SERVER_MEMORYMONITOR_SERVER_DISKMONITOR_SERVER_NETCARDMONITOR_SERVER_OS 服务器各硬件维度数据
    Docker MONITOR_DOCKERMONITOR_DOCKER_CONTAINERMONITOR_DOCKER_IMAGEMONITOR_DOCKER_EVENTMONITOR_DOCKER_STATS Docker全量信息
    网络/TCP/HTTP MONITOR_NETMONITOR_TCPMONITOR_HTTP 及对应的 History 表 连通性检测数据
    网络设备 MONITOR_NETWORK_DEVICEMONITOR_NETWORK_DEVICE_SYSMONITOR_NETWORK_DEVICE_IF SNMP设备信息
    系统 MONITOR_USERMONITOR_ROLEMONITOR_CONFIGMONITOR_LOG_OPERATIONMONITOR_LOG_EXCEPTION 用户、角色、配置、日志

    一个重要的设计模式是实时表 + 历史表的分离:例如 MONITOR_SERVER_CPU 存储最新一次采集的 CPU 数据,而 MONITOR_SERVER_CPU_HISTORY 按时间序列存储所有历史数据。这样查询最新状态时效率很高,历史趋势分析也不受影响。

    八、本系列博客规划

    本系列将细分为几十篇,每篇聚焦一个具体主题,力求讲透讲深。以下是目前规划的脉络(后续可能随写作进展动态调整):

    第一部分:通信与数据安全

    篇目 主题
    第二篇 HTTP通信通道:请求/响应模型与RestTemplate封装
    第三篇 WebSocket通信通道:基于Netty的长连接实现
    第四篇 Netty WebSocket服务端启动与初始化流程
    第五篇 Netty WebSocket客户端连接与重连机制
    第六篇 数据加解密体系:AES、DES、SM4国密算法的统一抽象
    第七篇 数据压缩与传输优化:Gzip策略与CiphertextPackage设计

    第二部分:客户端SDK

    篇目 主题
    第八篇 Monitor入口类:客户端启动全流程解析
    第九篇 配置加载机制:properties文件与SpringBoot配置的双轨制
    第十篇 心跳机制:HeartbeatTaskScheduler的设计与实现
    第十一篇 JVM信息采集:内存、线程、GC、类加载数据的收集
    第十二篇 线程池信息采集:MonitoredExecutor注册表与定时上报机制
    第十三篇 SpringBoot Starter自动配置:@EnableMonitoring注解原理
    第十四篇 SpringMVC Integrator适配:Listener机制集成方案
    第十五篇 业务埋点:同步与异步告警发送API设计

    第三部分:代理端

    篇目 主题
    第十六篇 代理端整体架构与角色定位
    第十七篇 服务器信息采集(上):oshi方案详解
    第十八篇 服务器信息采集(下):Sigar方案与oshi对比
    第十九篇 Docker信息采集:docker-java的封装与使用
    第二十篇 Docker容器资源统计:Stats采集与IO速率计算
    第二十一篇 网络设备采集:snmp4j与SNMP协议交互
    第二十二篇 代理端的数据转发与命令执行器模式

    第四部分:服务端核心

    篇目 主题
    第二十三篇 服务端数据接收架构:Controller层设计
    第二十四篇 并行数据处理:CompletableFuture异步编排实践
    第二十五篇 应用实例管理:心跳处理与在线状态维护
    第二十六篇 服务器监控数据处理:多维信息的入库与更新策略
    第二十七篇 Docker监控数据处理:系统/容器/镜像/事件/统计的全链路
    第二十八篇 数据库监控:MySQL/Oracle/Redis/Mongo的连接与信息采集
    第二十九篇 慢SQL检测:MySQL与Oracle的慢查询发现机制
    第三十篇 网络/TCP/HTTP状态监测:Ping、端口探测与接口可用性检查
    第三十一篇 分布式锁设计:基于数据库的轻量级分布式锁实现
    第三十二篇 实时监控表与告警收敛:MONITOR_REALTIME_MONITORING的设计

    第五部分:告警引擎

    篇目 主题
    第三十三篇 告警定义体系:类型、级别与编码设计
    第三十四篇 告警触发流程:从状态变化到告警包构造
    第三十五篇 告警通道实现(一):电子邮件
    第三十六篇 告警通道实现(二):钉钉
    第三十七篇 告警通道实现(三):企业微信
    第三十八篇 告警通道实现(三):飞书
    第三十九篇 告警收敛策略:频率控制与风暴抑制

    第六部分:UI端与安全

    篇目 主题
    第四十篇 UI端整体架构:SpringBoot + Thymeleaf + Layui
    第四十一篇 SpringSecurity认证体系:自有认证流程详解
    第四十二篇 CAS单点登录集成:第三方认证方案
    第四十三篇 验证码机制与登录安全防护
    第四十四篇 操作日志与异常日志:AOP切面的日志记录设计
    第四十五篇 前端交互设计:Layui模块化与ECharts图表实践
    第四十六篇 拓扑图实现:jtopo的链路可视化

    第七部分:线程池监控

    篇目 主题
    第四十七篇 线程池注册体系:MonitoredExecutor构造器注册与@MonitoringThreadPool注解辅助纳管
    第四十八篇 线程池运行时动态调参:核心参数的热更新实现
    第四十九篇 线程池历史趋势:数据记录与利用率分析

    第八部分:公共模块与工程化

    篇目 主题
    第五十篇 phoenix-common-core:DTO体系与AbstractSuperBean设计
    第五十一篇 phoenix-common-core:Domain模型与Server信息建模
    第五十二篇 phoenix-common-web:HTTP加解密切面的AOP实现
    第五十三篇 Maven多模块工程管理:依赖版本统一与构建配置

    第九部分:部署与运维

    篇目 主题
    第五十四篇 Docker部署:Dockerfile编写与镜像构建
    第五十五篇 Docker Compose一键部署方案
    第五十六篇 Windows/Linux服务化部署与启停脚本
    第五十七篇 集群部署架构与高可用方案

    第十部分:数据库设计

    篇目 主题
    第五十八篇 数据库整体设计:表分域、索引策略与外键约束
    第五十九篇 实时表+历史表双表模式的设计思想
    第六十篇 Quartz调度表与定时任务持久化

    九、小结

    Phoenix 作为一个完整的开源监控平台,麻雀虽小,五脏俱全。它的设计有几点值得学习:

    1. 分层清晰:四端分离,公共模块下沉,客户端轻量易集成
    2. 通信安全:传输数据全程加密,支持多种加密算法,包括国密SM4
    3. 可扩展:基于 HTTP + WebSocket 的协议设计,天然支持跨语言接入
    4. 实用导向:不追求大而全,聚焦实际运维场景中最常见的监控需求
    5. 数据设计合理:实时+历史双表、完善的索引设计、外键约束保证数据一致性

    从下一篇开始,我们将深入源码,逐层剥开 Phoenix 的技术内核。

    end
  1. 作者: 锋哥 (联系作者)
  2. 发表时间: 2026-03-25 14:28
  3. 版权声明:自由转载-非商用-非衍生-保持署名(创意共享3.0许可证)
  4. 转载声明:如果是转载博主转载的文章,请附上原文链接
  5. 公众号转载:请在文末添加作者公众号二维码(公众号二维码见右边,欢迎关注)
  6. 评论

    站长头像 知录

    你一句春不晚,我就到了真江南!

    文章0
    浏览0

    文章分类

    标签云