自动化监控系统(四) 客户端设计

一个程序的目录结构:

bin:可执行文件

conf:配置文件

core:逻辑关系

plugins:各种插件

var:日志

客户端:

1、设置一个程序入口,运行该文件A就能启动客户端。

2、给A传位置参数(start 或 stop),通过获取位置参数名称,使用反射来调用相应方法,做到启动或者停止client。

3、启动客户端后,通过发起HTTP请求,获取service下发的任务(监控哪些服务:CPU、memory、network。。。。。。)

发送请求中,应该有client相关配置信息:主机Id、主机IP地址、主机端口、url配置、请求超时时间和更新监控配置时间。

暂时这些,后面再添加

client端通过特定url,发送http请求,然后server端返回相应的信息,告诉client需要监控什么服务

在服务端也需要添加相应的url和view,返回客户端的请求信息。

view

from django.shortcuts import render

# Create your views here.

from django.views.generic import View
from django.http import HttpResponse
import json

from .serializer import ClientHandler

class client_config_view(View):

    #返回客户端需要监控信息
    def get(self,request,client_id):
        #获取client信息
        # client_configs = ClientHandler(client_id).fetch_configs()
        client_obj = ClientHandler(client_id)
        client_config = client_obj.fetch_configs()
        print("客户端ID",client_id)
        if client_config:
            return HttpResponse(json.dumps(client_config),content_type="application/json")

serializer

#!/usr/bin/env python
# _*_ coding:utf-8 _*_
__author__ = "BIGNI"
__date__ = "2017/4/29 16:34"
import traceback

from django.views.generic import View

from .models import Host

class ClientHandler(View):
    #初始化
    def __init__(self,client_id):
        self.client_id = client_id
        #client配置
        self.client_configs = {
            "services":{}
        }

    def fetch_configs(self):

        try:

            host_obj_id = Host.objects.get(id=self.client_id)
            print(">>>>>>>>>",host_obj_id)
            #获取模板list
            template_list = list(host_obj_id.templates.select_related())
            print(">>>>",template_list)
            #获取主机组obj

            host_group_obj = host_obj_id.host_groups.select_related()
            #把主机组下的目标添加进来
            template_list.extend([template for template in host_group_obj])
            print("--->",template_list)
            #获取服务列表
            for template in template_list:
                for service in template.services.select_related():
                    print(service)
                    #获取插件名和间隔时间
                    self.client_configs[‘services‘][service.name] = [service.plugin_name,service.interval]

        except:
            traceback.print_exc()
        return self.client_configs

# test = ClientHandler(1)
# print(test,test.fetch_configs())

测试下:

调用特定url,server端可以返回需要监控的信息。

接下来继续client端的开发:

1、通过运行monitor_client启动客户端,执行main_command方法。

2、main_command方法自带start和stop两个方法

#!/usr/bin/env python
# _*_ coding:utf-8 _*_
__author__ = "BIGNI"
__date__ = "2017/4/15 23:48"

from .client import ClientHandlers

class main_command(object):
    #初始化
    def __init__(self,sys_argv):
        self.sys_argv = sys_argv
        if len(sys_argv) < 2 :
            exit("请输入start或stop")
        else:
            self.entry_command()

    #根据命令调用方法
    def entry_command(self):
        print("##############################################")
        if hasattr(self.sys_argv[1]):
            func = getattr(self,self.sys_argv[1])
            return func()
        else:
            print("请输入正确的命令")

    def start(self):
        client = ClientHandlers()
        client.forever_run()

    def stop(self):
        pass

main_command

3、start方法会创建ClientHandlers对象,接着调用里面的forever_run方法,获取server端返回的信息,并根据插件名给各个服务进行监控

#!/usr/bin/env python3
# _*_ coding:utf-8 _*_
__author__ = "BIGNI"
__date__ = "2017/4/29 11:42"
import time,threading,json

import requests

from conf import settings
from plugins import plugin_api

class ClientHandlers(object):

    def __init__(self):
        #初始化监控服务
        self.monitor_services = {}

    def load_lastest_config(self):
        """
        加载最新的配置信息
        :return:
        """
        #request请求方式
        request_type = settings.configs["urls"]["get_configs"][1]
        #拼接url
        request_url = "%s/%s" % (settings.configs[‘urls‘][‘get_configs‘][0], settings.configs[‘HostID‘])
        lastest_config = self.url_request(request_type,request_url)
        #把最小配置更新到监控服务字典中
        self.monitor_services.update(lastest_config)

    def forever_run(self):
        #启动客户端
        exit_flag = False
        #第一次启动时初始化最新配置时间
        config_lastest_update_time = 0
        while not exit_flag:

            if time.time() - config_lastest_update_time > settings.configs[‘ConfigUpdateInterval‘]:
                self.load_lastest_config()
                print("Lastest_config:",self.monitor_services)
                config_lastest_update_time = time.time()

            """
            Lastest_config: {‘services‘: {‘LinuxCPU‘: [‘get_linux_cpu‘, 15], ‘LinuxMemory‘: [‘get_memory_info‘, 60],
            ‘LinuxNetwork‘: [‘GetNetworkStatus‘, 60]}}

            """
            for service_name,val in self.monitor_services[‘services‘].items():
                if len(val) ==2:
                    # 第一次启动插件时,初始化当前时间,给每个服务维护一个计时器
                    self.monitor_services[‘services‘][service_name].append(0)
                #获取监控间隔和最新插件时间
                monitor_interval = val[1]
                last_invoke_time = val[2]
                if time.time() - last_invoke_time > monitor_interval:
                    print("--->",last_invoke_time,"--->",time.time())
                    #重置计时器时间
                    self.monitor_services[‘services‘][service_name][2] = time.time()
                    t = threading.Thread(target=self.invoke_plugin,args=(service_name,val))
                    t.start()
                    print("启动监控的服务: [{ServiceName}]".format(ServiceName=service_name))

                else:
                    #需要等待监控间隔时间
                    print("监控的服务: {ServiceName} 距离下次启动时间:{interval} secs".format(ServiceName=service_name,
                                                                  interval=monitor_interval - (time.time() - last_invoke_time)))
                    time.sleep(5)

        time.sleep(1)

    #运行插件
    def invoke_plugin(self,service_name,val):
        #{"services": {"LinuxNetwork": ["n/a", 60,0], "LinuxMemory": ["n/a", 60,0], "LinuxCPU": ["n/a", 60,0]}}
        #获取插件名
        plugin_name = val[0]
        if hasattr(plugin_api,plugin_name):
            func = getattr(plugin_api,plugin_name)
            plugin_callback = func()
            print("####################################################")
            print(plugin_callback)
            print("####################################################")

            report_data = {
                ‘client_id‘:settings.configs[‘HostID‘],
                ‘service_name‘:service_name,
                ‘data‘:plugin_callback
            }
            #请求方式get or post
            request_action = settings.configs[‘urls‘][‘service_report‘][1]
            #请求路径
            request_url = settings.configs[‘urls‘][‘service_report‘][0]

            #report_data = json.dumps(report_data)
            # print(‘---report data(发送的数据):‘,report_data)
            #调用url_request方法,以post方式发送request
            self.url_request(request_action, request_url, params=report_data)
        else:
            print("\033[31;1mCannot find service [%s]‘s plugin name [%s] in plugin_api\033[0m"% (service_name,plugin_name ))
        print(‘--plugin:‘,val)

    def url_request(self,action,request_url,**extra_data):

        abs_url = "http://{ip_addr}:{port}/{url}".format(ip_addr=settings.configs["Server"],
                                                         port=settings.configs["ServerPort"],
                                                         url=request_url)
        print("\033[31;1m{abs_url}\033[0m".format(abs_url=abs_url),type(extra_data),extra_data)
        if action in (‘get‘,"GET"):
            print(abs_url,extra_data)
            try:
                r = requests.get(abs_url,timeout=settings.configs[‘RequestTimeout‘])
                r_data = r.json()
                return r_data

            except requests.RequestException as E :
                exit("\033[31;1m%s\033[0m" % E)

        elif action in (‘post‘,‘POST‘):
            try:
                #把数据转换成json再通过post发送
                # data = json.dumps(extra_data[‘params‘])
                req = requests.post(url=abs_url,data=extra_data["params"])

                res_data = req.json()
                # res_data = req.text
                print("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~")
                print("\033[31;1m[%s]:[%s]\033[0m response:\n%s,%s" % (action, abs_url, res_data,data))
                print("~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~")
                return res_data

            except Exception as e:
                print(‘------exec‘, e)
                exit("\033[31;1m%s\033[0m" % e)

client

PS:客户端在接收到服务端返回的配置信息,并不能识别具体要监控的服务,比如server端告诉client端需要监控CPU各项参数等,所以两端要能约定好,比如server端返回CPU、Memory和Network这三个字符串,就表示要监控这三种服务,三个字符串在这里就是插件名。插件统一放在plugins目录下。

 不同服务监控的时间可以通过server端返回的监控间隔来判断

每次监控服务就生成一个新的线程,然后就让线程返回数据给服务端,不需要再做处理。

对于server端和client端的数据交互,推荐使用requests模块,可以自动处理数据的编码、json、发送超时等问题。

问题1:在models里的manytomany字段不会存储在数据表中,多对多的在xadmin里要按ctrl选中才行,不然通过select_relate获取到的是空的queryset,

问题2:我调用model的serializer没放在app的默认views文件里,进行debug调试时,serializer也需要打上断点。

问题3:我在client通过post方式发送数据给server端,debug调试时发现没取到值,查了资料,原来requests库有三种post发送数据方式,我使用的是json方式(发送前先用json.dumps处理下),改成用form方式(实际就是不需要json,requests会自动转换)

时间: 2024-10-11 07:24:36

自动化监控系统(四) 客户端设计的相关文章

自动化监控系统(三) 搭建xadmin做网站后台

Django有个自带的admin后台,不过界面不怎么好看,这里我用xadmin 我的python版本是3.5,可以使用支持py3的xadmin:https://github.com/sshwsfc/xadmin xadmin部署步骤: 1.把xadmin整个目录拷贝到项目里面 2.需要安装的依赖包: django~=1.9.0django-crispy-forms~=1.6.0django-reversion~=2.0.0django-formtools==1.0future==0.15.2ht

zabbix(一):zabbix自动化监控系统搭建详解

一.监控系统机制 1.监控工具工作机制 监控是通过传感器采集数据,在经过数据的存储加工后,进行展示.一般采集的数据为时间序列数据,即随时间变化而动态变化的数据:当采集到的数据超出阈值将会报警.监控功能的实现可基于专用agent.ssh.SNMP协议.IPMI(专业级监控接口IntelligentPlatform Management Interface,指挥平台管理接口) 2.SNMP协议 Simple Network Management Protocol,简单网络管理协议.由一组网络管理的标

庖丁解监控系统(四)

这一篇我们来聊聊监控系统的架构.欢迎大家加入运维开发讨论交流群来交流,群号 365534424,本文仅授权51reboot.51cto上发布. 架构这个词太大了,这里我们缩小一下,只来谈谈宏观的监控系统整体架构.在这个范围里面,web由于负责统一的系统管理和操作功能,缩减为一个模块. 最简单的架构如下图 这是监控系统第一层的架构.比照百度地图的话,我们可以认为这个是全国地图.最粗粒度的几个模块就是这三个.web.数据采集.数据处理. PUSH  PULL 我们先来关注数据采集模块到数据处理和报警

20155114许星霖《远程安防监控系统》课程设计个人报告

一.对任务的理解 1.项目概述 本项目需要实现以嵌入式Web服务器为核心的视频监控系统. 摄像头采集的到的图像经过压缩后,传到内置的web服务器中.用户只需要通过浏览器就可以观看摄像头采集到的数据. 2.系统架构 该项目基本可以看作B/S架构,由有三部分组成: (1)核心服务端:其实是客户端(严格意义上说,PC上的浏览器才是客户端)一台普通的PC机,需要与前端数据中心在同一局域网中,然后通过浏览器对系统进行监控和设置. (2)前端数据中心:FS4412开发平台,可以连接摄像头.GPRS.zigB

基于Android平台的i-jetty网站智能农业监控系统

基于android平台i-jetty网站的智能农业监控系统 摘要:传统的监控系统,一般是基于PC的有线通信传输,其有很多不足之处,如功耗较高.布线成本高.难度大,适应性差,可扩展性不强,增加新的通信线路需要再次布线施工,而且维护起来也比较麻烦,一旦线路出问题,需要繁琐的检查.而嵌入式Web监控系统是基于物联网技术,其无线通信技术具有成本低廉.适应性强.扩展性强.信息安全.使用维护简单等优点. 智能农业中,种植大棚是通过大棚内安装温湿度以及光照传感器,来对农作物的环境参数进行实时采集,由Web监控

项目一. 移动物体监控系统

项目一. 移动物体监控系统 Sprint0-产品设计与规划 第1课-产品功能展示 我们在学校的时候,做项目开发,可能就是想到了哪里就做哪里.但是在实际公司的开发过程中,我们是要严格的按照公司的流程来进行的. 项目开发分成了准备阶段和开发阶段: 我们的最后效果就是,利用摄像头和音响完成连接,如图: 当有移动物体在摄像头面前移动时,摄像头能采集图像和视频,并且发出报警的声音.通过访问对应的局域网,我们可以通过网页访问,如下: 第2课-产品功能模型设计 第3课-Product Backlog规划 我们

开源监控系统中 Zabbix 和 Nagios 哪个更好?

监控平台的话,各有优劣,但基本都可以满足需求.等达到一定监控指标后,发现,最困难的是监控项目的管理. CMDB中小规模(服务器<=1k):Zabbix大规模(1k>=服务器<=10k):Nagios进行二次开发超大规模(服务器>=10k):开发适应自己平台的监控软件吧另推荐个牛逼的东西:http://prometheus.io 作者:好撑链接:https://www.zhihu.com/question/19973178/answer/131911060来源:知乎著作权归作者所有.

手机端的音视频监控系统开发

网络信息化的趋势,随着流媒体技术.无线网络技术以及视频压缩技术的不断进步,视频监控技术得到了广泛的应用,同时,监控的规模和范围也在不断的扩大.人们对于安全保障的要求不断的提高,从而使得过去以图文为主的内容服务应经不能够满足用户的需求,取而代之的则是音视频多媒体服务.使用移动终端技术的视频监控系统,不仅具有体积小型化.安装傻瓜化以及配置灵活化的优势,最重要的是还降低了成本.由于网络功能和视频压缩都被集中的保存在小体积的设备中,因此,通过网络远程监控视频设备就可以获得监控视频.目前,网络视频监控不仅

项目三. 基于图像压缩的视频监控系统

项目三. 基于图像压缩的视频监控系统 Sprint0-产品设计与规划 基于图像压缩的视频监控系统 1. 产品功能演示 在linux系统上运行程序,弹出登录界面,输入地址.端口信息,弹出视频监控界面,实时传出视频信息. 2. 功能模块分析 采集端: 图像采集子系统 图像编码子系统 传输子系统 主程序 监控端: 传输子系统 图像编码子系统 传输子系统 主程序 Sprint1-基于Epoll架构的采集端程序框架设计 第1课-Epoll机制精通 大纲: v  为什么用Epoll? 阻塞型IO与多路复用