M3db

背景 我们的云平台需要采集所有集群正在运行的容器的性能数据与业务指标,最开始采用的每个集群一个独立Promethues的配置,如下图: 结构比较简单,这里就不累述了。需要解释下的是 prom-nanny 这个组件是个啥,其实就是对社区版本 prometheus 的封装,它主要实现以下功能: watch 用户配置的自定义告警规则,然后更新到配置文件中 更新配置文件后,调用 prometheus 接口热更新配置 以上则是以前老的监控体系下的拓扑图。很明显这里很多问题: 存储、采集、查询单点:这里 Prometheus 承担了三个责任,但是它仅有一个实例,一旦故障,我们将失去所有功能 无法水平扩容:由于只有一个实例,所以我们只能垂直扩容,而母机的配置是有上限的,你不可能无线扩下去,对于有的集群动则几千个节点,单一实例是不可能满足的。有的同学可能会提到 hashmod 、federation 和 remote_read,其实这三个功能可以解决采集和查询的水平扩容,但是解决不了存储的水平扩容,Prometheus 提出了 remote_write 来解决存储单点的问题 权限未分开:由于我们不但采集性能数据,还采集业务系统自行暴露的业务指标,因此存在一些敏感数据,但是 grafana 和 prometheus 都共用一个的情况下,权限都是共用的,这带来的一定的安全风险 方案对比 由于现在集群的指标都是通过 Prometheus 的 exporter 来暴露,所以方案已经限定以 Prometheus 为基础了。 基于这个前提,在作者进行方案选型时(2019年中),了解到的有以下几种解决方案: Prometheus + influxdb Thanos cortex M3 这里其中第一个方案由于此前隔壁组的同事以前做过预研,发现性能存在较大缺陷,所以不在考虑范围内,最终他们选择了 Thanos。 这里列个对比图: 简述 优点 缺点 Thanos 开源社区很有名的集群方案,它的核心点在于将查询最近时间的查询请求路由到各个 Prom 分片进行查询,同时通过 SideCar 将数据同步到对象存储中,作为历史存储。 已经有了很多案例资料可参考,查询快,功能成熟 历史查询慢,由于是是从对象存储转换过来,很显然这里存在复杂的转换过程,同时对象存储的数据库也不会没有针对时序型数据的优化;同一 Prom 分片承担采集与查询的责任,会互相影响 cortex WeaveCloud 公司搞的开源项目,通过 Prometheus 的 remote_write 写入自研的组件后将其转换为块存储,然后提供兼容 PromQL 的查询组件来提供外部使用 虽然使用的块存储,但是它还利用了额外的存储来简历索引,同时提供了优化查询的缓存组件,可以是说是煞费苦心了;功能应该是我了解的方案中最为丰富的一个 太复杂,它的优点其实也是它的缺点,为了能优化查询的速度,让整个拓扑图的复杂度增高了,每多一个组件在分布式系统里面其实都是一种负担。 m3 这是 Uber 在2014 年开始自研的一个方案,他们在开始之前,也尝试了很多开源组件作为底层存储,发现都无法满足他们的要求,于是他们从底层存储开始自研了这套方案,有兴趣的同学可以看下 这篇文章,m3 的理念非常简单,直接通过 remote_write 写到转换组件,然后存入自研的时序数据库,并且提供兼容 PromQL 和 Graphite 语法的查询组件 拓扑简单,落地方便;由于自研的时序数据专门针对时序型数据进行了优化,所以无论短期还是历史数据查询效率和压缩率都非常高;已经在 Uber 内部经过大量数据的验证 案例太少,由于 2018 年才刚刚对外开源,网上关于 m3 实践的资料非常少,偶尔有几篇文章也只是在浅显地跑了起来而已,规模不可考;还没有稳定,版本还是0.
查看更多 →

Prometheus笔记

Prometheus笔记 Prometheus metrics 名称必须满足: [a-zA-Z_:][a-zA-Z0-9_:]* label 名必须满足 [a-zA-Z0-9_]* Prometheus远程存储优化 Prometheus 以每两个小时为一个块,存储到磁盘中,内存保存近两个小时的内容,同时也会写 WAL(write-ahead-log),预写日志文件wal以128MB的段存储在目录中。这些文件包含尚未压缩的原始数据,因此它们比常规的块文件要大。Prometheus将至少保留3个预写日志文件,但是高流量服务器可能会看到三个以上的WAL文件,因为它需要保留至少两个小时的原始数据。 这些块会在后台被压缩成更大的块以节省磁盘,最大长度取决于 storage.tsdb.max-block-duration 参数的设置,默认为保留时间的 10%。 一般来说 storage.tsdb.max-block-duration = storage.tsdb.min-block-duration = 2h 就相当于禁用了压缩功能, 但是别让它们低于 2h,否则有以下的问题: 落盘过于频繁,这会很大程度影响 Promethues 的吞吐量。 由于 WAL 和落盘之前的内存都需要保留两个小时,所以这部分的内存是没办法释放的。 注意 storage.tsdb.max-block-duration 和 storage.tsdb.min-block-duration 指的都是落盘后的块大小,在内存中用于存储最近两小时数据的内存是不可控的,Prometheus 会在落盘后在后台再去压缩合并这些数据。 参考Remote write tuning rate vs irate 它们都用于计算一个时间区间内指标的每秒变化率,两者的决定性差别在于: rate 使用整个时间区间所有点计算出平均变化速率,它会削平峰值 irate 使用时间区间内最后的两个数据点作为变化速率 从它们两者的计算公式我们可以得到以下推论: 当选择的计算区间内仅仅包含两个数据点时,rate 和 irate 没有区别 我们使用 rate 来查看某个数据在较长一段时间内的变化趋势,它会消除一些细节防止影响趋势的展示 使用 irate 来查看某个数据在一段时间内的细小抖动和完整的变化。 使用 rate 时尽量选择较长的时间,而 irate 则反之(太长会丢失很多变化) relabel_config vs metric_relabel_configs relabel_config 发生在 metric_relabel_configs,通常用于挑选 target
查看更多 →