
Redis 内存和连接异常怎么排查用 redis_exporter 搭一套可远程抓取的监控链路前言Redis 出问题时最让人难受的往往不是进程彻底停了而是业务还在运行缓存命中率却开始下降连接数慢慢逼近上限内存持续上涨直到接口响应变慢才有人发现。临时登录服务器查看状态能回答“现在怎么样”却很难追溯异常从什么时候开始、此前有哪些变化。我更愿意让监控从日常运行时就开始先把 Redis 的统计信息转成连续指标再交给 Prometheus 抓取、保存和查询等到需要时再接告警规则而不是故障发生后才拼凑现场。这套实践使用 Linux 上的redis_exporter v0.21.2和Prometheus 3.5.0。我会先验证 Redis 连接与9121/metrics再配置 systemd、Prometheus 抓取目标和 Redis 告警规则如果 Prometheus 位于另一处网络再用 cpolar 将 Exporter 的 HTTP 指标入口映射出去先测试随机公网地址最后改成固定二级子域名redis。每一步都按“能启动、能采集、能抓取、能判断告警、能跨网络访问”的顺序展开尤其分清 Exporter 进程在运行与 Redis 指标可用、Prometheus 发现目标与告警真正送达之间的区别。这样出现异常时可以知道应该从哪一层查起。对经常管理缓存服务的人来说先确定是 Redis 本身、采集进程、抓取配置还是远端网络出了问题比看到一张漂亮的监控页面更有用。一、先弄清 Redis 监控各组件的职责Redis 常被用于缓存、热点数据、限流和分布式锁。遇到内存、连接、命令执行或复制状态异常时我希望看到的不只是一张当前状态截图而是一段时间里的连续变化。redis_exporter正是 Redis 与 Prometheus 之间的指标适配器它读取 Redis 的运行统计再通过 HTTP/metrics输出 Prometheus 可以抓取的数据。关注的指标可以按问题归类内存占用和碎片率、客户端连接与拒绝连接、Key 与过期情况、GET/SET/DEL 等命令统计、RDB/AOF 状态、网络流量以及有相应部署形态时的主从或集群状态。Grafana 可在后续接入可视化Prometheus 的规则可用于识别异常。指标采集、Prometheus 规则文件与跨网络抓取是这里的核心Grafana 看板和 Alertmanager 通知链路需要另外配置。一个容易混淆的地方是Exporter 的进程存活、/metrics能访问以及其中确实存在 Redis 的有效数据是三个不同层次。后续验证需要依次看。二、部署 redis_exporter先拿到指标再考虑服务托管如果 Redis 尚未安装可以先参考 Redis 完整安装部署教程。本次以已经运行的 Redis 实例为前提Exporter 放在自选的/app/redis_exporter目录下载版本为v0.21.2。1. 下载并解压wgethttps://github.com/oliver006/redis_exporter/releases/download/v0.21.2/redis_exporter-v0.21.2.linux-amd64.tar.gztar-zxvfredis_exporter-v0.21.2.linux-amd64.tar.gz2. 按 Redis 的连接条件选择启动方式Redis 设置了密码时使用带密码的启动示例nohup./redis_exporter-redis.addr你的redis的ip:6379-redis.password密码 -web.listen-address :9121没有密码的实例使用nohup./redis_exporter-redis.addr你的redis的ip:6379 -web.listen-address :9121如果 Redis 和 Exporter 在同一台服务器主机地址还可以写成localhost:6379nohup./redis_exporter-redis.addrlocalhost:6379 -web.listen-address :9121这三条是不同场景下的选择不需要连续启动三个 Exporter。示例中的 Redis 地址、密码应与实际实例对应同机地址也以 Redis 确实监听的位置为准。3. 验证进程和指标接口先检查进程ps-ef|grepredis_exporter再在浏览器打开指标地址http://服务器ip:9121/metrics这里的9121是 Exporter 的 HTTP 端口6379是被监控 Redis 的连接端口。能够打开/metrics是第一步还应确认实际 Redis 指标存在、采集未报错不能只凭 HTTP 页面出现就认定数据库连接无误。4. 需要常驻运行时再配置 systemd创建服务文件vim/usr/lib/systemd/system/redis_exporter.service服务内容如下[Unit]DescriptionRedis ExporterforPrometheusDocumentationhttps://github.com/oliver006/redis_exporterAfternetwork.target[Service]TypesimpleUserredis-exporterGroupredis-exporterExecStart/app/redis_exporter/redis_exporter\--redis.addrredis://localhost:6379\--web.listen-address:9121\--web.telemetry-path/metricsRestarton-failureRestartSec5StandardOutputjournalStandardErrorjournalSyslogIdentifierredis_exporter[Install]WantedBymulti-user.target服务使用Userredis-exporter和Groupredis-exporter二进制路径写成/app/redis_exporter/redis_exporter并通过redis://localhost:6379连接数据库。这里没有创建 Linux 用户或组的命令也没有展示将压缩包中的二进制放入/app/redis_exporter的过程真正启用前需要确认这些对象和路径存在、具备运行权限。如果实际 Redis 带密码systemd 连接配置也要与前面手动启动的认证条件一致。服务文件下面给出的命令是systemctlenableprometheus systemctl start prometheus systemctl status prometheus它们操作的是prometheus而不是redis_exporter。这组命令继续保留供对照配置 Exporter 服务时应先核对实际服务名及进程状态避免出现“写好了 Exporter 文件却只启动了 Prometheus”的情况。三、安装 Prometheus保存并抓取时序数据Exporter 负责暴露指标Prometheus 才负责周期性抓取与保存。先准备安装目录mkdir/appcd/app到 Prometheus 下载页面 选择 Linux 安装包示例使用prometheus-3.5.0.linux-amd64.tar.gz。图形终端使用 MobaXterm Personal将安装包上传到/app。检查上传结果ls解压tar-xzvfprometheus-3.5.0.linux-amd64.tar.gz重命名解压目录删除压缩包是示例中的可选清理动作mvprometheus-3.5.0.linux-amd64 prometheusrm-rfprometheus-3.5.0.linux-amd64.tar.gz进入目录查看版本cd/app/prometheus ./prometheus--version1. 创建数据目录和服务文件时序数据目录mkdir-p/var/lib/prometheus创建 systemd 服务文件vim/usr/lib/systemd/system/prometheus.service写入[Unit]DescriptionPrometheusDocumentationhttps://prometheus.io/Afternetwork.target[Service]# Type设置为notify时服务会不断重启TypesimpleUserroot# --storage.tsdb.path是可选项默认数据目录在运行目录的./dada目录中ExecStart/app/prometheus/prometheus--config.file/app/prometheus/prometheus.yml--storage.tsdb.path/var/lib/prometheus --web.enable-lifecycleExecReload/bin/kill-HUP$MAINPIDKillModeprocessRestarton-failure[Install]WantedBymulti-user.target配置将可执行文件指向/app/prometheus/prometheus配置文件指向/app/prometheus/prometheus.yml数据目录指向/var/lib/prometheus。文件里的注释和命令均按示例保留Userroot是进程运行身份不代表监控 Redis 时必须使用数据库超级权限。启动并查看服务systemctlenableprometheus systemctl start prometheus systemctl status prometheus接下来给出的访问示例为ip:9200这一行写成了ip:9200但后面实际验证 Prometheus 时使用的是IP:9090而 cpolar 的 Web 管理端口同样是9200。访问时应核对自己运行的服务和实际监听端口避免打开了另一个管理页面却以为进入了 Prometheus。四、把 redis_exporter 添加到 Prometheus 抓取列表编辑正在使用的配置文件viprometheus.yml增加 Redis Exporter 目标- targets:[localhost:9121]labels: app:redis_exporterlocalhost:9121只适合 Prometheus 与 Exporter 位于同一台机器的情况。这里展示的是 target 和标签片段需要放进实际scrape_configs对应的 job 中app: redis_exporter是自定义标签并不等于 Prometheus 的job标签名称。重启 Prometheussystemctl restart prometheus通过IP:9090进入页面查看目标状态确认redis_exporter被检测到并且抓取正常。这时形成的链路是 Redis6379→ Exporter9121→ Prometheus。若抓取状态正常但 Redis 指标为空还要返回 Exporter 的 Redis 连接配置检查。五、添加 Redis 告警规则规则生效与通知送达分开看已有的 Alertmanager 部署可参考 服务器监控告警系统教程。下面先增加 Redis 规则文件包含 Exporter 不响应、内存使用率、连接数及主从链路状态这四类场景。groups: - name: redis-alerts rules:# Redis 实例宕机Exporter 无响应- alert: RedisDown expr: up{jobredis}0for: 1m labels: severity: critical annotations: summary:Redis instance downdescription:Redis instance {{$labels.instance }} is down for more than 1 minute.# Redis 内存使用率过高85%- alert: RedisMemoryHigh expr: redis_memory_used_bytes{jobredis}/ redis_memory_max_bytes{jobredis}0.85for: 2m labels: severity: warning annotations: summary:Redis memory usage highdescription:Redis instance {{$labels.instance }} memory usage is above 85% (current value: {{$value| humanizePercentage }}).# Redis 连接数接近上限90%- alert: RedisTooManyConnections expr: redis_connected_clients{jobredis}/ redis_config_maxclients{jobredis}0.9for: 2m labels: severity: warning annotations: summary:Redis too many connectionsdescription:Redis instance {{$labels.instance }} has too many clients ({{$value| humanizePercentage }} of max).# Redis 主从复制延迟仅适用于主从架构- alert: RedisReplicationLag expr: redis_slave_info{master_link_statusdown,jobredis}1for: 1m labels: severity: critical annotations: summary:Redis replication brokendescription:Redis slave {{$labels.instance }} lost connection to master.规则包含RedisDown、RedisMemoryHigh、RedisTooManyConnections、RedisReplicationLag。其中内存阈值为0.85、连接数阈值为0.9复制规则仅适用于相关主从指标存在的场景。示例表达式都使用了jobredis必须与抓取任务实际生成的job标签核对不能只凭前面配置了app: redis_exporter就认为一定匹配。将规则保存为7.yml后编辑 Prometheus 配置viprometheus.yml添加规则文件路径rule_files: -/app/prometheus/7.yml重启服务systemctl restart prometheus通过IP:9090查看规则页面。能够看到告警规则说明规则已被加载但“规则已加载”“表达式命中”和“通知已由 Alertmanager 发出”是不同结果。这里没有展示 Prometheus 对接 Alertmanager 的路由、接收器或实际通知记录所以不会直接认定通知链路已完成。六、异地 Prometheus 需要抓取时再给 Exporter 配公网入口如果要监控另一处网络里的 Redis远端 Prometheus 无法直接访问本地的localhost:9121。这时可以让 cpolar 为 Exporter 提供 HTTP 入口cpolar 只负责网络可达性Exporter 负责生成指标Prometheus 仍负责抓取与存储。既不需要把 Redis6379作为本方案的公网端口也不需要把 Prometheus 管理页作为抓取地址。先安装 cpolarsudocurlhttps://get.cpolar.sh|sh检查服务状态sudosystemctl status cpolar通过主机 IP:9200进入 cpolar Web UI 并登录。1. 创建随机 HTTP 隧道验证链路进入隧道管理 → 创建隧道参数如下隧道名称redis_exporter协议http本地地址9121域名类型随机域名地区China Top。在线隧道列表会显示生成的地址。从其他网络打开它确认能到达 Exporter。对于监控验证时还应查看公网地址对应的/metrics而不仅是 Exporter 首页。将指标接口开放到公网意味着外部网络也能访问其中的运行信息应结合实际访问控制要求决定开放范围。2. 远端 Prometheus 抓取随机地址示例公网主机名为a214e29.r2.cpolar.top抓取片段如下- targets:[a214e29.r2.cpolar.top]labels: app:redis_exporter随后在 Prometheus 中查看抓取结果。示例说明中还出现了“本地9105端口”但前面的启动命令和隧道都使用9121。同时这段公网 target 没写端口和scheme实际使用时必须与生成的 HTTP/HTTPS 地址及 Prometheus 配置对应确认连接的是 Exporter/metrics而不是仅凭示例字符串推断任何环境都能抓取。七、固定子域名适合长期抓取随机域名更适合先测试。Prometheus 要持续抓取时可以预留固定二级子域名减少目标地址变更带来的维护工作。进入预留 → 保留二级子域名地区选择china Top名称使用redis填写备注后保留。实际名称具有唯一性以账号中保留成功的结果为准。回到隧道管理 → 隧道列表找到redis_exporter隧道并编辑域名类型二级子域名Sub Domain填写成功预留的名称地区China Top。点击更新。在线隧道列表会显示固定形式的地址。最后从外部继续验证指标页面。固定地址稳定的是网络入口不会替 Redis 修复性能问题也不会替 Exporter 处理认证、替 Prometheus 修复抓取配置。完成固定域名切换后还需要同步更新远端 Prometheus 的目标地址并再次确认抓取状态。总结一套能用的 Redis 监控关键不在于装了多少组件而在于数据是否能从 Redis 正确进入 Exporter、持续被 Prometheus 抓到再按照真实标签和阈值进入规则判断。内存、连接、命令和复制指标能够留下时间序列后排查就不必只依赖故障发生时的一次登录和一次截图。跨网络场景再由 cpolar 给9121提供公网入口先随机测试再固定地址。把采集、存储、规则和网络入口分开维护比把“进程启动、网页可访问、告警已送达”混成一句部署成功更可靠真正需要通知时再核实 Alertmanager 的路由与接收器是否配置完整。