一.服务发现
1.简介
当我们使用各类exporter分别对系统、数据库和HTTP服务进行监控指标采集,对于所有监控指标对应的Target的运行状态和资源使用情况,都是用Prometheus的静态配置功能 static_configs 来手动添加主机IP和端口,然后重载服务让Prometheus发现。
对于一组比较少的服务器的测试环境中,这种手动方式添加配置信息是最简单的方法。但是实际生产环境中,对于成百上千的节点组成的大型集群又或者Kubernetes这样的大型集群,很明显,手动方式捉襟见肘了。为此,Prometheus提前已经设计了一套服务发现功能。
Prometheus 服务发现能够自动检测分类,并且能够识别新节点和变更节点。也就是说,可以在容器或者云平台中,自动发现并监控节点或更新节点,动态的进行数据采集和处理。
2.常见的服务发现
kubernetes_sd_config: k8s的服务发现,让prometheus动态发现k8s中被监控的目标
static_configs: 静态服务发现,基于prometheus配置文件指定的监控目标
dns_sd_configs: 基于dns服务发现监控目标
consul_sd_configs: consul服务发现,基于consul服务动态发现监控目标
file_sd_configs: 基于指定的文件实现服务发现,基于指定的文件发现监控目标
3.标签重写
3.1简介
prometheus的relabeling(标签重写)可以在抓取到目标实例之前把目标实例的元数据标签动态修改,动态添加或覆盖.
Prometheus在加载Target成功之后,在Taret实例中,都包含一些Metadata标签信息,默认标签有:
标签 | 含义 |
---|
address | 以:格式显示targets的地址 |
scheme | 采用的目标服务地址的Scheme形式,HTTP或者HTTPS |
metrics_path | 采用的目标服务的访问路径 |
修改标签的时机:
relabel_configs: 在抓取数据之前,可以使用relabel_configs添加一些标签,也可以值采集特定目标或过滤目标
metric_relabel_configs: 在抓取数据之后,可以使用metric_relabel_configs做最后的重新标记和过滤
- job_name: 'kubernetes-node-cadvisor' #job名称
kubernetes_sd_configs: #基于kubernetes_sd_configs实现服务发现
- role: endpoint # 发现endpoint
scheme: https # 当前job使用的发现协议
tls_config: # 证书配置
ca_file: /var/run/secrets/kubernetes.io/serviceaccount/ca.crt # 容器里的证书路径
bearer_token_file: /var/run/secrets/kubernetes.io/serviceaccount/token # 容器里的token路径
relabel_configs: # 抓取前重写修改标签配置
- source_labels: [__meta_kubernetes_namespace, __meta_kubernetes_service_name, __meta_kubernetes_endpoint_port_name] # 源标签
- action: keep # action定义了relabel的具体动作.action支持多种
regex: default;kubernetes;https # 通过正则匹配条件
#在default命名空间service名是kubernetes,并且使用https协议访问一旦条件成立,只保留匹配成功的数据(其实就是api-server)
3.2label
source_labels: 源标签,没有经过relabel处理之前的名字
target_labels: 通过action处理之后的新标签名字
regex: 正则表达式,匹配源标签
replacement: 通过分组替换后标签(target_label)对应的值
3.3action
标签 | 含义 |
---|
replace | 替换标签值,根据regex正则匹配到源标签的值,使用replacement来引用表达式匹配的分组 |
keep | 满足regex正则条件的实例进行采集,把source_labels中没有匹配到regex正则内容的target实例丢弃,只采集匹配成功的实例 |
drop | 满足regex正则匹配条件的不采集,把source_labels中匹配到regex正则内容的Target丢弃,只采集没有匹配到的实例 |
Hashmod | 使用Hashmod计算source_labels的Hash值并进行对比,基于自定义的模数取模,以实现对目标进行分类,重新赋值等功能 |
labelmap | 匹配regex所有标签名称,然后赋值匹配标签的值进行分组,通过replacement分组引用替代 |
labelkeep | 匹配regex所有标签名称,其他不匹配的标签都将从标签集中删除 |
labeldrop | 匹配regex所有标签名称,其他匹配的标签都将从标签集中删除 |
3.4监控api-server
[root@master01 ~]# kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes ClusterIP 10.10.0.1 <none> 443/TCP 1d
[root@master01 ~]# kubectl get ep
NAME ENDPOINTS AGE
kubernetes 192.168.10.10:6443,192.168.10.11:6443,192.168.10.12:6443 1d
- 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
3.5监控kube-dns
创建kube-dns时需要再metadata中加入
annotations:
prometheus.io/port: "9153"
prometheus.io/scrape: "true"
这样就能在kube-dns的注解中看到prometheus.io/port: 9153,prometheus.io/scrape: true
才能使得prometheus发现kube-dns
[root@master01 ~]# kubectl describe svc kube-dns -n kube-system
Name: kube-dns
Namespace: kube-system
Labels: addonmanager.kubernetes.io/mode=Reconcile
k8s-app=kube-dns
kubernetes.io/cluster-service=true
kubernetes.io/name=CoreDNS
Annotations: prometheus.io/port: 9153
prometheus.io/scrape: true
通过configmap进行匹配
匹配任意namespace的endpoint
- job_name: 'kubernetes-service-endpoints'
kubernetes_sd_configs:
- role: endpoints # 类型是endpoints
relabel_configs:
- source_labels: [__meta_kubernetes_service_annotation_prometheus_io_scrape] # 匹配prometheus.io/scrape值
action: keep
regex: true #如果是true则保留,继续往下匹配,否则就不进行保存
- source_labels: [__meta_kubernetes_service_annotation_prometheus_io_scheme]
action: replace
target_label: __scheme__
regex: (https?) # 匹配http和https
- source_labels: [__meta_kubernetes_service_annotation_prometheus_io_path]
action: replace
target_label: __metrics_path__
regex: (.+) # 至少1个字符任意长度
- source_labels: [__address__, __meta_kubernetes_service_annotation_prometheus_io_port]
action: replace
target_label: __address__
regex: ([^:]+)(?::\d+)?;(\d+)
replacement: $1:$2 # 将地址和端口两个值合并成 ip:port格式的__address__
- 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
3.6cadvisor发现
- job_name: 'kubernetes-node-cadvisor' # job名称
kubernetes_sd_configs: # 基于k8s发现
- 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_(.+) #匹配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 # $1是node_name
4.服务发现模式
4.1node
node角色可以发现集群中每个node节点的地址端口,默认为Kubelet的HTTP端口。目标地址默认为Kubernetes节点对象的第一个现有地址,地址类型顺序为NodeInternalIP、NodeExternalIP、NodeLegacyHostIP和NodeHostName。
作用:监控K8S的node节点的服务器相关的指标数据。
标签:
__meta_kubernetes_node_name: node节点的名称
__meta_kubernetes_node_label_<labelname>: k8s中node节点的标签.<labelname>代表标签名称
__meta_kubernetes_node_labelpresent_<labelname>: 标签存在则为true.<labelname>代表标签名称
__meta_kubernetes_node_annotation_<annotationname>: k8s中node节点的注解.<annotationname>代表注解名称
__meta_kubernetes_node_annotationpresent_<annotationname>: 注解存在则为true.<annotationname>代表注解名称
__meta_kubernetes_node_address_<address_type>: 不同类型的node节点地址,例如:
_meta_kubernetes_node_address_Hostname="k8s-node1"
_meta_kubernetes_node_address_InternalIP="10.0.0.1"
instance: 从apiserver获取到的节点名称
4.2service
service角色可以发现每个service的ip和port,将其作为target。这对于黑盒监控(blackbox)很有用。
即:一个Service访问到哪个pod,就把哪个pod的数据传上来。使用的场景很少。只是看Service对应业务是否健康的时候可以使用。
标签:
__meta_kubernetes_namespace: service所在的命名空间
__meta_kubernetes_service_annotation_<annotationname>: k8s中service的注解
__meta_kubernetes_service_annotationpresent_<annotationname>: 注解存在则为true
__meta_kubernetes_service_cluster_ip: k8s中service的clusterIP
__meta_kubernetes_service_external_name: k8s中service的external_name
__meta_kubernetes_service_label_<labelname>: k8s中service的标签
__meta_kubernetes_service_labelpresent_<labelname>: 标签存在则为true
__meta_kubernetes_service_name: k8s中service的名称
__meta_kubernetes_service_port_name: k8s中service的端口
__meta_kubernetes_service_port_protocol: k8s中service的端口协议
__meta_kubernetes_service_type: k8s中service的类型
4.3pod
pod角色可以发现所有pod并将其中的pod ip作为target。如果有多个端口或者多个容器,将生成多个target
标签:
__meta_kubernetes_namespace: pod所在的命名空间
__meta_kubernetes_pod_name: pod的名称
__meta_kubernetes_pod_ip: pod的ip
__meta_kubernetes_pod_label_<labelname>: pod的标签
__meta_kubernetes_pod_labelpresent_<labelname>: 标签存在则为true
__meta_kubernetes_pod_annotation_<annotationname>: pod的注解
__meta_kubernetes_pod_annotationpresent_<annotationname>: 注解存在则为true
__meta_kubernetes_pod_container_init: 如果容器是InitContainer,则为true
__meta_kubernetes_pod_container_name: 容器的名称
__meta_kubernetes_pod_container_port_name: 容器的端口名称
__meta_kubernetes_pod_container_port_number: 容器的端口号
__meta_kubernetes_pod_container_port_protocol: 容器的端口协议
__meta_kubernetes_pod_ready: pod的就绪状态,true或false。
__meta_kubernetes_pod_phase: pod的生命周期状态.Pending, Running, Succeeded, Failed or Unknown
__meta_kubernetes_pod_node_name: pod所在node节点名称
__meta_kubernetes_pod_host_ip: pod所在node节点ip
__meta_kubernetes_pod_uid: pod的uid
__meta_kubernetes_pod_controller_kind: pod控制器的类型ReplicaSet ,DaemonSet,Job,StatefulSet...
__meta_kubernetes_pod_controller_name: pod控制器的名称
4.4endpoints
endpoints角色可以从ep(endpoints)列表中发现所有targets。
标签:
__meta_kubernetes_namespace : ep对象所在的命名空间
__meta_kubernetes_endpoints_name : ep的名称
直接从ep对象的列表中获取的所有target,下面的标签将会被附加上
__meta_kubernetes_endpoint_hostname: ep的主机名
__meta_kubernetes_endpoint_node_name: ep的node节点名
__meta_kubernetes_endpoint_ready: ep的就绪状态,true或false。
__meta_kubernetes_endpoint_port_name: ep的端口名称
__meta_kubernetes_endpoint_port_protocol: ep的端口协议
__meta_kubernetes_endpoint_address_target_kind: ep对象的目标类型,比如Pod
__meta_kubernetes_endpoint_address_target_name: ep对象的目标名称,比如pod名称
如果ep是属于service的话,则会附加service角色的所有标签
对于ep的后端节点是pod,则会附加pod角色的所有标签(即上边介绍的pod角色可用标签)
比如我么手动创建一个ep,这个ep关联到一个pod,则prometheus的标签中会包含这个pod角色的所有标签
4.5ingress
ingress角色发现ingress的每个路径的target。这通常对黑盒监控很有用。该地址将设置为ingress中指定的host。
标签:
__meta_kubernetes_namespace: ingress所在的命名空间
__meta_kubernetes_ingress_name: ingress的名称
__meta_kubernetes_ingress_label_<labelname>: ingress的标签
__meta_kubernetes_ingress_labelpresent_<labelname>: 标签存在则为true
__meta_kubernetes_ingress_annotation_<annotationname>: ingress的注解
__meta_kubernetes_ingress_annotationpresent_<annotationname>: 注解存在则为true
__meta_kubernetes_ingress_scheme: ingress的协议,如果设置了tls则是https,默认http
__meta_kubernetes_ingress_path: ingress中指定的的路径。默认为/
二.静态服务发现(static_configs)
- job_name: "node"
static_configs:
- targets:
- 192.168.10.10:9100
三.Consul自动发现
1.简介
Consul是分布式k/v数据存储集群,目前常用于服务注册和服务发现
2.consul的添加
curl -X PUT -d '{"id": "zookeeper-1","name": "zookeeper-1","address": "192.168.10.10","port": 9100,"tags": ["zookeeper","node-exporter"],"checks": [{"http": "http://192.168.10.10:9100/","interval": "5s"}]}' http://192.168.10.10:8500/v1/agent/service/register
curl -X PUT -d '{"id": "zookeeper-2","name": "zookeeper-2","address": "192.168.10.11","port": 9100,"tags": ["zookeeper","node-exporter"],"checks": [{"http": "http://192.168.10.11:9100/","interval": "5s"}]}' http://192.168.10.11:8500/v1/agent/service/register
3.consul的删除
curl --request PUT http://192.168.31.121:8500/v1/agent/service/deregister/cadvisor-1
curl --request PUT http://192.168.31.121:8500/v1/agent/service/deregister/zookeeper
四.file的服务发现
1.简介
在Prometheus支持的众多服务发现的实现方式中,基于文件的服务发现是最通用的方式。这种方式不需要依赖于任何的平台或者第三方服务。对于Prometheus而言也不可能支持所有的平台或者环境。通过基于文件的服务发现方式下,Prometheus会定时从文件中读取最新的Target信息,因此,你可以通过任意的方式将监控Target的信息写入即可。
用户可以通过JSON或者YAML格式的文件,定义所有的监控目标。例如,在下面的yaml文件中分别定义了2个采集任务,以及每个任务对应的Target列表:
2.配置
通过prometheus加载本地文件,当本地文件发生变化,prometheus随之变化
mkdir -p /apps/prometheus/file_sd
cd /apps/prometheus/file_sd
vim sd_my_server.json
[
{
"targets": ["192.168.31.121:9100","192.168.31.122:9100","192.168.31.123:9100"]
}
]
prometheus调用sd_configs
- job_name: "file_sd_my_server"
file_sd_configs:
- files:
- /apps/prometheus/file_sd/sd_my_server.json
refresh_interval: 10s
五.Dns服务发现
192.168.10.10 node-1 k8s-node-1
192.168.10.11 node-2 k8s-node-2
- job_name: "file_sd_my_server"
file_sd_configs:
- files:
- /apps/prometheus/file_sd/sd_my_server.json
refresh_interval: 10s
- job_name: "dns-server-monitor"
metrics_path: /metrics
dns_sd_configs:
- names: ["k8s-node-1","k8s-node-2"]
type: A
port: 9100
评论区