一、目录结构

二、入口

1、文件MonitorServer.py

import os
import sys if __name__ == "__main__":
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "CrazyMonitor.settings") from monitor.backends.management import execute_from_command_line execute_from_command_line(sys.argv)

2、启动函数management.py

    def start(self):
'''start monitor server frontend and backend'''
reactor = data_processing.Datandler(settings)
reactor.looping()

三、检测主机需要监控的服务数据是否按时正常汇报

1、功能如下

1、生成全局的监控配置dict

2、循环所有要监控的服务

3、检测此服务最近的汇报数据

4、检测 有没有这个机器的trigger,如果没有,把机器状态改成ok

2、实现代码

    def looping(self):
'''
start looping data ...
检测所有主机需要监控的服务的数据有没有按时汇报上来,只做基本检测
:return:
'''
#get latest report data
self.update_or_load_configs() #生成全局的监控配置dict
count = 0
while not self.exit_flag:
print("looping %s".center(50,'-') % count)
count += 1
if time.time() - self.config_last_loading_time >= self.config_update_interval:
print("\033[41;1mneed update configs ...\033[0m")
self.update_or_load_configs()
print("monitor dic",self.global_monitor_dic)
if self.global_monitor_dic:
for h,config_dic in self.global_monitor_dic.items():
print('handling host:\033[32;1m%s\033[0m' %h)
for service_id,val in config_dic['services'].items(): #循环所有要监控的服务
#print(service_id,val)
service_obj,last_monitor_time = val
if time.time() - last_monitor_time >= service_obj.interval: #reached the next monitor interval
print("\033[33;1mserivce [%s] has reached the monitor interval...\033[0m" % service_obj.name)
self.global_monitor_dic[h]['services'][service_obj.id][1] = time.time()
#self.load_service_data_and_calulating(h,service_obj)
#only do basic data validataion here, alert if the client didn't report data to server in \
#the configured time interval
self.data_point_validation(h,service_obj) #检测此服务最近的汇报数据
else:
next_monitor_time = time.time() - last_monitor_time - service_obj.interval
print("service [%s] next monitor time is %s" % (service_obj.name,next_monitor_time)) if time.time() - self.global_monitor_dic[h]['status_last_check'] >10:
#检测 有没有这个机器的trigger,如果没有,把机器状态改成ok
trigger_redis_key = "host_%s_trigger*" % (h.id)
trigger_keys = self.redis.keys(trigger_redis_key)
#print('len grigger keys....',trigger_keys)
if len(trigger_keys) ==0: #没有trigger被触发,可以把状态改为ok了
h.status = 1
h.save()
#looping triggers 这里是真正根据用户的配置来监控了
#for trigger_id,trigger_obj in config_dic['triggers'].items():
# #print("triggers expressions:",trigger_obj.triggerexpression_set.select_related())
# self.load_service_data_and_calulating(h,trigger_obj) time.sleep(self.poll_interval)

四、监控主机是否存活

1、功能如下

1、拼出此服务在redis中存储的对应key

2、超过监控间隔但数据还没汇报过来

3、监控主机是否存活

4、要是主机死掉了我就在数据库你注释有问题

5、客户端起来从来每连上过没所以没有数据数据

2、实现代码

    def data_point_validation(self,host_obj,service_obj):
'''
only do basic data validation here, alert if the client didn't report data to server in the configured time interval
:param h:
:param service_obj:
:return:
'''
service_redis_key = "StatusData_%s_%s_latest" %(host_obj.id,service_obj.name) #拼出此服务在redis中存储的对应key
latest_data_point = self.redis.lrange(service_redis_key,-1,-1)
if latest_data_point: #data list is not empty,
latest_data_point = json.loads(latest_data_point[0].decode())
#print('laste::::',latest_data_point)
print("\033[41;1mlatest data point\033[0m %s" % latest_data_point)
latest_service_data,last_report_time = latest_data_point
monitor_interval = service_obj.interval + self.django_settings.REPORT_LATE_TOLERANCE_TIME
if time.time() - last_report_time > monitor_interval: #超过监控间隔但数据还没汇报过来,something wrong with client
no_data_secs = time.time() - last_report_time
msg = '''Some thing must be wrong with client [%s] , because haven't receive data of service [%s] \
for [%s]s (interval is [%s])\033[0m''' %(host_obj.ip_addr, service_obj.name,no_data_secs, monitor_interval)
self.trigger_notifier(host_obj=host_obj,trigger_id=None,positive_expressions=None,
msg=msg)
print("\033[41;1m%s\033[0m" %msg )
if service_obj.name == 'uptime': #监控主机存活的服务
host_obj.status = 3 #unreachable
host_obj.save()
else:
host_obj.status = 5 #problem
host_obj.save() else: # no data at all
print("\033[41;1m no data for serivce [%s] host[%s] at all..\033[0m" %(service_obj.name,host_obj.name))
msg = '''no data for serivce [%s] host[%s] at all..''' %(service_obj.name,host_obj.name)
self.trigger_notifier(host_obj=host_obj,trigger_id=None,positive_expressions=None,msg=msg)
host_obj.status = 5 #problem
host_obj.save()
#print("triggers:", self.global_monitor_dic[host_obj]['triggers'])

五、存活检测监控项间隔设计

1、实例化

1、循环检测每台主机多久没有给我汇报数据
2、监控配置有可能变更
3、检测每个主机每个服务
4、主机是好的服务全挂了

class DataHandler(object):
def __init__(self,django_settings,connect_redis=True):
self.django_settings = django_settings
self.poll_interval = 3 #每3秒进行一次全局轮训
self.config_update_interval = 120 #每120s重新从数据库加载一次配置数据
self.config_last_loading_time = time.time()
self.global_monitor_dic = {}
self.exit_flag = False
if connect_redis:
self.redis = redis_conn.redis_conn(django_settings

2、方法

1、要是主机死掉了我就在数据库你注释有问题
2、客户端起来从来每连上过没所以没有数据数据

    def update_or_load_configs(self):
'''
load monitor configs from Mysql DB
:return:
'''
all_enabled_hosts = models.Host.objects.all()
for h in all_enabled_hosts:
if h not in self.global_monitor_dic: # new host
self.global_monitor_dic[h] = {'services':{}, 'triggers':{}}
'''self.global_monitor_dic ={
'h1':{'services'{'cpu':[cpu_obj,0],
'mem':[mem_obj,0]
},
'trigger':{t1:t1_obj,}
}
}'''
#print(h.host_groups.select_related())
service_list = []
trigger_list = []
for group in h.host_groups.select_related():
#print("grouptemplates:", group.templates.select_related()) for template in group.templates.select_related():
#print("tempalte:",template.services.select_related())
#print("triigers:",template.triggers.select_related())
service_list.extend(template.services.select_related())
trigger_list.extend(template.triggers.select_related())
for service in service_list:
if service.id not in self.global_monitor_dic[h]['services']: #first loop
self.global_monitor_dic[h]['services'][service.id] = [service,0]
else:
self.global_monitor_dic[h]['services'][service.id][0] = service
for trigger in trigger_list:
#if not self.global_monitor_dic['triggers'][trigger.id]:
self.global_monitor_dic[h]['triggers'][trigger.id] = trigger #print(h.templates.select_related() )
#print('service list:',service_list) for template in h.templates.select_related():
service_list.extend(template.services.select_related())
trigger_list.extend(template.triggers.select_related())
for service in service_list:
if service.id not in self.global_monitor_dic[h]['services']: #first loop
self.global_monitor_dic[h]['services'][service.id] = [service,0]
else:
self.global_monitor_dic[h]['services'][service.id][0] = service
for trigger in trigger_list:
self.global_monitor_dic[h]['triggers'][trigger.id] = trigger
#print(self.global_monitor_dic[h])
#通过这个时间来确定是否需要更新主机状态
self.global_monitor_dic[h].setdefault('status_last_check',time.time()) self.config_last_loading_time = time.time()
return True

3、网络延迟容忍度设置

1、网络延迟应该可以自定义容忍度30秒
2、客户端每30秒给我汇报一次我还活着

REPORT_LATE_TOLERANCE_TIME = 10 #allow service report late than monitor interval no more than defined seconds.

  

分布式监控系统开发【day38】:主机存活检测程序解析(七)的更多相关文章

  1. Python之路,Day20 - 分布式监控系统开发

    Python之路,Day20 - 分布式监控系统开发   本节内容 为什么要做监控? 常用监控系统设计讨论 监控系统架构设计 监控表结构设计 为什么要做监控? –熟悉IT监控系统的设计原理 –开发一个 ...

  2. 分布式监控系统开发【day37】:需求讨论(一)

    本节内容 为什么要做监控? 常用监控系统设计讨论 监控需求讨论 如何实现监控服务器的水平扩展? 监控系统架构设计 一.为什么要做监控? 熟悉IT监控系统的设计原理 开发一个简版的类Zabbix监控系统 ...

  3. Python之分布式监控系统开发

    为什么要做监控? –熟悉IT监控系统的设计原理 –开发一个简版的类Zabbix监控系统 –掌握自动化开发项目的程序设计思路及架构解藕原则 常用监控系统设计讨论 Zabbix Nagios 监控系统需求 ...

  4. day26 分布式监控系统开发

    本节内容 为什么要做监控? 常用监控系统设计讨论 监控系统架构设计 监控表结构设计 为什么要做监控? –熟悉IT监控系统的设计原理 –开发一个简版的类Zabbix监控系统 –掌握自动化开发项目的程序设 ...

  5. 分布式监控系统开发【day37】:表结构设计(二)

    一.表结构关系图 二.表结构需求讨论 1.主机表(Host) 1.解决了什么问题? 1.如果我不想让它监控了,就有一个开关的东西给它禁掉2.主机存活状态检测间隔 2.代码 class Host(mod ...

  6. 分布式监控系统开发【day38】:报警阈值程序逻辑解析(三)

    一.需求讨论 1.请问如何解决延迟问题 1000台机器,每1分钟循环一次但是刚好第一次循环第一秒刚处理完了,结果还没等到第二分钟又出问题,你那必须等到第二次循环,假如我这个服务很重要必须实时知道,每次 ...

  7. 分布式监控系统开发【day38】:报警策略队列处理(五)

    一.目录结构 二.报警策略队列处理 1.入口MonitorServer import os import sys if __name__ == "__main__": os.env ...

  8. 分布式监控系统开发【day38】:监控trigger表结构设计(一)

    一.需求讨论 1.zabbix触发器的模板截图 1.zabbix2.4.7 2.zabbix3.0 2.模板与触发器关联的好处 好处就是可以批量处理,比如我说我有1000机器都要监控cpu.内存.IO ...

  9. 分布式监控系统开发【day38】:报警策略设计(二)

    一.策略和动作多对多的好处坏处 1.好处: 相同服务,相同策略的服务可以不用重复写好多次触发器 2.坏处: 1.策略A给小李和小罗发邮件2.策略B给小胡和小崔发邮件3.策略A是第三部发邮件4.策略B是 ...

随机推荐

  1. Asp.Net Core 下 Newtonsoft.Json 转换字符串 null 替换成string.Empty

    public class NullToEmptyStringResolver : DefaultContractResolver { /// <summary> /// 创建属性 /// ...

  2. Java文件下载:如何编码文件名称以及如何设置HttpServletResponse

    在下载文件时,经常遇到文件名乱码等问题. 本文说明如何编码文件名,以及如何设置HttpServletResponse对象. 1,如何编码文件名 String userAgent = request.g ...

  3. SQLServer之创建LOGON触发器

    LOGON触发器工作原理 登录触发器将为响应 LOGON 事件而激发存储过程. 与 SQL Server实例建立用户会话时将引发此事件. 登录触发器将在登录的身份验证阶段完成之后且用户会话实际建立之前 ...

  4. MySql 学习之路-Date函数

    MySQL中重要的内建函数 函数 描述 NOW() 返回当前的日期和时间 NOW() 返回当前的日期和时间. 语法 NOW() -- 实例 -- 下面是 SELECT 语句: SELECT NOW() ...

  5. 解析Object.defineProperty的作用

    对象是由多个名/值对组成的无序的集合.对象中每个属性对应任意类型的值. 定义对象可以使用构造函数或字面量的形式: 除了以上添加属性的方式,还可以使用Object.defineProperty定义新属性 ...

  6. java 下载word freemaker

    网上有很多优质的博文了,这里这篇博客就是记录一下字自己,写demo的历程,坑和收获 在java程序中下载word 有6中方式,此处省略(嘻嘻),不过大家公认的是 freemaker 和 PageOff ...

  7. 8-过滤器Filter和监听器Listener

    一.web监听器:监听特殊事件的发生1.监听实现步骤 a.写一个java类,实现特定的接口,重写相关方法 b.在web.xml中,牌配置 <listener> <listener-c ...

  8. iOS开发基础-九宫格坐标(3)之Xib

    延续iOS开发基础-九宫格坐标(2)的内容,对其进行部分修改. 本部分采用 Xib 文件来创建用于显示图片的 UIView 对象. 一.简单介绍  Xib 和 storyboard 的比较: 1) X ...

  9. 网站添加icon

    设置网站的icon<link rel="shortcut icon" href="./static/img/favicon.ico" >

  10. 利用cocoapods管理开源项目,支持 pod install安装整个流程记录(github公有库)

    利用cocoapods管理开源项目,支持 pod install安装整个流程记录(github公有库),完成预期的任务,大致有下面几步: 1.代码提交到github平台 2.创建.podspec 3. ...