如何避免与prometheus模块结合使用的metricbeat中的“超出总字段限制”错误?
Posted
技术标签:
【中文标题】如何避免与prometheus模块结合使用的metricbeat中的“超出总字段限制”错误?【英文标题】:How to avoid "Limit of total fields exceeded" error in metricbeat in conjunction with the prometheus module? 【发布时间】:2022-01-08 00:31:09 【问题描述】:我正在使用来自 helm.elastic.co 的 helm 图表在 kubernetes 中运行 metricbeat。 这导致 metricbeat 将具有 3776 个字段的巨大索引模板加载到 elasticsearch 索引中。 但实际只使用了 633 个并将值发送到索引。
问题是,当 metricbeat-metricbeat-metrics pod 尝试将事件发送到 elasticsearch 时,我收到以下错误:
Cannot index event ..."reason":"Limit of total fields [5000] has been exceeded"
此错误发生在 metricbeat 实例中,其中使用了带有“收集器”度量集的 prometheus 模块。 我不确定是加载的模板是原因,还是从 prometheus 转发的事件实际上每个包含超过 5000 个字段。
尽管如此: elasticsearch 加载这么大的模板是常见的做法吗? 如果不是:将模板限制为实际使用的字段的方法是什么?
编辑:
进一步分析得出结论,elasticsearch模板的大小并没有导致这个错误: 仅当 metricbeat 中的 prometheus 模块处于活动状态时,才会发生索引错误。在这种情况下,模板大小保持不变。
prometheus 应该从正在运行的 pod 中抓取指标。 最初的指标数量是:
总共有 61274 个指标 (__name__!=""
)
956 个不同的指标名称。 (group by(__name__) (__name__!=""
)
我更改了prometheus的scrape设置,导致:
总共 118 个指标 (__name__!=""
)
55 个不同的指标名称。 (group by(__name__) (__name__!=""
)
metricbeat的prometheus模块配置为:
- module: prometheus
period: 30s
metricsets: ["collector"]
hosts: ["prometheus-server"]
metrics_path: '/federate'
query:
'match[]': 'job="kubernetes-pods"'
processors:
- add_cloud_metadata: ~
该查询 job="kubernetes-pods"
的结果恰好是 118 系列。
但是:Cannot index event ...
错误仍然出现!
这是完整的错误日志行:
2021-12-03T07:15:07.227Z WARN [elasticsearch] elasticsearch/client.go:408 Cannot index event publisher.EventContent:beat.EventTimestamp:time.Timewall:0xc0628ede3b502221, ext:907213012182, loc:(*time.Location)(0x5862e80), Meta:null, Fields:"agent":"ephemeral_id":"e7ef097d-95c8-4f60-a63f-0de436c45195","hostname":"metricbeat-metricbeat-metrics-59c8d8b865-b2gqc","id":"2c17c983-631e-4f70-ab36-a56bc1b5b254","name":"metricbeat-metricbeat-metrics-59c8d8b865-b2gqc","type":"metricbeat","version":"7.10.0","cloud":"account":"id":"xxxx","availability_zone":"eu-central-1b","image":"id":"ami-xxxx","instance":"id":"i-xxxx","machine":"type":"t3a.xlarge","provider":"aws","region":"eu-central-1","ecs":"version":"1.6.0","event":"dataset":"prometheus.collector","duration":5888251,"module":"prometheus","host":"name":"metricbeat-metricbeat-metrics-59c8d8b865-b2gqc","metricset":"name":"collector","period":30000,"prometheus":"labels":"app_kubernetes_io_instance":"...","app_kubernetes_io_name":"my-pod-name","instance":"10.124.2.235:8080","job":"kubernetes-pods","kubernetes_namespace":"mynamespace","kubernetes_pod_name":"my-pod-85746d8c4f-wb4kq","name":"rabbit","pod_template_hash":"85746d8c4f","metrics":"rabbitmq_acknowledged_published_total":0.000000,"rabbitmq_acknowledged_total":9.000000,"rabbitmq_channels":2.000000,"rabbitmq_connections":1.000000,"rabbitmq_consumed_total":9.000000,"rabbitmq_failed_to_publish_total":0.000000,"rabbitmq_not_acknowledged_published_total":0.000000,"rabbitmq_published_total":0.000000,"rabbitmq_rejected_total":0.000000,"rabbitmq_unrouted_published_total":0.000000,"service":"address":"http://prometheus-server/federate?match%5B%5D=%7Bjob%3D%22kubernetes-pods%22%7D","type":"prometheus", Private:interface (nil), TimeSeries:true, Flags:0x0, Cache:publisher.EventCachem:common.MapStr(nil) (status=400): "type":"illegal_argument_exception","reason":"Limit of total fields [5000] has been exceeded"
使用查询api而不是federation会导致同样的错误:
- module: prometheus
period: 30s
metricsets: ["collector"]
hosts: ["prometheus-server"]
metrics_path: /metrics
metrics_filters:
include: [".+"]
只有当我指定一个包含模式,它匹配一些指标——比如“jvm.*”——错误才会消失。 但我绝对不想在 metricbeat 配置中明确包含我的所有指标。
【问题讨论】:
3776 个字段肯定很多。你试过overriding the template吗? 没有。但事实证明,模板大小实际上并没有导致这个错误。该错误仅在从 prometheus 服务器转发事件时发生。禁用prometheus后,模板大小不变,但报错消失了。 您在 Prometheus 中公开了多少指标?不正确的设置(例如,为每个客户创建一个新指标而不是使用标签)可能会导致指标爆炸,这也会影响 Elasticsearch。 prometheus 服务器的指标集非常有限。在 prometheus gui 中查询group by(__name__) (__name__ != "")
仅返回 55 个系列。
我将 metricbeat 设置更改为使用查询 api 而不是联合(如 metricbeat 所建议的那样:这会导致相同的错误。当我在 include 中使用例如 "jvm.*"
的模式时没有错误子句(19系列匹配)
【参考方案1】:
我通过将index.mapping.total_fields.limit
增加到 10000 解决了这个问题。
只要 metricbeat 能够应用新的索引模板,错误就会消失。这意味着,我需要删除当前索引,metricbeat 在其中附加文档并重新启动 metricbeat 进程。
这并不令人满意。 但据我所知,大多数用户只是使用稍大的默认索引模板而没有任何问题。
【讨论】:
以上是关于如何避免与prometheus模块结合使用的metricbeat中的“超出总字段限制”错误?的主要内容,如果未能解决你的问题,请参考以下文章
prometheus 与 alertmanager 结合 发送邮件报警
Prometheus 中的 increase() 有时会使值翻倍:如何避免?
如何将 Testcontainers 与 @DataJpaTest 结合使用以避免代码重复?
在Python 3中将Ctrl-D与sys.stdin.readlines()结合使用后,如何避免input()出现EOFError?