- 时序数据库
- 后端
- 数据存储
- 可观测性
- 云原生
【免费下载链接】mimir
Grafana Mimir provides horizontally scalable, highly available, multi-tenant, long-term storage for Prometheus.
Grafana Mimir 2.0 是该项目的第一个正式发布版本(v2.0 版本号用于表达对 Cortex 项目的敬意——Mimir 正是从 Cortex fork 而来),同时也是一个大规模多租户、高可用、长期存储的时序数据库里程碑。本文基于 v2.0 发布说明 展开,系统梳理 2.0 引入的部署简化、配置精简、split-and-merge 压缩、查询分片、基数分析等核心能力,并结合当前仓库中的源码与配置文档给出可验证的细节;读完你将掌握 Mimir 2.0 相对 Cortex 1.10.0 的全部增量能力,以及从 Cortex 无损迁移到 Mimir 的具体路径。
版本背景:为什么首个版本号是 2.0
Grafana Mimir 2.0 以 Cortex 1.10.0 为基线,叠加了 Grafana Labs 在运行 Grafana Cloud Metrics 与 Grafana Enterprise Metrics 时沉淀的能力。官方发布说明称,在客户测试中,单个集群可以支撑超过十亿条活跃时间序列(active time series)。
之所以跳过 1.x 直接以 2.0 命名,官方解释是两层含义:
- 致敬 Cortex:Mimir 是从 Cortex fork 而来,2.0 表达了对该项目及其社区的尊重;
- 生产就绪:Mimir 已作为 Grafana Cloud Metrics 与 Grafana Enterprise Metrics 的底层引擎长期运行,2.0 代表其"真实环境验证、可上生产"的定位。
因此,2.0 发布说明中列出的特性增强、迁移注意事项与缺陷修复,本质上刻画的是Cortex 1.10.0 与 Grafana Mimir 2.0 之间的全部差异。
核心特性与增强
本节对应发布说明的 "Features and enhancements",逐一展开 2.0 相对 Cortex 的关键增量。
简化部署体验:monolithic mode、memberlist 与内置监控
2.0 在部署维度做了三件大事,目标是"开箱即用、减少外部依赖":
重命名并重做单进程模式为 monolithic mode:Cortex 原有的 single process mode 被改造为 monolithic mode。新版单进程模式补齐了此前缺失的 compactor 组件,并调优了配置默认值,使绝大多数场景无需额外改动即可运行。从部署文档可以看到,启用方式为
-target=all,可用-modules查看单进程内运行的全部组件列表;monolithic mode 也可以部署多个副本水平扩展(-target=all的多个进程),以获得高可用与更大的容量,但因其所有组件同进退,官方不建议在超大规模场景下使用。hash ring 默认存储切换为 memberlist:Mimir 的 hash ring 默认不再依赖 Consul 或 etcd 这类外部组件。根据 memberlist 与 gossip 协议 的说明,memberlist 是一个基于 gossip 协议的 Go 库,负责集群成员管理、节点故障检测与消息传递;默认情况下 Mimir 用它实现 KV 存储来共享 hash ring 数据结构,每个实例在本地维护 ring 副本并通过 gossip 传播变更(
-memberlist.gossip-interval、-memberlist.pullpush-interval控制传播节奏)。2.0 同时对 memberlist 做了性能优化以降低其 CPU 占用,确保在拥有大量活跃序列的集群上运行平稳。内置运维最佳实践面板与告警:Mimir 官方把内部使用的 dashboards、mixins 与 alerts 随项目发布,用于监控 Grafana Mimir。与以往必须借助 Jsonnet 不同,2.0 直接提供可直接导入 Grafana 的 JSON 面板,以及可直接导入 Prometheus 的 YAML 告警与记录规则;告警还配套了源自官方内部运维经验的 runbooks。仓库中
operations/mimir-mixin-compiled/目录下的dashboards/*.json、alerts.yaml、rules.yaml即是这套已编译产物的实物。
配置参数精简与分类:basic / advanced / experimental
2.0 直接移除了 36% 的配置参数,并把剩余参数划分为三类:
- basic(基础):默认安装只需关注这一类;
- advanced(高级):熟悉系统后可针对集群做进一步调优;
- experimental(实验):面向探索性功能,可能在未来版本变更或移除。
这一分类体系在 configuration parameters 文档中有完整定义。在仓库的配置参考文档docs/sources/mimir/configure/configuration-parameters/index.md中可以看到,每个参数条目都标注了(advanced)或(experimental)前缀及对应的 CLI flag,例如cache_unaligned_requests标记为(advanced),默认false。
更可扩展的指标压缩:split-and-merge 算法
针对 Cortex 中超过 3000 万时间序列的租户经常遇到的"未压缩 block 数量无限增长"问题(compactor 处理速度跟不上写入速度),2.0 引入了新的split-and-merge(拆分合并)压缩算法:
- 并行化:将重叠 block 的压缩任务并行分发到多台机器;
- 突破索引上限:通过拆分 block,规避 Prometheus 的 64 GB 索引大小限制。
从 compactor 组件文档 可以还原算法细节,它是一个两阶段过程:
- split(拆分)阶段:compactor 把第一级压缩(默认 2h 时间范围)的所有源 block 划分为
N组(-compactor.split-groups),每组压缩时不是产出一个结果 block,而是产出M个split blocks(-compactor.split-and-merge-shards)。每个 split block 只包含M个分片中的某一个分片所属的 series 子集。最终产生N × M个 block,并在每个 block 的meta.json中记录其分片引用; - merge(合并)阶段:对每个分片合并其全部
N个 split blocks,把 block 数量从N × M收敛到M,随后再对 12h、24h 等更长压缩时间范围做跨分片合并。
官方给出的配置经验:每约 800 万活跃序列配置 1 个分片(如 1 亿活跃序列的租户大约配 16 个分片),且分片数建议取 2 的幂——这与查询分片的分片数形成呼应,便于查询端跳过不可能命中某分片的 block。分片数可以在租户维度动态调整,已拆分 block 的合并仍沿用meta.json中记录的原始配置。该实现位于 split_merge_compactor.go,其中的splitAndMergeGrouperFactory、splitAndMergeCompactorFactory与configureSplitAndMergeCompactor负责组装这一压缩流水线。正是这套新压缩器,让单个 Mimir 集群得以支撑超十亿活跃序列。
查询分片(Query Sharding):把单条查询拆分到多台机器并行执行
Mimir 2.0 引入的查询分片(query sharding)用于加速高基数或 CPU 密集型查询。其原理是:把数据集拆成更小的shard,由 query-frontend 将每个分片的局部查询分发到不同 querier 上并行执行,最后再聚合局部结果返回完整查询结果。官方宣称在 Grafana Cloud Metrics 集群中实测取得10~30 倍查询加速。
查询分片文档 说明了其适用范围与机制:
- 仅作用于
query(即时查询)与query_range(范围查询)两类 API; - 并非所有查询都可分片:可结合的聚合运算(
sum、min、max、count、avg)可分片,而absent、absent_over_time、histogram_quantile、sort_desc、sort等函数不可分片;即便整条查询不可分片,其内部子表达式仍可能被分片执行; - 分片通过给局部查询注入
__query_shard__标签选择器实现,所有携带该标签的局部查询并行执行,query-frontend 负责拼接/聚合。
相关配置参数(见 configuration parameters):
| 参数 | CLI flag | 默认值 | 说明 |
|---|---|---|---|
query_sharding_total_shards | -query-frontend.query-sharding-total-shards | 16 | 分片总数;0表示禁用查询分片;大于 1 的值向上取整为 2 的幂,与 compactor 的 2 的幂分片数对齐,使 querier 可跳过不可能命中给定查询分片的 block |
query_sharding_max_sharded_queries | -query-frontend.query-sharding-max-sharded-queries | 128 | 单条查询(或衍生子查询)最多可产生的分片查询数,0不限制 |
query_sharding_max_regexp_size_bytes | -query-frontend.query-sharding-max-regexp-size-bytes | 4096 | 对正则匹配器超过该字节数的查询禁用分片,0不限制 |
从实现上,查询分片中间件位于 querysharding.go:newQueryShardingMiddleware先判断查询是否可分片,再把查询重写为分片形式,配合修改过的Queryable(见pkg/frontend/querymiddleware/sharded_queryable.go)执行。其指标命名空间保留了 Cortex 前缀(如cortex_frontend_query_sharding_rewrites_attempted_total、cortex_frontend_sharded_queries_per_query),可用于观测分片改写成功率与单查询分片数量。
联邦规则组(Federated Rule Groups):规则跨租户聚合数据
2.0 引入实验性的联邦规则组,使告警与记录规则可以消费多个租户的指标数据。典型场景是:创建一条记录规则,把tenantA的metricA与tenantB的metricB相加,并把结果写入tenantC。
根据 ruler 组件文档,联邦规则组即带有非空source_tenants字段的规则组,例如:
name: MyGroupName source_tenants: ["tenant-a", "tenant-b"] rules: - record: sum:metric expr: sum(metric)使用要点与限制:
source_tenants为空或省略时,规则组所属租户自身即数据源租户;- 该特性默认跳过(不参与求值),需要同时开启
-ruler.tenant-federation.enabled=true与-tenant-federation.enabled=true(或对应 YAML 配置项),因为它依赖跨租户查询联邦能力; - 求值期间,
source_tenants中每个租户的查询限制(query limits)都会被逐条应用,任一租户超限都会导致整组求值失败且不保存任何部分结果; - 联邦规则产生的序列会携带
__tenant_id__标签; - 需要注意:联邦规则允许把多个源租户的数据写入单个目标租户,会弱化租户间数据隔离,配置访问控制层时应加以考虑。
基数分析 API:识别高基数指标
2.0 新增两个 HTTP API 端点帮助定位高基数指标:
- label_names cardinality 端点:
GET/POST <prometheus-http-prefix>/api/v1/cardinality/label_names。传入指标名时返回该指标用到的全部标签名及各标签名的取值数量;不传指标名时返回基数最高的标签名列表。返回的cardinality字段按label_values_count降序、label_name升序排序,支持limit参数(默认 20,范围 0~500)。 - label_values cardinality 端点:
GET/POST <prometheus-http-prefix>/api/v1/cardinality/label_values。返回基数最高的指标,并可用于统计某一具体标签值对(label-value pair)对应的序列数量。
根据 HTTP API 参考,这两个端点默认禁用,需通过-querier.cardinality-analysis-enabledCLI flag(或对应 YAML 配置)开启;若开启-query-frontend.cache-results且-query-frontend.results-cache-ttl-for-cardinality-query大于0,query-frontend 可能返回结果缓存中的过期响应。
在此基础上,自定义追踪器(custom trackers)允许按特定标签匹配器(label matcher)持续统计活跃序列数量随时间的变化,把"一次性诊断"升级为"持续观测"。
由实验转为稳定的特性
2.0 同时把以下特性从 experimental 提升为 stable:
- 跨租户查询联邦(Cross-tenant query federation):允许一次查询聚合多个租户的序列,获得全局视图。配置开关为
tenant-federation.enabled(对应 CLI flag-tenant-federation.enabled,默认false);启用后,请求方需要在X-Scope-OrgID头中用|分隔多个租户 ID。相关配置还包含tenant-federation.max-tenants(默认0,即不限量)与实验性的tenant-federation.max-concurrent(默认16,限制联邦查询中各租户子查询的并发度)。实现上,tenant_federation.go 负责解析该开关与租户数量限制,merge_queryable.go 中的NewMergeQueryable则把多租户查询合并为一个逻辑查询,并为序列附加__tenant_id__标签以标识来源租户。 - Zone-aware replication(区域感知复制):通过在多个可用区之间复制数据,防止单个可用区故障导致的数据丢失。配套发布了 rollout-operator(Kubernetes 运算符),方便在 K8s 上管理多区域滚动发布。具体配置可参考配置 zone-aware replication。
- Azure Blob Storage 与 OpenStack Swift 支持:对象存储后端从 AWS S3、GCS 扩展为 AWS S3、GCS、Azure Blob Storage、OpenStack Swift,以及任意 S3 兼容对象存储。
- 可水平扩展的 Alertmanager:根据 Alertmanager 组件文档,Alertmanager 可以把工作负载按租户分片到多个副本上,大幅提升集群可承载的租户数量上限。它以租户 ID 决定哪个副本拥有哪个租户;复制因子(replication factor)可配置(
-alertmanager.sharding-ring.replication-factor),副本数需不小于复制因子,告警会在多个副本间复制以降低漏告风险。注意其分片粒度是租户而非单条告警,单租户场景下副本数超过复制因子并不能带来额外收益。 - Query-scheduler 组件:为解决 query-frontend 的扩展性瓶颈,2.0 提供可选的 query-scheduler 组件,官方强烈建议较大规模的集群运行它。根据 query-scheduler 文档,它把"排队"从 query-frontend 中剥离:query-frontend 对查询做拆分/分片或缓存处理后,将查询入队到 query-scheduler 的内存队列,由空闲 querier 领取执行,结果再经 query-frontend 返回客户端。它可通过 DNS(
-query-frontend.scheduler-address)或 hash ring(-query-scheduler.service-discovery-mode=ring及-query-scheduler.ring.*)两种方式被发现,从而支持 query-frontend 的独立水平扩展。
迁移注意事项:从 Cortex 无损迁移到 Grafana Mimir
官方声明Grafana Mimir 与 Cortex 100% 兼容,从 Cortex 迁移到 Mimir 可以在不丢失数据、不停机的前提下完成。2.0 作为主版本升级,对 Cortex 用户引入了一系列破坏性变更;为降低迁移成本,官方做了两件事:
- 在
mimirtool中新增自动化配置转换能力; - 编写了详尽的迁移指南逐步说明所有必需变更。
使用 mimirtool 自动转换配置
从 Cortex 迁移到 Grafana Mimir 指南给出了完整的工具链路径。mimirtool config convert命令负责把Cortex 1.11 配置文件转换为 Mimir 配置文件(源码实现见 convert.go,其中Convert函数按源 schema 将旧 YAML 与 CLI flags 映射为新格式,测试用例convert_test.go中亦有cortex->mimir的显式验证):
- 删除在 Mimir 中不再可用的配置参数;
- 重命名已更名的参数;
- 默认情况下,若某参数被显式设置为与 Cortex 默认值一致,转换时不会更新该值;如需把这些值一并更新为 Mimir 的新默认值,需加
--update-defaults标志。
mimirtool的安装方式为从官方 release 下载对应平台二进制并赋予执行权限,例如 Linux AMD64:
curl -fLo mimirtool https://github.com/grafana/mimir/releases/latest/download/mimirtool-linux-amd64 chmod +x mimirtool迁移中的显著行为变更
migrate 指南还列出了需要人工注意的 breaking changes:
- HTTP 监听端口:Mimir 默认监听
8080,而 Cortex 默认监听80;若需保持80端口,设置-server.http-listen-port=80。 - 默认租户 ID:
-auth.multitenancy=false时,Mimir 默认租户 ID 为anonymous,Cortex(-auth.enabled=false)则为fake;可用-auth.no-auth-tenant=fake匹配 Cortex 的默认租户 ID。 - 移除遗留 HTTP 前缀:Cortex 中已废弃的 legacy HTTP 前缀在 Mimir 中全部移除,涉及查询、distributor、ingester、ruler、alertmanager 的多组端点,例如:
- 查询:
/<legacy-http-prefix>/api/v1/query→<prometheus-http-prefix>/api/v1/query; - distributor:
/<legacy-http-prefix>/push→/api/v1/push; - ingester:
/ring→/ingester/ring、/flush→/ingester/flush; - ruler:
/<legacy-http-prefix>/api/v1/rules→<prometheus-http-prefix>/api/v1/rules; - alertmanager:
/<legacy-http-prefix>→/alertmanager、/status→/multitenant_alertmanager/status。
- 查询:
使用 Jsonnet 库迁移
对于基于 Jsonnet 的部署,可用jsonnet-bundler安装新版库:
jb install github.com/grafana/mimir/operations/mimir@main jb install github.com/grafana/mimir/operations/mimir-mixin@main随后把对 Cortex Jsonnet 库的 import 替换为import 'github.com/grafana/mimir/operations/mimir/mimir.libsonnet',并从<MIMIR>._config对象的成员键中移除cortex_前缀(如cortex_compactor_disk_data_size改为compactor_disk_data_size)。仓库中的 Jsonnet 库即位于 operations/mimir/,监控 mixin 位于 operations/mimir-mixin/。此外,迁移前应确保已安装 Cortex 的告警/记录规则与 dashboards,并把规则通过mimirtool rules上传到 ruler、把面板导入 Grafana。
注意:本文仅介绍查看、安装与配置方式;当前仓库为只读,迁移过程应在你自己的部署环境中进行。
2.0.0 缺陷修复
发布说明记录了 2.0.0 修复的三个关键 bug:
修复一:step 对齐缓存污染未对齐查询(PR 424)
此前存在一个 bug:缓存中面向 step 对齐查询的结果被错误地用于响应未对齐查询,导致用户拿到错误结果。修复同时新增配置参数query-frontend.cache-unaligned-requests(YAML 为cache_unaligned_requests),用于安全地开启"查询 step 未对齐时的结果缓存";该参数默认值为false(见 configuration parameters)。
源码层面可以验证其行为:在 results_cache.go 的isRequestCachable函数中,if !cacheUnalignedRequests && !isRequestStepAligned(req)时直接返回不可缓存原因NotCachableReasonUnalignedTimeRange;而 split_and_cache.go 会按租户聚合ResultsCacheForUnalignedQueryEnabled的结果(对应 limits 接口 limits.go 中的ResultsCacheForUnalignedQueryEnabled(userID string) bool),决定是否允许缓存未对齐请求。
修复二:Alertmanager 配置竞态(PR 224)
修复了 Alertmanager 中的一个竞态条件,该竞态偶尔会导致某租户的配置被空白的 fallback 配置覆盖。Alertmanager 的租户隔离与 fallback 机制在 Alertmanager 组件文档 中有说明:租户上传配置后即可使用/alertmanager路径前缀下的 Alertmanager HTTP API;当租户无配置时使用 fallback 配置,无 fallback 且无租户配置时该租户的 Alertmanager API 不可用。
修复三:memberlist 大消息损坏(PR 551)
修复了memberlist中大消息被损坏的问题。该修复与此前的 memberlist 性能优化共同为"将 memberlist 设为 Mimir hash ring 的默认存储"扫清了障碍——这正是 2.0 简化部署(去除 Consul/etcd 外部依赖)的关键前提之一。
总结
Grafana Mimir 2.0 作为从 Cortex 1.10.0 fork 而来的首个正式版本,围绕"大规模、易部署、可运维"三个目标完成了系统性升级:以 split-and-merge 压缩与查询分片突破单集群的扩展边界,以 memberlist 默认存储与 monolithic mode 简化部署,以 36% 参数裁剪与 basic/advanced/experimental 分类降低配置门槛,同时提供基数分析 API 与内置监控面板来提升可观测性。对 Cortex 存量用户,2.0 提供mimirtool config convert自动化工具与完整迁移指南,实现不丢数据、不停机的平滑升级。若想继续深入,可进一步阅读 架构总览、配置参数全量参考 以及仓库中的 CHANGELOG。
- 时序数据库
- 后端
- 数据存储
- 可观测性
- 云原生
【免费下载链接】mimir
Grafana Mimir provides horizontally scalable, highly available, multi-tenant, long-term storage for Prometheus.
相关推荐
Grafana Mimir 2.5 版本发布说明深度解读:新特性、Helm 变更与关键修复
Grafana Mimir 2.5 版本发布说明深度解读:新特性、Helm 变更与关键修复 本文基于 Grafana Mimir 2.5 官方发布说明( v2.
时序数据库后端数据存储可观测性云原生NumPy 1.9.1 发布说明深度解读:bugfix 版本的关键修复与迁移指引
NumPy 1.9.1 发布说明深度解读:bugfix 版本的关键修复与迁移指引 NumPy 1.9.1 是 1.9.x 系列中的一次纯缺陷修复(bugfix
数据科学科学计算数据分析高性能计算Grafana Mimir Helm Chart 5.2 版本发布说明:PVC 保留策略、原生 Ingress 与关键修复详解
Grafana Mimir Helm Chart 5.2 版本发布说明:PVC 保留策略、原生 Ingress 与关键修复详解 本文基于 mimir distr
时序数据库后端数据存储可观测性云原生
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考