本篇是《Prometheus 从入门到生产实践》第 22 / 24 篇。配置以文中版本与环境前提为准,实验和故障均为教学场景。完整程序、配置及校验范围见配套实验包。

当本地保留期不足、需要跨集群查询或集中保存指标时,可以把样本送往远端存储。Remote Write 解决的是传输路径,不会自动把 Prometheus 变成分布式数据库,也不保证所有接收端具有相同协议、查询和高可用语义。
1. 先把采集、发送、存储和查询分开
典型链路是 exporter → Prometheus 抓取与 WAL → Remote Write 队列 → 接收端写入 → 查询系统。每一步都可能独立失败:本地采集成功时远端仍可能断流,远端接受写入也不代表最终查询入口已经能读到最新数据。
本地 Server 模式通常仍保留自己的 TSDB,用于本地规则和短期排障。Remote Write 不会因为远端数据很多就自动延长本机历史,也不会把远端数据透明接回全部本地查询。
因此验收至少要同时记录本地最新样本、队列积压和远端可查询时间点,而不是只看发送 URL 返回过一次 200。
2. 一份可阅读的发送端配置
下面是独立示意配置。example.test 是文档域名,必须换成授权测试接收端,并按后端要求配置 TLS、身份和租户,不能直接用于生产:
global:
scrape_interval: 15s
external_labels:
monitor_cluster: lab
replica: a
scrape_configs:
- job_name: demo
static_configs:
- targets: ['127.0.0.1:19100']
remote_write:
- name: central-lab
url: https://metrics.example.test/api/v1/write
remote_timeout: 30s
queue_config:
capacity: 10000
min_shards: 1
max_shards: 4
max_samples_per_send: 2000
batch_send_deadline: 5s
write_relabel_configs:
- source_labels: [__name__]
regex: 'up|ops_demo_.*'
action: keep
write_relabel 在发送前筛选样本,这里只保留 up 与教学业务指标,不会删除本地已保存数据。它位于外部标签应用之后,与 scrape 阶段的 metric relabel 不同。这个示例保留副本标签,后端如何去重需要明确配置。
配置检查只证明结构和相关语义被接受,不证明域名可达、认证有效或后端完成存储。正式连接前还要核对接收路径:不同产品和单机/集群部署的写入 URL 可能不同。
3. 队列参数控制什么
Remote Write 将发送工作分到 shard。capacity 是每个 shard 的缓冲能力,不是整个系统的可容忍中断时长;max_samples_per_send 影响批量大小,max_shards 限制并发上限,batch_send_deadline 控制低吞吐时的等待。
增加 shard 可能提高吞吐,也可能让接收端限流、连接数和发送端内存更糟。队列内存还与序列缓存、标签和样本类型有关,不能只用“capacity × 8 字节”估算整个进程。
先测正常输入速率和远端实际处理能力,再调参数。若恢复后的发送能力不高于新进入速率,积压就无法被追平。机制和观测方向见 Remote write tuning。
4. 断网后会补发,但不是无限缓存
远端短暂不可用时,系统会根据 WAL 和队列状态尝试重发。中断过久、WAL 截断、磁盘耗尽或明确不可重试的错误都可能导致数据丢失。不同模式与版本的保留策略也不同,因此不能把“可补发”写成“断网多久都不丢”。
观察 samples_pending、发送失败/重试/丢弃计数和最高已发送时间等自监控指标,并结合日志中的 HTTP 状态。具体指标名称、标签和重试条件先在所用版本的 /metrics 与文档中确认。
例如下面的时间差可以作为延迟线索:
time() - prometheus_remote_storage_queue_highest_sent_timestamp_seconds
它不是天然可靠的延迟告警:没有新样本的空闲队列也可能让时间差增长。需要同时确认本地仍有新数据、积压和采集状态,再解释这个值。
5. Remote Write 1.0 与 2.0 要做兼容验证
较新版本支持通过 protobuf_message 选择消息类型,例如 prometheus.WriteRequest 和 io.prometheus.write.v2.Request。后者对元数据、起始时间和直方图等处理有所变化,不是简单换一个 Content-Type 就能保证兼容。本文核对的 Remote Write 2.0 规范仍标为实验状态,采用前需确认发送端与接收端具体实现,而不是假定它已经替换全部现有链路。
切换前核对发送端版本、接收端具体版本与配置、原生直方图和 exemplar 的支持,先用小流量 job 验证写入响应、远端样本和查询语义。不要因为产品宣称“兼容 Prometheus”就认定它接受所有协议变体。规范见 Remote Write 2.0 specification。
启用 Prometheus 自身的 Remote Write receiver 也不是把它改造成通用大规模集中写入平台的默认推荐路线,应按其设计限制选择使用场景。
6. 长期存储的几条架构路线
| 路线 | 典型组织方式 | 选型时必须核对 |
|---|---|---|
| Thanos Sidecar | Prometheus 旁路组件、对象存储、统一查询 | 块上传时序、压缩参数、副本标签与 Query 去重 |
| Grafana Mimir | Remote Write 接入、分布式存储和查询 | 租户身份、接入限额、HA 去重及运维规模 |
| VictoriaMetrics | 单机或集群写入与查询组件 | 实际写入 URL、复制/去重、查询差异与容量 |
Thanos 也有 Receive 路线,但 Sidecar 块上传与 Remote Write 不是同一机制。架构选择应阅读各自的 Thanos Sidecar、Mimir 架构 和 VictoriaMetrics 集群说明,再用自己的数据验证,不仅比较压缩率或宣传中的节点数。
7. 一次可控的远端恢复演练
在测试链路持续产生教学请求,记录本地与远端 rate 的结果及最近时间。停止测试接收端一小段时间,观察积压、失败和重试,再恢复并确认积压能被追平。全程记录资源峰值和样本是否缺口。
再测试错误认证或错误租户,确认它们能被明确报警,而不是无限重试掩盖。最后写下“允许多长中断、最多接受多少数据丢失、追平需要多久”的实测预算,并为传输链路本身设置监控。
8. 用吞吐预算解释“恢复了,为什么仍然落后”
假设本地持续摄入每秒一万样本,远端中断十分钟,理想情况下已经积压约六百万样本。恢复后的有效写入能力如果只有每秒一万二,扣除新进入的一万,每秒只有两千能力用来追平,理论上就需要约五十分钟,尚未计算额外重试与序列开销。
因此,连接重新建立和数据恢复到最新是两个里程碑。若接收端只按正常流量配置容量,断流恢复后可能长期落后。应在正常负载之外验证追平余量,并将限流与背压同时纳入实验,而不是只提高发送端 max_shards。
还要检查错误分类。认证不通过、租户不存在、数据格式不支持、样本过旧或标签限制,都可能与网络暂时失败有不同的处理结果。不能用“重试次数增加”证明系统正在恢复,需要核对远端接收计数和实际查询样本。
当后端有多副本或分布式写入路径时,某个入口请求成功也未必等于它承诺的持久化级别,具体语义由后端定义。验收记录应写清被测版本、协议、租户、故障持续时间、积压峰值、追平时间与最终缺口。保存这组信息,后面升级发送端或切换远端产品时才有可比较的基准。
上一篇:高可用架构:双 Prometheus 与 Alertmanager 集群 · 系列目录 · 下一篇:联邦、Agent 与 OpenTelemetry:画清不同数据路径