介绍k8s集群中部署prometheus、grafana、alertmanager,并且配置prometheus的动态、静态服务发现,实现对容器、物理节点、service、pod等资源指标监控,并在Grafana的web界面展示prometheus的监控指标,然后通过配置自定义告警规则,通过alertmanager实现qq、钉钉、微信报警。Promql 语法、prometheus数据类型。
1、prometheus 1、prometheus介绍 Prometheus是一个开源的系统监控和报警系统,现在已经加入到CNCF 基金会,成为继k8s之后第二个在CNCF托管的项目,在kubernetes容器管理系统中,通常会搭配prometheus进行监控,同时也支持多种exporter采集数据,还支持pushgateway 进行数据上报,Prometheus性能足够支撑上万台规模的集群。
2、prometheus特点 1、多维度数据模型 每一个时间序列数据都由metric度量指标名称和它的标签labels键值对集合唯一确定:
这个metric度量指标名称指定监控目标系统的测量特征(如:http_requests_total- 接收http请求的总计数)。labels开启了Prometheus的多维数据模型:对于相同的度量名称,通过不同标签列表的结合, 会形成特定的度量维度实例。(例如:所有包含度量名称为/api/tracks的http请求,打上method=POST的标签,则形成了具体的http请求)。这个查询语言在这些度量和标签列表的基础上进行过滤和聚合。改变任何度量上的任何标签值,则会形成新的时间序列图。
2、灵活的查询语言(PromQL) 可以对采集的metrics指标进行加法,乘法,连接等操作
3、可以直接在本地部署,不依赖其他分布式存储 4、通过基于HTTP的pull方式采集时序数据 5、可以通过中间网关pushgateway的方式把时间序列数据推送到prometheus server端 6、可通过服务发现或者静态配置来发现目标服务对象(targets) 7、有多种可视化图像界面,如Grafana等 8、高效的存储,每个采样数据占3.5 bytes左,300万的时间序列,30s间隔,保留60天,消耗磁盘大概200G 9、做高可用,可以对数据做异地备份,联邦集群,部署多套prometheus,pushgateway上报数据 10、样本 在时间序列中的每一个点称为一个样本(sample),样本由以下三部分组成:
1、指标(metric):指标名称和描述当前样本特征的 labelsets;
2、时间戳(timestamp):一个精确到毫秒的时间戳;
3、样本值(value): 一个 folat64 的浮点型数据表示当前样本的值。
表示方式:
通过如下表达方式表示指定指标名称和指定标签集合的时间序列:
{=, …}
例如,指标名称为 api_http_requests_total,标签为 method=”POST” 和 handler=”/messages” 的时间序列可以表示为:
api_http_requests_total{method=”POST”, handler=”/messages”}
3、Prometheus组件介绍 1、Prometheus server 用于收集和存储时间序列数据,采集数据使用Retrieval来实现的。
2、Client Library 客户端库,检测应用程序代码,当Protheus抓取实例的HTTP端点时,客户端会将所有追踪的metrics指标的当前状态发送到protheus server端
3、Exporters prometheus支持多种exporter,通过exporter可以采集metrics数据,然后发送到prometheus server端,所有向prometheus server提供监控数据的程序都可以称为exporter
4、Alertmanager 从prometheus server端接收到alerts后,会进行去重,分组,并路由到相应的接收方,发出警报,常见的接收方式有:电子邮件、微信、钉钉、slack
5、Grafana 监控仪表盘,可视化监控数据
6、pushgateway 各个目标主机可上报数据到pushgateway,然后protheus server统一从pushgateway上拉取数据
从上图可发现,Prometheus整个生态圈组成主要包括prometheus server,Exporter,pushgateway,alertmanager,grafana,Web ui界面,Prometheus server由三个部分组成,Retrieval,Storage,PromQL
1.Retrieval负责在活跃的target主机上抓取监控指标数据
2.Storage存储主要是把采集到的数据存储到磁盘中
3.PromQL是Prometheus提供的查询语言模块。
4、Prometheus工作流程 1.Prometheus server可定期从活跃的(up)目标主机上(target)拉取监控指标数据,目标主机的监控数据可通过配置静态job或者服务发现的方式被prometheus server采集到,这种方式默认的pull方式拉取指标;也可通过pushgateway把采集的数据上报到prometheus server中;还可通过一些组件自带的exporter采集相应组件的数据;
2.Prometheus server把采集到的监控指标数据保存到本地磁盘或者数据库;
3.Prometheus采集的监控指标数据按时间序列存储,通过配置报警规则,把触发的报警发送到alertmanager
4.Alertmanager通过配置报警接收方,发送报警到邮件,微信或者钉钉等
5.Prometheus 自带的web ui界面提供PromQL查询语言,可查询监控数据
6.Grafana可接入prometheus数据源,把监控数据以图形化形式展示出
5、Prometheus和zabbix对比分析
6、Prometheus的集中部署方式 1、基本高可用模式
基本的HA模式只能确保Promthues服务的可用性问题,但是不解决Prometheus Server之间的数据一致性问题以及持久化问题(数据丢失后无法恢复),也无法进行动态的扩展。因此这种部署方式适合监控规模不大,Promthues Server也不会频繁发生迁移的情况,并且只需要保存短周期监控数据的场景。
2、基本高可用+远程存储
在解决了Promthues服务可用性的基础上,同时确保了数据的持久化,当Promthues Server发生宕机或者数据丢失的情况下,可以快速的恢复。 同时Promthues Server可能很好的进行迁移。因此,该方案适用于用户监控规模不大,但是希望能够将监控数据持久化,同时能够确保Promthues Server的可迁移性的场景。
3、基本HA+远程存储+联邦集群方案
Promthues的性能瓶颈主要在于大量的采集任务,因此用户需要利用Prometheus联邦集群的特性,将不同类型的采集任务划分到不同的Promthues子服务中,从而实现功能分区。例如一个Promthues Server负责采集基础设施相关的监控指标,另外一个Prometheus Server负责采集应用监控指标。再有上层Prometheus Server实现对数据的汇聚。
7、Prometheus的四种数据类型 1、Counter Counter是计数器类型
1、Counter 用于累计值,例如记录请求次数、任务完成数、错误发生次数。
2、一直增加,不会减少。
3、重启进程后,会被重置。
1 2 http_response_total{method="GET" ,endpoint="/api/tracks" } 100 http_response_total{method="GET" ,endpoint="/api/tracks" } 160
Counter 类型数据可以让用户方便的了解事件产生的速率的变化,在PromQL内置的相关操作函数可以提供相应的分析,比如以HTTP应用请求量来进行说明:
1、通过rate()函数获取HTTP请求量的增长率
rate(http_requests_total[5m])
2、查询当前系统中,访问量前10的HTTP地址
topk(10, http_requests_total)
2、Gauge Gauge是测量器类型:
1、Gauge是常规数值,例如温度变化、内存使用变化。
2、可变大,可变小。
3、重启进程后,会被重置
1 2 3 4 memory_usage_bytes{host="master-01" } 100 memory_usage_bytes{host="master-01" } 30 memory_usage_bytes{host="master-01" } 50 memory_usage_bytes{host="master-01" } 80
对于 Gauge 类型的监控指标,通过 PromQL 内置函数 delta() 可以获取样本在一段时间内的变化情况,例如,计算 CPU 温度在两小时内的差异:
dalta(cpu_temp_celsius{host=”zeus”}[2h])
你还可以通过PromQL 内置函数 predict_linear() 基于简单线性回归的方式,对样本数据的变化趋势做出预测。例如,基于 2 小时的样本数据,来预测主机可用磁盘空间在 4 个小时之后的剩余情况:
predict_linear(node_filesystem_free{job=”node”}[2h], 4 * 3600) < 0
3、histogram histogram是柱状图,在Prometheus系统的查询语言中,有三种作用:
1、在一段时间范围内对数据进行采样(通常是请求持续时间或响应大小等),并将其计入可配置的存储桶(bucket)中. 后续可通过指定区间筛选样本,也可以统计样本总数,最后一般将数据展示为直方图。
2、对每个采样点值累计和(sum)
3、对采样点的次数累计和(count)
度量指标名称: [basename]_上面三类的作用度量指标名称
1、[basename]_bucket{le=”上边界”}, 这个值为小于等于上边界的所有采样点数量
2、[basename]_sum
3、[basename]_count
小结:如果定义一个度量类型为Histogram,则Prometheus会自动生成三个对应的指标
1、为什需要用histogram柱状图? 在大多数情况下人们都倾向于使用某些量化指标的平均值,例如 CPU 的平均使用率、页面的平均响应时间。这种方式的问题很明显,以系统 API 调用的平均响应时间为例:如果大多数 API 请求都维持在 100ms 的响应时间范围内,而个别请求的响应时间需要 5s,那么就会导致某些 WEB 页面的响应时间落到中位数的情况,而这种现象被称为长尾问题。
为了区分是平均的慢还是长尾的慢,最简单的方式就是按照请求延迟的范围进行分组。例如,统计延迟在 010ms 之间的请求数有多少,而 1020ms 之间的请求数又有多少。通过这种方式可以快速分析系统慢的原因。Histogram 和 Summary 都是为了能够解决这样问题的存在,通过 Histogram 和 Summary 类型的监控指标,我们可以快速了解监控样本的分布情况。
Histogram 类型的样本会提供三种指标(假设指标名称为 ):
样本的值分布在 bucket 中的数量,命名为 _bucket{le=”<上边界>”}。解释的更通俗易懂一点,这个值表示指标值小于等于上边界的所有样本数量。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 1、在总共2次请求当中。http 请求响应时间 <=0.005 秒 的请求次数为0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="0.005" ,} 0.0 2、在总共2次请求当中。http 请求响应时间 <=0.01 秒 的请求次数为0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="0.01" ,} 0.0 3、在总共2次请求当中。http 请求响应时间 <=0.025 秒 的请求次数为0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="0.025" ,} 0.0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="0.05" ,} 0.0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="0.075" ,} 0.0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="0.1" ,} 0.0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="0.25" ,} 0.0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="0.5" ,} 0.0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="0.75" ,} 0.0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="1.0" ,} 0.0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="2.5" ,} 0.0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="5.0" ,} 0.0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="7.5" ,} 2.0 4、在总共2次请求当中。http 请求响应时间 <=10 秒 的请求次数为 2 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="10.0" ,} 2.0 io_namespace_http_requests_latency_seconds_histogram_bucket{path="/" ,method="GET" ,code="200" ,le="+Inf" ,} 2.0 所有样本值的大小总和,命名为 <basename>_sum。 5、实际含义: 发生的2次 http 请求总的响应时间为 13.107670803000001 秒 io_namespace_http_requests_latency_seconds_histogram_sum{path="/" ,method="GET" ,code="200" ,} 13.107670803000001 样本总数,命名为 <basename>_count。值和 <basename>_bucket{le="+Inf" } 相同。 6、实际含义: 当前一共发生了 2 次 http 请求 io_namespace_http_requests_latency_seconds_histogram_count{path="/" ,method="GET" ,code="200" ,} 2.0
注意:
bucket 可以理解为是对数据指标值域的一个划分,划分的依据应该基于数据值的分布。注意后面的采样点是包含前面的采样点的,假设 xxx_bucket{…,le=”0.01”} 的值为 10,而 xxx_bucket{…,le=”0.05”} 的值为 30,那么意味着这 30 个采样点中,有 10 个是小于 0.01s的,其余 20 个采样点的响应时间是介于0.01s 和 0.05s之间的。
可以通过 histogram_quantile() 函数 来计算 Histogram 类型样本的分位数 。分位数可能不太好理解,你可以理解为分割数据的点。我举个例子,假设样本的 9 分位数(quantile=0.9)的值为 x,即表示小于 x 的采样值的数量占总体采样值的 90%。Histogram 还可以用来计算应用性能指标值(Apdex score )。
4、summary 与 Histogram 类型类似,用于表示一段时间内的数据采样结果(通常是请求持续时间或响应大小等),但它直接存储了分位数(通过客户端计算,然后展示出来),而不是通过区间来计算。它也有三种作用:
1、对于每个采样点进行统计,并形成分位图。(如:正态分布一样,统计低于60分不及格的同学比例,统计低于80分的同学比例,统计低于95分的同学比例)
2、统计班上所有同学的总成绩(sum)
3、统计班上同学的考试总人数(count)
带有度量指标的[basename]的summary 在抓取时间序列数据有如命名。
1、观察时间的φ-quantiles (0 ≤ φ ≤ 1), 显示为[basename]{分位数=”[φ]”}
2、[basename]_sum, 是指所有观察值的总和
3、[basename]_count, 是指已观察到的事件计数值
样本值的分位数分布情况,命名为 {quantile="
<φ>"}
。
1、含义:这 12 次 http 请求中有 50% 的请求响应时间是 3.052404983s
io_namespace_http_requests_latency_seconds_summary{path=”/“,method=”GET”,code=”200”,quantile=”0.5”,} 3.052404983
2、含义:这 12 次 http 请求中有 90% 的请求响应时间是 8.003261666s
io_namespace_http_requests_latency_seconds_summary{path=”/“,method=”GET”,code=”200”,quantile=”0.9”,} 8.003261666
所有样本值的大小总和,命名为 _sum
。
1、含义:这12次 http 请求的总响应时间为 51.029495508s
io_namespace_http_requests_latency_seconds_summary_sum{path=”/“,method=”GET”,code=”200”,} 51.029495508
样本总数,命名为 _count
。
1、含义:当前一共发生了 12 次 http 请求
io_namespace_http_requests_latency_seconds_summary_count{path=”/“,method=”GET”,code=”200”,} 12.0
现在可以总结一下 Histogram 与 Summary 的异同:
它们都包含了 _sum 和 _count 指标
Histogram 需要通过 _bucket 来计算分位数,而 Summary 则直接存储了分位数的值。
prometheus_tsdb_wal_fsync_duration_seconds{quantile=”0.5”} 0.012352463
prometheus_tsdb_wal_fsync_duration_seconds{quantile=”0.9”} 0.014458005
prometheus_tsdb_wal_fsync_duration_seconds{quantile=”0.99”} 0.017316173
prometheus_tsdb_wal_fsync_duration_seconds_sum 2.888716127000002
prometheus_tsdb_wal_fsync_duration_seconds_count 216
从上面的样本中可以得知当前Promtheus Server进行wal_fsync操作的总次数为216次,耗时2.888716127000002s。其中中位数(quantile=0.5)的耗时为0.012352463,9分位数(quantile=0.9)的耗时为0.014458005s。
8、Promethus能监控什么 • Databases
• Hardware related
• Messaging systems
• Storage
• HTTP
• APIs
• Logging
• Other monitoring systems
• Miscellaneous
• Software exposing Prometheus metrics
1、DATABASES-数据库 • Aerospike exporter
• ClickHouse exporter
• Consul exporter (official)
• Couchbase exporter
• CouchDB exporter
• ElasticSearch exporter
• EventStore exporter
• Memcached exporter (official)
• MongoDB exporter
• MSSQL server exporter
• MySQL server exporter (official)
• OpenTSDB Exporter
• Oracle DB Exporter
• PgBouncer exporter
• PostgreSQL exporter
• ProxySQL exporter
• RavenDB exporter
• Redis exporter
• RethinkDB exporter
• SQL exporter
• Tarantool metric library
• Twemproxy
• apcupsd exporter
• Collins exporter
• IBM Z HMC exporter
• IoT Edison exporter
• IPMI exporter
• knxd exporter
• Netgear Cable Modem Exporter
• Node/system metrics exporter (official)
• NVIDIA GPU exporter
• ProSAFE exporter
• Ubiquiti UniFi exporter
3、Messaging systems-消息服务 • Beanstalkd exporter
• Gearman exporter
• Kafka exporter
• NATS exporter
• NSQ exporter
• Mirth Connect exporter
• MQTT blackbox exporter
• RabbitMQ exporter
• RabbitMQ Management Plugin exporter
4、Storage-存储 • Ceph exporter
• Ceph RADOSGW exporter
• Gluster exporter
• Hadoop HDFS FSImage exporter
• Lustre exporter
• ScaleIO exporter
5、http-网站服务 • Apache exporter
• HAProxy exporter (official)
• Nginx metric library
• Nginx VTS exporter
• Passenger exporter
• Squid exporter
• Tinyproxy exporter
• Varnish exporter
• WebDriver exporter
6、API • AWS ECS exporter
• AWS Health exporter
• AWS SQS exporter
• Cloudflare exporter
• DigitalOcean exporter
• Docker Cloud exporter
• Docker Hub exporter
• GitHub exporter
• InstaClustr exporter
• Mozilla Observatory exporter
• OpenWeatherMap exporter
• Pagespeed exporter
• Rancher exporter
• Speedtest exporter
7、Logging-日志 • Fluentd exporter
• Google’s mtail log data extractor
• Grok exporter
8、Other monitoring systems • Akamai Cloudmonitor exporter
• Alibaba Cloudmonitor exporter
• AWS CloudWatch exporter (official)
• Cloud Foundry Firehose exporter
• Collectd exporter (official)
• Google Stackdriver exporter
• Graphite exporter (official)
• Heka dashboard exporter
• Heka exporter
• InfluxDB exporter (official)
• JavaMelody exporter
• JMX exporter (official)
• Munin exporter
• Nagios / Naemon exporter
• New Relic exporter
• NRPE exporter
• Osquery exporter
• OTC CloudEye exporter
• Pingdom exporter
• scollector exporter
• Sensu exporter
• SNMP exporter (official)
• StatsD exporter (official)
9、Miscellaneous-其他 • ACT Fibernet Exporter
• Bamboo exporter
• BIG-IP exporter
• BIND exporter
• Bitbucket exporter
• Blackbox exporter (official)
• BOSH exporter
• cAdvisor
• Cachet exporter
• ccache exporter
• Confluence exporter
• Dovecot exporter
• eBPF exporter
• Ethereum Client exporter
• Jenkins exporter
• JIRA exporter
• Kannel exporter
• Kemp LoadBalancer exporter
• Kibana Exporter
• Meteor JS web framework exporter
• Minecraft exporter module
• PHP-FPM exporter
• PowerDNS exporter
• Presto exporter
• Process exporter
• rTorrent exporter
• SABnzbd exporter
• Script exporter
• Shield exporter
• SMTP/Maildir MDA blackbox prober
• SoftEther exporter
• Transmission exporter
• Unbound exporter
• Xen exporter
10、Software exposing Prometheus metrics-Prometheus度量指标 • App Connect Enterprise
• Ballerina
• Ceph
• Collectd
• Concourse
• CRG Roller Derby Scoreboard (direct)
• Docker Daemon
• Doorman (direct)
• Etcd (direct)
• Flink
• FreeBSD Kernel
• Grafana
• JavaMelody
• Kubernetes (direct)
• Linkerd
9、Prometheus对kubernetes的监控 对于Kubernetes而言,我们可以把当中所有的资源分为几类:
• 基础设施层(Node):集群节点,为整个集群和应用提供运行时资源
• 容器基础设施(Container):为应用提供运行时环境
• 用户应用(Pod):Pod中会包含一组容器,它们一起工作,并且对外提供一个(或者一组)功能
• 内部服务负载均衡(Service):在集群内,通过Service在集群暴露应用功能,集群内应用和应用之间访问时提供内部的负载均衡
• 外部访问入口(Ingress):通过Ingress提供集群外的访问入口,从而可以使外部客户端能够访问到部署在Kubernetes集群内的服务
因此,如果要构建一个完整的监控体系,我们应该考虑,以下5个方面:
• 集群节点状态监控:从集群中各节点的kubelet服务获取节点的基本运行状态;
• 集群节点资源用量监控:通过Daemonset的形式在集群中各个节点部署Node Exporter采集节点的资源使用情况;
• 节点中运行的容器监控:通过各个节点中kubelet内置的cAdvisor中获取个节点中所有容器的运行状态和资源使用情况;
• 如果在集群中部署的应用程序本身内置了对Prometheus的监控支持,那么我们还应该找到相应的Pod实例,并从该Pod实例中获取其内部运行状态的监控指标。
• 对k8s本身的组件做监控:apiserver、scheduler、controller-manager、kubelet、kube-proxy
10、node-exporter组件安装和配置 1、介绍 node-exporter可以采集机器(物理机、虚拟机、云主机等)的监控指标数据,能够采集到的指标包括CPU, 内存,磁盘,网络,文件数等信息。
2、安装node-exporter 将node-export.tar.gz镜像压缩包上传到k8s集群的各个节点上,手动解压 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 [root@master1 ~] prom/node-exporter v0.16.0 188af75e2de0 4 years ago 22.9MB [root@master2 ~] prom/node-exporter v0.16.0 188af75e2de0 4 years ago 22.9MB [root@master3 ~] prom/node-exporter v0.16.0 188af75e2de0 4 years ago 22.9MB [root@node1 ~] prom/node-exporter v0.16.0 188af75e2de0 4 years ago 22.9MB [root@node2 ~] prom/node-exporter v0.16.0 188af75e2de0 4 years ago 22.9MB [root@node3 ~] prom/node-exporter v0.16.0 188af75e2de0 4 years ago 22.9MB
创建node-export.yml 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 [root@master1 promethus] apiVersion: apps/v1 kind: DaemonSet metadata: name: node-exporter namespace: monitor-sa labels: name: node-exporter spec: selector: matchLabels: name: node-exporter template: metadata: labels: name: node-exporter spec: hostPID: true hostIPC: true hostNetwork: true containers: - name: node-exporter image: prom/node-exporter:v0.16.0 ports: - containerPort: 9100 resources: requests: cpu: 0.15 securityContext: privileged: true args: - --path.procfs - /host/proc - --path.sysfs - /host/sys - --collector.filesystem.ignored-mount-points - '"^/(sys|proc|dev|host|etc)($|/)"' volumeMounts: - name: dev mountPath: /host/dev - name: proc mountPath: /host/proc - name: sys mountPath: /host/sys - name: rootfs mountPath: /rootfs tolerations: - key: "node-role.kubernetes.io/master" operator: "Exists" effect: "NoSchedule" volumes: - name: proc hostPath: path: /proc - name: dev hostPath: path: /dev - name: sys hostPath: path: /sys - name: rootfs hostPath: path: / [root@master1 promethus] NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES node-exporter-fbpkr 1/1 Running 0 7m52s 192.168.106.22 node2 <none> <none> node-exporter-ffn4x 1/1 Running 0 7m52s 192.168.106.21 node1 <none> <none> node-exporter-z78gj 1/1 Running 0 7m52s 192.168.106.23 node3 <none> <none>
查看主机的cpu使用情况 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 [root@master1 promethus] % Total % Received % Xferd Average Speed Time Time Time Current Dload Upload Total Spent Left Speed 0 0 0 0 0 0 0 0 --:--:-- --:--:-- --:--:-- 0 node_cpu_seconds_total{cpu="0" ,mode="idle" } 623938.6 node_cpu_seconds_total{cpu="0" ,mode="iowait" } 318.36 node_cpu_seconds_total{cpu="0" ,mode="irq" } 0 node_cpu_seconds_total{cpu="0" ,mode="nice" } 0.27 node_cpu_seconds_total{cpu="0" ,mode="softirq" } 386.91 node_cpu_seconds_total{cpu="0" ,mode="steal" } 474.33 node_cpu_seconds_total{cpu="0" ,mode="system" } 9936.77 node_cpu_seconds_total{cpu="0" ,mode="user" } 11128.03 node_cpu_seconds_total{cpu="1" ,mode="idle" } 623877.85 node_cpu_seconds_total{cpu="1" ,mode="iowait" } 466.91 node_cpu_seconds_total{cpu="1" ,mode="irq" } 0 node_cpu_seconds_total{cpu="1" ,mode="nice" } 0.27 node_cpu_seconds_total{cpu="1" ,mode="softirq" } 181.27 node_cpu_seconds_total{cpu="1" ,mode="steal" } 488.87 node_cpu_seconds_total{cpu="1" ,mode="system" } 9762.55 node_cpu_seconds_total{cpu="1" ,mode="user" } 11358.75 node_cpu_seconds_total{cpu="2" ,mode="idle" } 623435.87 node_cpu_seconds_total{cpu="2" ,mode="iowait" } 483.85 node_cpu_seconds_total{cpu="2" ,mode="irq" } 0 node_cpu_seconds_total{cpu="2" ,mode="nice" } 0.13 node_cpu_seconds_total{cpu="2" ,mode="softirq" } 136.85 node_cpu_seconds_total{cpu="2" ,mode="steal" } 495.61 node_cpu_seconds_total{cpu="2" ,mode="system" } 9875.75 node_cpu_seconds_total{cpu="2" ,mode="user" } 11594.71 node_cpu_seconds_total{cpu="3" ,mode="idle" } 625033.69 node_cpu_seconds_total{cpu="3" ,mode="iowait" } 455.69 node_cpu_seconds_total{cpu="3" ,mode="irq" } 0 node_cpu_seconds_total{cpu="3" ,mode="nice" } 0.18 node_cpu_seconds_total{cpu="3" ,mode="softirq" } 121 node_cpu_seconds_total{cpu="3" ,mode="steal" } 488.24 node_cpu_seconds_total{cpu="3" ,mode="system" } 9200.91 node_cpu_seconds_total{cpu="3" ,mode="user" } 11219.9 100 101k 100 101k 0 0 5913k 0 --:--:-- --:--:-- --:--:-- 6333k
#HELP:解释当前指标的含义,上面表示在每种模式下node节点的cpu花费的时间,以s为单位
#TYPE:说明当前指标的数据类型,上面是counter类型
node_cpu_seconds_total{cpu=”0”,mode=”idle”} :
cpu0上idle进程占用CPU的总时间,CPU占用时间是一个只增不减的度量指标,从类型中也可以看出node_cpu的数据类型是counter(计数器)
counter计数器: 只是采集递增的指标
1 2 3 4 5 6 7 8 9 10 11 12 13 [root@master1 promethus] % Total % Received % Xferd Average Speed Time Time Time Current Dload Upload Total Spent Left Speed 0 0 0 0 0 0 0 0 --:--:-- --:--:-- --:--:-- 0 node_load1 0 node_load15 0.1 node_load5 0.04 100 101k 100 101k 0 0 6262k 0 --:--:-- --:--:-- --:--:-- 6753k
node_load1该指标反映了当前主机在最近一分钟以内的负载情况,系统的负载情况会随系统资源的使用而变化,因此node_load1反映的是当前状态,数据可能增加也可能减少,从注释中可以看出当前指标类型为gauge(标准尺寸)
gauge标准尺寸: 统计的指标可增加可减少
11、Promethus server安装和配置 1、创建一个sa账号,对sa做rbac授权 1 2 3 4 5 6 7 [root@master1 promethus] serviceaccount/monitor created [root@master1 promethus] clusterrolebinding.rbac.authorization.k8s.io/monitor-clusterrolebinding created
2、创建prometheus数据存储目录(在node1节点上) 1 2 [root@node1 ~] [root@node1 ~]
3、安装prometheus server服务 创建configmap存储卷,用来存放prometheus配置信息 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 [root@master1 promethus] --- kind: ConfigMap apiVersion: v1 metadata: labels: app: prometheus name: prometheus-config namespace: monitor-sa data: prometheus.yml: | global: scrape_interval: 15s scrape_timeout: 10s evaluation_interval: 1m scrape_configs: - job_name: 'kubernetes-node' kubernetes_sd_configs: - role: node relabel_configs: - source_labels: [__address__] regex: '(.*):10250' replacement: '${1}:9100' target_label: __address__ action: replace - action: labelmap regex: __meta_kubernetes_node_label_(.+) - job_name: 'kubernetes-node-cadvisor' kubernetes_sd_configs: - role: node scheme: https tls_config: ca_file: /var/run/secrets/kubernetes.io/serviceaccount/ca.crt bearer_token_file: /var/run/secrets/kubernetes.io/serviceaccount/token relabel_configs: - action: labelmap regex: __meta_kubernetes_node_label_(.+) - target_label: __address__ replacement: kubernetes.default.svc:443 - source_labels: [__meta_kubernetes_node_name] regex: (.+) target_label: __metrics_path__ replacement: /api/v1/nodes/${1} /proxy/metrics/cadvisor - job_name: 'kubernetes-apiserver' kubernetes_sd_configs: - role: endpoints scheme: https tls_config: ca_file: /var/run/secrets/kubernetes.io/serviceaccount/ca.crt bearer_token_file: /var/run/secrets/kubernetes.io/serviceaccount/token relabel_configs: - source_labels: [__meta_kubernetes_namespace, __meta_kubernetes_service_name, __meta_kubernetes_endpoint_port_name] action: keep regex: default;kubernetes;https - job_name: 'kubernetes-service-endpoints' kubernetes_sd_configs: - role: endpoints relabel_configs: - source_labels: [__meta_kubernetes_service_annotation_prometheus_io_scrape] action: keep regex: true - source_labels: [__meta_kubernetes_service_annotation_prometheus_io_scheme] action: replace target_label: __scheme__ regex: (https?) - source_labels: [__meta_kubernetes_service_annotation_prometheus_io_path] action: replace target_label: __metrics_path__ regex: (.+) - source_labels: [__address__, __meta_kubernetes_service_annotation_prometheus_io_port] action: replace target_label: __address__ regex: ([^:]+)(?::\d+)?;(\d+) replacement: $1 :$2 - action: labelmap regex: __meta_kubernetes_service_label_(.+) - source_labels: [__meta_kubernetes_namespace] action: replace target_label: kubernetes_namespace - source_labels: [__meta_kubernetes_service_name] action: replace target_label: kubernetes_name [root@master1 promethus]
创建prometheus的service 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 [root@master1 prometheus] apiVersion: v1 kind: Service metadata: name: prometheus namespace: monitor-sa labels: app: prometheus spec: type : NodePort ports: - port: 9090 targetPort: 9090 protocol: TCP selector: app: prometheus component: server
部署prometheus 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 [root@master1 prometheus] --- apiVersion: apps/v1 kind: Deployment metadata: name: prometheus-server namespace: monitor-sa labels: app: prometheus spec: replicas: 1 selector: matchLabels: app: prometheus component: server template: metadata: labels: app: prometheus component: server annotations: prometheus.io/scrape: 'false' spec: nodeName: node1 serviceAccountName: monitor containers: - name: prometheus image: prom/prometheus:v2.2.1 imagePullPolicy: IfNotPresent command : - prometheus - --config.file=/etc/prometheus/prometheus.yml - --storage.tsdb.path=/prometheus - --storage.tsdb.retention=720h - --web.enable-lifecycle ports: - containerPort: 9090 protocol: TCP volumeMounts: - mountPath: /etc/prometheus/prometheus.yml name: prometheus-config subPath: prometheus.yml - mountPath: /prometheus/ name: prometheus-storage-volume volumes: - name: prometheus-config configMap: name: prometheus-config items: - key: prometheus.yml path: prometheus.yml mode: 0644 - name: prometheus-storage-volume hostPath: path: /data/prometheus/ type : Directory
4、prometheus配置文件自动加载 热加载(速度特别慢) 1 2 3 4 5 6 7 8 9 10 11 12 13 14 [root@master1 prometheus] scrape_timeout: 15s [root@master1 prometheus] [root@master1 prometheus] 10.244.166.162 [root@master1 prometheus] [root@master2 ~]
2、可视化UI界面Grafana的安装和配置 1、Grafana介绍 Grafana是一个跨平台的开源的度量分析和可视化工具,可以将采集的数据可视化的展示,并及时通知给告警接收方。它主要有以下六大特点:
1、展示方式:快速灵活的客户端图表,面板插件有许多不同方式的可视化指标和日志,官方库中具有丰富的仪表盘插件,比如热图、折线图、图表等多种展示方式;
2、数据源:Graphite,InfluxDB,OpenTSDB,Prometheus,Elasticsearch,CloudWatch和KairosDB等;
3、通知提醒:以可视方式定义最重要指标的警报规则,Grafana将不断计算并发送通知,在数据达到阈值时通过Slack、PagerDuty等获得通知;
4、混合展示:在同一图表中混合使用不同的数据源,可以基于每个查询指定数据源,甚至自定义数据源;
5、注释:使用来自不同数据源的丰富事件注释图表,将鼠标悬停在事件上会显示完整的事件元数据和标记。
2、安装grafana 1、上传镜像压缩包并解压到node节点 1 2 3 4 5 6 [root@node1 ~] [root@node2 ~] [root@node1 ~] k8s.gcr.io/heapster-grafana-amd64 v5.0.4 [root@node2 ~] k8s.gcr.io/heapster-grafana-amd64 v5.0.4
2、更新yaml配置文件 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 [root@master1 prometheus] apiVersion: apps/v1 kind: Deployment metadata: name: monitoring-grafana namespace: kube-system spec: replicas: 2 selector: matchLabels: task: monitoring k8s-app: grafana template: metadata: labels: task: monitoring k8s-app: grafana spec: containers: - name: grafana image: k8s.gcr.io/heapster-grafana-amd64:v5.0.4 ports: - containerPort: 3000 protocol: TCP volumeMounts: - mountPath: /etc/ssl/certs name: ca-certificates readOnly: true - mountPath: /var name: grafana-storage env: - name: INFLUXDB_HOST value: monitoring-influxdb - name: GF_SERVER_HTTP_PORT value: "3000" - name: GF_AUTH_BASIC_ENABLED value: "false" - name: GF_AUTH_ANONYMOUS_ENABLED value: "true" - name: GF_AUTH_ANONYMOUS_ORG_ROLE value: Admin - name: GF_SERVER_ROOT_URL value: / volumes: - name: ca-certificates hostPath: path: /etc/ssl/certs - name: grafana-storage emptyDir: {} --- apiVersion: v1 kind: Service metadata: labels: kubernetes.io/cluster-service: 'true' kubernetes.io/name: monitoring-grafana name: monitoring-grafana namespace: kube-system spec: ports: - port: 80 targetPort: 3000 selector: k8s-app: grafana type : NodePort
3、grafana界面接入Prometheus数据源 查看grafana前端的service 1 2 [root@master1 prometheus] monitoring-grafana NodePort 10.10.78.198 <none> 80:32361/TCP 12m
登录grafana,在浏览器访问192.168.100.21:32361
配置grafana界面(点击Create your first data source)
导入监控模板 1 https://grafana.com/dashboards?dataSource=prometheus&search=kubernetes
可直接导入node_exporter.json监控模板,这个可以把node节点指标显示出来
node_exporter.json在课件里
可直接导入docker_rev1.json,显示容器资源指标的,docker_rev1.json在课件里
导入docker_rev1.json监控模板,步骤和上面导入node_exporter.json步骤一样,导入之后显示如下:
3、安装kube-state-metrics组件 1、kube-state-metrics简介 kube-state-metrics通过监听API Server生成有关资源对象的状态指标,比如Deployment、Node、Pod,需要注意的是kube-state-metrics只是简单的提供一个metrics数据,并不会存储这些指标数据,所以我们可以使用Prometheus来抓取这些数据然后存储,主要关注的是业务相关的一些元数据,比如Deployment、Pod、副本状态等;调度了多少个replicas?现在可用的有几个?多少个Pod是running/stopped/terminated状态?Pod重启了多少次?我有多少job在运行中。
2、创建sa,并对sa进行授权 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 [root@master1 prometheus] --- apiVersion: v1 kind: ServiceAccount metadata: name: kube-state-metrics namespace: kube-system --- apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRole metadata: name: kube-state-metrics rules: - apiGroups: ["" ] resources: ["nodes" , "pods" , "services" , "resourcequotas" , "replicationcontrollers" , "limitranges" , "persistentvolumeclaims" , "persistentvolumes" , "namespaces" , "endpoints" ] verbs: ["list" , "watch" ] - apiGroups: ["extensions" ] resources: ["daemonsets" , "deployments" , "replicasets" ] verbs: ["list" , "watch" ] - apiGroups: ["apps" ] resources: ["statefulsets" ] verbs: ["list" , "watch" ] - apiGroups: ["batch" ] resources: ["cronjobs" , "jobs" ] verbs: ["list" , "watch" ] - apiGroups: ["autoscaling" ] resources: ["horizontalpodautoscalers" ] verbs: ["list" , "watch" ] --- apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRoleBinding metadata: name: kube-state-metrics roleRef: apiGroup: rbac.authorization.k8s.io kind: ClusterRole name: kube-state-metrics subjects: - kind: ServiceAccount name: kube-state-metrics namespace: kube-system [root@master1 prometheus] serviceaccount/kube-state-metrics created clusterrole.rbac.authorization.k8s.io/kube-state-metrics created clusterrolebinding.rbac.authorization.k8s.io/kube-state-metrics created
3、上传镜像到node节点 1 2 [root@node1 ~] [root@node2 ~]
4、部署pod与service 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 [root@master1 prometheus] apiVersion: apps/v1 kind: Deployment metadata: name: kube-state-metrics namespace: kube-system spec: replicas: 1 selector: matchLabels: app: kube-state-metrics template: metadata: labels: app: kube-state-metrics spec: serviceAccountName: kube-state-metrics containers: - name: kube-state-metrics image: quay.io/coreos/kube-state-metrics:v1.9.0 ports: - containerPort: 8080 [root@master1 prometheus] apiVersion: v1 kind: Service metadata: annotations: prometheus.io/scrape: 'true' name: kube-state-metrics namespace: kube-system labels: app: kube-state-metrics spec: ports: - name: kube-state-metrics port: 8080 protocol: TCP selector: app: kube-state-metrics
3、基于Alertmanager发送报警到多个接收方 1、配置Alertmanager发送报警到qq邮箱 报警: 指prometheus将监测到的异常事件发送给alertmanager
通知: alertmanager将报警信息发送到邮件、微信、钉钉等
1、创建alertmanager配置文件 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 [root@master1 prometheus] kind: ConfigMap apiVersion: v1 metadata: name: alertmanager namespace: monitor-sa data: alertmanager.yml: |- global: resolve_timeout: 1m smtp_smarthost: 'smtp.163.com:25' smtp_from: '[email protected] ' smtp_auth_username: '13164377870' smtp_auth_password: 'DJDDZXJFFTSLRJYG' smtp_require_tls: false route: group_by: [alertname] group_wait: 10s group_interval: 10s repeat_interval: 10m receiver: default-receiver receivers: - name: 'default-receiver' email_configs: - to: '[email protected] ' send_resolved: true [root@master1 prometheus]
2、Prometheus一条报警的触发流程 \1. Prometheus Server监控目标主机上暴露的http接口(这里假设接口A),通过Promethes配置的’scrape_interval’定义的时间间隔,定期采集目标主机上监控数据。 \2. 当接口A不可用的时候,Server端会持续的尝试从接口中取数据,直到”scrape_timeout”时间后停止尝试。这时候把接口的状态变为“DOWN”。 \3. Prometheus同时根据配置的”evaluation_interval”的时间间隔,定期(默认1min)的对Alert Rule进行评估;当到达评估周期的时候,发现接口A为DOWN,即UP=0为真,激活Alert,进入“PENDING”状态,并记录当前active的时间; \4. 当下一个alert rule的评估周期到来的时候,发现UP=0继续为真,然后判断警报Active的时间是否已经超出rule里的‘for’ 持续时间,如果未超出,则进入下一个评估周期;如果时间超出,则alert的状态变为“FIRING”;同时调用Alertmanager接口,发送相关报警数据。 \5. AlertManager收到报警数据后,会将警报信息进行分组,然后根据alertmanager配置的“group_wait”时间先进行等待。等wait时间过后再发送报警信息。 \6. 属于同一个Alert Group的警报,在等待的过程中可能进入新的alert,如果之前的报警已经成功发出,那么间隔“group_interval”的时间间隔后再重新发送报警信息。比如配置的是邮件报警,那么同属一个group的报警信息会汇总在一个邮件里进行发送。 \7. 如果Alert Group里的警报一直没发生变化并且已经成功发送,等待‘repeat_interval’时间间隔之后再重复发送相同的报警邮件;如果之前的警报没有成功发送,则相当于触发第6条条件,则需要等待group_interval时间间隔后重复发送。
同时最后至于警报信息具体发给谁,满足什么样的条件下指定警报接收人,设置不同报警发送频率,这里有alertmanager的route路由规则进行配置。
3、创建prometheus和告警规则配置文件 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 [root@master1 prometheus] configmap "prometheus-config" deleted [root@master1 prometheus] [root@master1 prometheus] 540 [root@master1 prometheus] configmap/prometheus-config created [root@master1 prometheus] secret/etcd-certs created [root@master1 prometheus] --- apiVersion: apps/v1 kind: Deployment metadata: name: prometheus-server namespace: monitor-sa labels: app: prometheus spec: replicas: 1 selector: matchLabels: app: prometheus component: server template: metadata: labels: app: prometheus component: server annotations: prometheus.io/scrape: 'false' spec: nodeName: node1 serviceAccountName: monitor containers: - name: prometheus image: prom/prometheus:v2.2.1 imagePullPolicy: IfNotPresent command : - "/bin/prometheus" args: - "--config.file=/etc/prometheus/prometheus.yml" - "--storage.tsdb.path=/prometheus" - "--storage.tsdb.retention=24h" - "--web.enable-lifecycle" ports: - containerPort: 9090 protocol: TCP volumeMounts: - mountPath: /etc/prometheus name: prometheus-config - mountPath: /prometheus/ name: prometheus-storage-volume - name: k8s-certs mountPath: /var/run/secrets/kubernetes.io/k8s-certs/etcd/ - name: localtime mountPath: /etc/localtime - name: alertmanager image: prom/alertmanager:v0.14.0 imagePullPolicy: IfNotPresent args: - "--config.file=/etc/alertmanager/alertmanager.yml" - "--log.level=debug" ports: - containerPort: 9093 protocol: TCP name: alertmanager volumeMounts: - name: alertmanager-config mountPath: /etc/alertmanager - name: alertmanager-storage mountPath: /alertmanager - name: localtime mountPath: /etc/localtime volumes: - name: prometheus-config configMap: name: prometheus-config - name: prometheus-storage-volume hostPath: path: /data/prometheus type : Directory - name: k8s-certs secret: secretName: etcd-certs - name: alertmanager-config configMap: name: alertmanager - name: alertmanager-storage hostPath: path: /data/alertmanager type : DirectoryOrCreate - name: localtime hostPath: path: /usr/share/zoneinfo/Asia/Shanghai [root@master1 prometheus] [root@master1 prometheus] prometheus-server-57cc7947d8-c8d8g 2/2 Running 0 4m51s [root@master1 prometheus] --- apiVersion: v1 kind: Service metadata: labels: name: prometheus kubernetes.io/cluster-service: 'true' name: alertmanager namespace: monitor-sa spec: ports: - name: alertmanager nodePort: 30066 port: 9093 protocol: TCP targetPort: 9093 selector: app: prometheus sessionAffinity: None type : NodePort [root@master1 prometheus] service/alertmanager created
4、修改配置文件(在第三步之前进行操作,安装集群的时候就进行修改) /etc/kubernetes/manifests/kube-scheduler.yaml
1 2 3 4 5 修改如下内容: 把--bind -address =127.0 .0.1 变成--bind -address =192.168 .100.11 把httpGet:字段下的hosts由127.0 .0.1 变成192.168 .100.11 把—port=0 删除
/etc/kubernetes/manifests/kube-controller-manager.yaml
1 2 3 把--bind -address =127.0 .0.1 变成--bind -address =192.168 .100.11 把httpGet:字段下的hosts由127.0 .0.1 变成192.168 .100.11 把—port=0 删除
在所有节点上执行重新启动kubelet服务
1 2 3 4 5 6 7 8 9 10 systemctl restart kubelet [root@master1 ~] Warning: v1 ComponentStatus is deprecated in v1.19+ NAME STATUS MESSAGE ERROR controller-manager Healthy ok scheduler Healthy ok etcd-0 Healthy {"health" :"true" }
5、修改kube-proxy的监听端口
将其中的“metricsBindAddress ”改成“**metricsBindAddress:”0.0.0.0:10249”**”,然后保存并退出
重新启动kube-proxy这个pod
全部的target运行正常
2、配置Alertmanager发送报警到钉钉群组 1、创建钉钉机器人 打开电脑版钉钉,创建一个群,创建自定义机器人,按如下步骤创建
1 https://open.dingtalk.com/document/group/custom-robot-access
我创建的机器人如下:
群设置–>智能群助手–>添加机器人–>自定义–>添加
1 webhook:https://oapi.dingtalk.com/robot/send?access_token=3e1762172067b61bd276bfa0cd32ab98b2e4ad1996b3394e0e472adfad338aa8
2、解压prometheus-webhook-dingtalk-0.3.0.linux-amd64二进制文件
3、启动钉钉报警插件 1 2 3 4 5 6 7 8 9 nohup /usr/local /bin/prometheus-webhook-dingtalk \ --web.listen-address="0.0.0.0:8060" \ --ding.profile="cluster1=https://oapi.dingtalk.com/robot/send? access_token=3e1762172067b61bd276bfa0cd32ab98b2e4ad1996b3394e0e472adfad338aa8" & [root@master1 system] tcp6 0 0 :::8060 :::* LISTEN 7369/prometheus-web
4、备份原来的prometheus-cm.yml文件 1 [root@master1 prometheus]
5、修改配置文件prometheus-cm.yml并应用配置文件 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 [root@master1 prometheus] kind: ConfigMap apiVersion: v1 metadata: name: alertmanager namespace: monitor-sa data: alertmanager.yml: |- global: resolve_timeout: 1m smtp_smarthost: 'smtp.163.com:25' smtp_from: '[email protected] ' smtp_auth_username: '13164377870' smtp_auth_password: 'DJDDZXJFFTSLRJYG' smtp_require_tls: false route: group_by: [alertname] group_wait: 10s group_interval: 10s repeat_interval: 10m receiver: cluster1 receivers: - name: 'cluster1' webhook_configs: - url: 'http://192.168.106.11:8060/dingtalk/cluster1/send' send_resolved: true [root@master1 prometheus] configmap/alertmanager configured [root@master1 prometheus] deployment.apps "prometheus-server" deleted [root@master1 prometheus] deployment.apps/prometheus-server created
3、配置Alermanager发送报警到微信 4、Prometheus PromQL语法 PromQL(Prometheus Query Language)是 Prometheus 自己开发的表达式语言,语言表现力很丰富,内置函数也很多。使用它可以对时序数据进行筛选和聚合。
1、数据类型 PromQL 表达式计算出来的值有以下几种类型:
瞬间向量(Instant vector) :一组时序,每个时序只有一个采样值
区间向量(Range vector) :一组时序,每个时序包含一段时间内的多个采样值
标量数据(String) :一个字符串,暂时未使用
1、瞬时向量选择器 瞬时向量选择器用来选择一组时序在某个采样点的采样值。 最简单的情况就是指定一个度量指标,选择出所有属于该度量指标的时序的当前采样值。比如下面的表达式:
apiserver_request_total
可以通过在后面添加用大括号包围起来的一组标签键值对来对时序进行过滤。比如下面的表达式筛选出了 job 为 kubernetes-apiservers,并且 resource为 pod的时序:
apiserver_request_total{job=”kubernetes-apiserver”,resource=”pods”}
匹配标签值时可以是等于,也可以使用正则表达式。总共有下面几种匹配操作符:
=:完全相等
!=: 不相等
=~: 正则表达式匹配
!~: 正则表达式不匹配
下面的表达式筛选出了container是kube-scheduler或kube-proxy或kube-apiserver的时序数据
container_processes{container=~”kube-scheduler|kube-proxy|kube-apiserver”}
2、区间向量选择器 区间向量选择器类似于瞬时向量选择器,不同的是它选择的是过去一段时间的采样值。可以通过在瞬时向量选择器后面添加包含在 [] 里的时长来得到区间向量选择器。比如下面的表达式选出了所有度量指标为apiserver_request_total且resource是pod的时序在过去1 分钟的采样值。
这个不支持Graph,需要选择Console,才会看到采集的数据
说明:时长的单位可以是下面几种之一:
s:seconds
m:minutes
h:hours
d:days
w:weeks
y:years
3、偏移向量选择器 前面介绍的选择器默认都是以当前时间为基准时间,偏移修饰器用来调整基准时间,使其往前偏移一段时间。偏移修饰器紧跟在选择器后面,使用 offset 来指定要偏移的量。比如下面的表达式选择度量名称为apiserver_request_total的所有时序在 5 分钟前的采样值
apiserver_request_total{job=”kubernetes-apiserver”,resource=”pods”} offset 5m
下面的表达式选择apiserver_request_total 度量指标在 1 周前的这个时间点过去 5 分钟的采样值。
apiserver_request_total{job=”kubernetes-apiserver”,resource=”pods”} [5m] offset 1w
4、聚合操作符号 PromQL 的聚合操作符用来将向量里的元素聚合得更少。总共有下面这些聚合操作符:
sum:求和
min:最小值
max:最大值
avg:平均值
stddev:标准差
stdvar:方差
count:元素个数
count_values:等于某值的元素个数
bottomk:最小的 k 个元素
topk:最大的 k 个元素
quantile:分位数
如:
计算master1节点所有容器总计内存
sum(container_memory_usage_bytes{instance=~”master1”})/1024/1024/1024
计算master1节点最近1m所有容器cpu使用率
sum (rate (container_cpu_usage_seconds_total{instance=“master1”}[1m])) / sum (machine_cpu_cores{ instance =“master1”}) * 100
计算最近1m所有容器cpu使用率
sum (rate (container_cpu_usage_seconds_total{id!=”/“}[1m])) by (id)
#把id会打印出来
5、函数 Prometheus 内置了一些函数来辅助计算,下面介绍一些典型的。
abs():绝对值
sqrt():平方根
exp():指数计算
ln():自然对数
ceil():向上取整
floor():向下取整
round():四舍五入取整
delta():计算区间向量里每一个时序第一个和最后一个的差值
sort():排序
5、Prometheus监控扩展 1、prometheus采集tomcat日志 1、下载war包和jar包 1 https://note.youdao.com/ynoteshare/index.html?id=0ddfc17eaf7bac94ad4497d7f5356213&type =note
2、制作tomcat镜像 1 2 3 4 5 6 7 8 9 10 11 [root@master1 tomcat] FROM tomcat ADD metrics.war /usr/local /tomcat/webapps/ ADD simpleclient-0.8.0.jar /usr/local /tomcat/lib/ ADD simpleclient_common-0.8.0.jar /usr/local /tomcat/lib/ ADD simpleclient_hotspot-0.8.0.jar /usr/local /tomcat/lib/ ADD simpleclient_servlet-0.8.0.jar /usr/local /tomcat/lib/ ADD tomcat_exporter_client-0.0.12.jar /usr/local /tomcat/lib/ [root@master1 tomcat]
3、查看tomcat镜像 1 2 [root@master1 tomcat] zy/tomcat_prometheus v1 f361fa5d5181 About a minute ago 680MB
4、登录dockerhub仓库 1 2 3 4 5 6 7 [root@master1 tomcat] Authenticating with existing credentials... WARNING! Your password will be stored unencrypted in /root/.docker/config.json. Configure a credential helper to remove this warning. See https://docs.docker.com/engine/reference/commandline/login/ Login Succeeded
5、上传镜像到dockerhub仓库 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 [root@master1 tomcat] The push refers to repository [docker.io/vorabend/tomcat_prometheus] a3c5dda2d577: Pushed c6c3536d5155: Pushed 5d2adf33b723: Pushed 8af756fc9dff: Pushed efc436679e04: Pushed 092bc7cd79cd: Pushed 3e2ed6847c7a: Mounted from library/tomcat bd2befca2f7e: Mounted from library/tomcat 59c516e5b6fa: Mounted from library/tomcat 3bb5258f46d2: Mounted from library/tomcat 832e177bb500: Mounted from library/tomcat f9e18e59a565: Mounted from library/tomcat 26a504e63be4: Mounted from library/tomcat 8bf42db0de72: Mounted from library/tomcat 31892cc314cb: Mounted from library/tomcat 11936051f93b: Mounted from library/tomcat v1: digest: sha256:e8c2d36966c2e8132ceed722900eb450e15ec806a8d3a99f6b5cf033186b90ba size: 3673
6、在k8s的node节点拉取镜像 1 2 3 [root@node1 ~] [root@node2 ~] [root@node3 ~]
7、写tomcat_deploy.yml文件,创建pod 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 [root@master1 tomcat] apiVersion: apps/v1 kind: Deployment metadata: name: tomcat-deployment namespace: default spec: selector: matchLabels: app: tomcat replicas: 2 template: metadata: labels: app: tomcat annotations: prometheus.io/scrape: 'true' spec: containers: - name: tomcat image: vorabend/tomcat_prometheus:v1 imagePullPolicy: IfNotPresent ports: - containerPort: 8080 securityContext: privileged: true [root@master1 tomcat] deployment.apps/tomcat-deployment created
8、创建service
port: 8080 , Service暴露出来的Port
nodePort: 31360, Node 暴露出来的Port
targetPort: 80, Container上暴露的Port
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 [root@master1 tomcat] apiVersion: v1 kind: Service metadata: name: tomcat-service spec: selector: app: tomcat ports: - nodePort: 31360 port: 80 protocol: TCP targetPort: 8080 type : NodePort [root@master1 tomcat]
9、开启prometheus的服务自动发现 1 2 [root@master1 tomcat] prometheus.io/scrape: "true"
2、prometheus监控redis 1、redis_deploy.yml redis 这个 Pod 中包含了两个容器,一个就是 redis 本身的主应用,另外一个容器就是 redis_exporter
由于Redis服务的metrics接口在redis-exporter 9121上,所以我们添加了prometheus.io/port=9121这样的annotation,在prometheus就会自动发现redis了
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 [root@master1 redis] apiVersion: apps/v1 kind: Deployment metadata: name: redis namespace: kube-system spec: replicas: 1 selector: matchLabels: app: redis template: metadata: labels: app: redis spec: containers: - name: redis image: redis:4 resources: requests: cpu: 100m memory: 100Mi ports: - containerPort: 6379 - name: redis-exporter image: oliver006/redis_exporter:latest resources: requests: cpu: 100m memory: 100Mi ports: - containerPort: 9121 --- apiVersion: v1 kind: Service metadata: name: redis namespace: kube-system annotations: prometheus.io/scrape: "true" prometheus.io/port: "9121" spec: selector: app: redis ports: - name: redis port: 6379 targetPort: 6379 - name: prom port: 9121 targetPort: 9121 [root@master1 redis]
2、测试监控是否正常 1 2 3 4 [root@master1 redis] HTTP/1.1 200 OK Content-Type: text/plain; version=0.0.4; charset=utf-8 Date: Mon, 10 Oct 2022 14:49:29 GMT
3、Prometheus监控mysql 1、在master1上安装mariadb-server 1 2 3 4 [root@master1 ~] [root@master1 ~]
2、解压mysqld_exporter压缩包 1 2 3 4 5 6 7 8 [root@master1 redis] [root@master1 mysqld_exporter-0.10.0.linux-amd64] [root@master1 ~]
3、登录mysql为mysql_exporter设置账号与权限 1 2 3 4 MariaDB [(none)]> CREATE USER 'mysql_exporter' @'localhost' IDENTIFIED BY 'password' ; MariaDB [(none)]> GRANT PROCESS, REPLICATION CLIENT, SELECT ON *.* TO 'mysql_exporter' @'localhost' ;
4、创建mysql配置文件,运行时可免密码连接数据库 1 2 3 4 [root@master1 mysqld_exporter-0.10.0.linux-amd64] [client] user=mysql_exporter password=password
5、启动mysql_exporter客户端 mysqld_exporter的监听端口是9104
1 2 3 4 5 [root@master1 mysqld_exporter-0.10.0.linux-amd64] [root@master1 mysqld_exporter-0.10.0.linux-amd64] tcp6 0 0 :::9104 :::* LISTEN 18186/./mysqld_expo
6、修改prometheus-alertmanager-cfg.yml 1 2 3 4 5 6 7 8 [root@master1 prometheus] - job_name: 'msyql' static_configs: - targets: ['192.168.106.11:9104' ] [root@master1 prometheus]
7、应用配置文件 1 2 3 4 [root@master1 prometheus] deployment.apps "prometheus-server" deleted [root@master1 prometheus] deployment.apps/prometheus-server created
4、prometheus监控nginx 1、配置nginx-module-vts-master模块 1 2 3 4 [root@node1 prometheus] [root@node1 prometheus]
2、在node1安装nginx 1 2 3 4 [root@node1 prometheus] [root@node1 prometheus] [root@node1 nginx-1.15.7] [root@node1 nginx-1.15.7]
3、修改配置文件 1 2 3 4 5 6 7 8 9 10 [root@node1 nginx-1.15.7] location /status { vhost_traffic_status_display; vhost_traffic_status_display_format html; } vhost_traffic_status_zone;
4、测试配置文件是否正确 1 2 3 [root@node1 nginx-1.15.7] nginx: the configuration file /usr/local /nginx/conf/nginx.conf syntax is ok nginx: configuration file /usr/local /nginx/conf/nginx.conf test is successful
5、启动nginx 1 [root@node1 nginx-1.15.7]
6、访问查看监控数据
7、在master1上安装nginx-vts-exporter 1 2 3 4 5 [root@master1 nginx] [root@master1 nginx] [root@master1 nginx] [root@master1 nginx] [root@master1 bin]
nginx-vts-exporter的监听端口是9913
1 2 [root@master1 ~] tcp6 0 0 :::9913 :::* LISTEN 3873/./nginx-vts-ex
8、修改prometheus-cfg.yaml文件 1 2 3 4 5 - job_name: 'nginx' scrape_interval: 5s static_configs: - targets: ['192.168.106.11:9913' ]
9、应用配置文件 1 2 3 [root@master1 prometheus] [root@master1 prometheus] [root@master1 prometheus]
5、prometheus监控mongodb 1 https://note.youdao.com/ynoteshare/index.html?id=39 b54acb1fbc0199f966115ce9523bb6&type =note
1、下载mongodb和mongodb_exporter镜像 1 2 [root@master1 ~] [root@master1 ~]
2、启动mongodb 1 2 3 [root@master1 ~] [root@master1 ~] [root@master1 ~]
3、登录mongo容器,设置密码 1 2 3 4 5 [root@master1 ~] root@143020f29095:/ > use admin > db.createUser({ user: 'admin' , pwd : 'admin' , roles: [ { role: "userAdminAnyDatabase" , db: "admin" } ] }) > exit
4、启动mongo_exporter 1 2 [root@master1 prometheus] 2ca7384506204d23b3880a9e65e69bd0df9df6c52d4f54d62ddae667ef3d0a21
5、查看mongo_exporter是否启动成功 1 2 [root@master1 prometheus] 2ca738450620 percona/mongodb_exporter:0.34.0 "/mongodb_exporter -…" About a minute ago Up About a minute 0.0.0.0:30056->9216/tcp, :::30056->9216/tcp mongodb_exporter
6、修改prometheus-cfg.yaml文件 1 2 3 4 5 [root@master1 prometheus] - job_name: 'mongodb' scrape_interval: 5s static_configs: - targets: ['192.168.106.11:30056' ]
7、应用配置文件 1 2 3 [root@master1 prometheus] [root@master1 prometheus] [root@master1 prometheus]
6、pushgateway 1、pushgateway简介 Pushgateway是prometheus的一个组件,prometheus server默认是通过exporter主动获取数据(默认采取pull拉取数据),pushgateway则是通过被动方式推送数据到prometheus server,用户可以写一些自定义的监控脚本把需要监控的数据发送给pushgateway, 然后pushgateway再把数据发送给Prometheus server
2、pushgateway的优点 Prometheus 默认采用定时pull 模式拉取targets数据,但是如果不在一个子网或者防火墙,prometheus就拉取不到targets数据,所以可以采用各个target往pushgateway上push数据,然后prometheus去pushgateway上定时pull数据
在监控业务数据的时候,需要将不同数据汇总, 汇总之后的数据可以由pushgateway统一收集,然后由 Prometheus 统一拉取。
3、pushgateway的缺点 Prometheus拉取状态只针对 pushgateway, 不能对每个节点都有效;
Pushgateway出现问题,整个采集到的数据都会出现问题
监控下线,prometheus还会拉取到旧的监控数据,需要手动清理 pushgateway不要的数据。
4、在node1节点上安装pushgateway 1、拉取镜像
2、运行pushgateway容器 1 2 [root@node1 ~] dcc6ce136668031f422f045a051c9a871dbcf25dfa5514fc4f60810f47632df1
3、测试浏览器访问node1节点的9091端口
4、修改prometheus-alertmanager-cfg.yaml配置文件 1 2 3 4 5 6 [root@master1 prometheus] - job_name: 'pushgateway' scrape_interval: 5s static_configs: - targets: ['192.168.106.21:9091' ] honor labels: true
5、应用配置文件 1 2 3 [root@master1 prometheus] [root@master1 prometheus] [root@master1 prometheus]
6、推送指定数据格式到pushgateway 1 [root@master1 prometheus]
注:–data-binary 表示发送二进制数据,注意:它是使用POST方式发送的!
7、测试推送复杂数据 1 2 3 4 5 6 cat << EOF | curl --data-binary @- http://192.168.106.21:9091/metrics/job/test_job/instance/test_instance #TYPE node_memory_usage gauge node_memory_usage 36 # TYPE memory_total gauge node_memory_total 36000 EOF
8、删除某个组下某个实例的所有数据
9、删除某个组下的所有实例
10、把数据上报到pushgateway 在被监控服务所在的机器配置数据上报,把192.168.106.21这个节点的内存数据上报到pushgateway,下面的步骤需要在192.168.106.21上进行操作
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 [root@node1 ~] node_memory_usages=$(free -m | grep -i mem | awk {'print $3/$2*100' }) job_name="memory" instance_name=$(hostname) cat <<EOF | curl --data-binary @- http://192.168.106.21:9091/metrics/job/$job_name/instance/$instance_name #TYPE node_memory_usages gauge node_memory_usages $node_memory_usages EOF [root@node1 ~] [root@node1 ~] [root@node1 ~] */1 * * * * /usr/bin/bash /root/pushgateway.sh
注意:从上面配置可以看到,我们上传到pushgateway中的数据有job也有instance,而prometheus配置pushgateway这个job_name中也有job和instance,这个job和instance是指pushgateway实例本身,添加 honor_labels: true 参数, 可以避免promethues的targets列表中的job_name是pushgateway的 job 、instance 和上报到pushgateway数据的job和instance冲突。