zoukankan      html  css  js  c++  java
  • [系统集成] 基于 elasticsearch 的企业监控方案

    注:

    2017年10月16日:

    使用中发现 es 查询时序数据的性能较差,且 watch 脚本的编写比较麻烦,因此已将监控系统切换到了 influxdb+grafana平台。新监控系统各方面情况比较满意。

    ---------------

    在企业监控领域,nagios 和 zabbix 一直是使用率比较高的工具。最近几年,业界又出现了新的工具和架构,比如:telegraf(数据抓取工具,还有 collectd, logstash,heapster) + influxdb(数据存储和搜索工具,还有 elasticsearch、opentsd) + kapacitor(数据处理和报警工具,还有 elastAlert,watch) + grafana(数据展示工具)。新的监控工具和架构具有分布式架构、组件独立、松耦合、易于扩展、插件丰富、适用范围广等优点,从容器监控到传统的服务器、虚拟机监控都适用。

    在数据存储和搜索方面,influxdb 正在快速发展中,目前免费版没有集群功能;而elasticsearch 是一种健壮、高效、使用广泛的大数据全文搜索引擎,将监控数据存储在 es里,能与大数据平台结合,发挥更大作用。

    (转载请注明出处:http://www.cnblogs.com/hahp)

    1. 系统结构图

    注:我的测试环境数据不多,因此源数据由 heapster 和 telegraf 抓取后直接存到 elasticsearch。如果数据量很大、elasticsearch 的写操作出现瓶颈,可以在 elasticsearch前加 kafka 和 logstash。

    2. 数据抓取

    heapster:用于抓取 kubernetes 容器监控数据,直接存到elasticsearch(也支持存到kafka等其它地方);

    telegraf:用于抓取非容器的其它监控数据,它的插件很多,几乎涵盖了各种数据源。

    3. 数据存储和搜索

    elasticsearch 集群,我采用的是两台虚拟机;

    4. 告警

    我采用的是 elastic x-pack中的 watch:

    https://www.elastic.co/guide/en/x-pack/current/how-watcher-works.html 

    目前 watch的action只支持 email、webhook、index、loggin、hipchat、slack、pagerduty、jira。如果想执行一个外部脚本,比如:shell、python、perl脚本,可以将这些脚本集成到一台 restful web service服务器中,watch 便能够通过 webhook 方式调用。

    watch 的搜索、状态判断、数据转换部分都支持一种 plainless script 语言,比 一般的方式更灵活、功能更强:

    https://www.elastic.co/guide/en/elasticsearch/painless/master/painless-specification.html

    5. 展示

    grafana 的效果非常好,支持 elasticsearch。

    附:x-pack watch 例子

    下面的 watch 用于监控 k8s nodes 的可用磁盘容量,如果任意一台node的可用磁盘容量低于5G,或者2分钟内获取不到监控数据,watch就会发送短信和邮件报警。

    我是把上述功能写到两个watch里,你也可以研究更好的方法精简这两个watch。

    PUT _xpack/watcher/watch/k8s_node_filesystem_available_evaluate
    {
      "trigger" : { "schedule" : { "interval" : "10s" }},
      "input" : {
        "search" : {
          "request" : {
            "indices" : [ 
              "<heapster-{now}>", 
              "<heapster-{now-1h}>" 
            ],
            "body" : {
              "query" : {
                "bool" : {
                  "must" : [
                    { "term": { "_type": "filesystem" }},
                    { "term": { "MetricsTags.resource_id": "/" }},
                    { "term": { "MetricsTags.type": "node" }}
                  ],
                  "filter" : [
                    { "range": { "Metrics.filesystem/available.value": {"lt": 5000000000}} },
                    { "range": {"FilesystemMetricsTimestamp": {"gte": "now-70s"}} }
                  ]
                }
              },
              "aggs": {
                "group_by_host_id": {
                  "terms": { "size": 20, "field": "MetricsTags.host_id" },
                  "aggs" : {
                    "group_by_available_value" : {
                      "terms": { "script": "params['_source']['Metrics']['filesystem/available']['value']>0?params['_source']['Metrics']['filesystem/available']['value']/(1024*1024*1024):params['_source']['Metrics']['filesystem/available']['value']" }
                    }
                  }
                }
              }
            }
          }
        }
      },
      "condition" : {
        "compare" : { "ctx.payload.hits.total" : { "gt": 0 }}
      },
      "throttle_period" : "60m",
      "actions" : {
        "send_sms" : {
          "webhook" : {
            "method" : "POST",
            "host" : "sms.xxx.com",
            "port" : 80,
            "path" : "/actions/sendsms",
            "params" : {
              "phone": "1580000000",
              "message": "【XXX】报警:k8s nodes filesytem available:{{#ctx.payload.aggregations.group_by_host_id.buckets}}{{key}} {{group_by_available_value.buckets.0.key}}GB, {{/ctx.payload.aggregations.group_by_host_id.buckets}}"
            }
          }
        },
        "send_email" : {
          "email" : {
            "to" : "AAAAAAA@xxx.com",
            "subject" : "【XXX】报警:k8s nodes filesytem available",
            "body" : "{{#ctx.payload.aggregations.group_by_host_id.buckets}}{{key}} {{group_by_available_value.buckets.0.key}}GB, {{/ctx.payload.aggregations.group_by_host_id.buckets}}"
          }
        }
      }
    }
    PUT _xpack/watcher/watch/k8s_node_filesystem_hava_data
    {
      "trigger" : { "schedule" : { "interval" : "10s" }},
      "input" : {
        "search" : {
          "request" : {
            "indices" : [ 
              "<heapster-{now}>", 
              "<heapster-{now-1h}>" 
            ],
            "body" : {
              "query" : {
                "bool" : {
                  "must" : [
                    { "term": { "_type": "filesystem" }},
                    { "term": { "MetricsTags.resource_id": "/" }},
                    { "term": { "MetricsTags.type": "node" }},
                    { "exists": { "field": "Metrics.filesystem/available.value" }}
                  ],
                  "filter" : [
                    { "range": {"FilesystemMetricsTimestamp": {"gte": "now-130s"}} }
                  ]
                }
              },
              "aggs": {
                "group_by_host_id": {
                  "terms": { "size": 20, "field": "MetricsTags.host_id" }
                }
              }
            }
          }
        }
      },
      "condition" : {
        "script" : "if(ctx.payload.aggregations.group_by_host_id.buckets.length<12){ return true; } else{ return false;}" 
      },
      "transform" : {
        "script" : "List host_all = ['172.31.17.31','172.31.17.32','172.31.17.33','172.31.17.34','172.31.17.35','172.31.17.36','172.31.17.37','172.31.17.38','172.31.17.39','172.31.17.71','172.31.17.72','172.31.17.73']; List host_ids = []; for (int i = 0; i < ctx.payload.aggregations.group_by_host_id.buckets.length; ++i ){ host_ids.add(ctx.payload.aggregations.group_by_host_id.buckets[i].key); } List host_no_data = []; for(item in host_all){ if(!host_ids.contains(item)){ host_no_data.add(['key':item]); } } return ['host_no_data':host_no_data];"
      },
      "throttle_period" : "60m",
      "actions" : {
        "send_sms" : {
          "webhook" : {
            "method" : "POST",
            "host" : "sms.xxx.com",
            "port" : 80,
            "path" : "/actions/sendsms",
            "params" : {
              "phone": "1580000000",
              "message": "【XXX】报警:k8s nodes filesytem no data:{{#ctx.payload.host_no_data}}{{key}},{{/ctx.payload.host_no_data}}"
            }
          }
        },
        "send_email" : {
          "email" : {
            "to" : "AAAAAAA@xxx.com",
            "subject" : "【XXX】报警:k8s nodes filesytem no data",
            "body" : "{{#ctx.payload.host_no_data}}{{key}},{{/ctx.payload.host_no_data}}"
          }
        }
      }
    }

      

  • 相关阅读:
    redis学习
    Ubuntu命令大全
    关于jquery中attr和prop的用法
    Ubuntu下修改为永久DNS的方法
    Yii2 behaviors中verbs access的一些理解
    vue_ form表单 v-model
    vue-one_demo_music
    ES6
    VUE 入门 01
    Django model.py表单设置默认值允许为空
  • 原文地址:https://www.cnblogs.com/hahp/p/7027195.html
Copyright © 2011-2022 走看看