def post(self, request): req = req_body_to_json(request) tpl_name = req.get("tpl_name", '') tpl_os = req.get("tpl_os", '') description = req.get("description", '') quotas = req.get("quotas", []) if not all([tpl_name, tpl_os, len(quotas)]): return Request.errorFcun("参数异常", data=[]) tpl_obj = Tpl.objects.filter(tpl_name=tpl_name, is_deleted=0).first() if tpl_obj: return Request.errorFcun(msg="添加失败 名称重复", data=[]) tpl = Tpl(tpl_name=tpl_name, tpl_os=tpl_os, description=description, author=request.user.username) # 批量插入 if tpl: try: # 下面的代码在一个事务中执行,一但出现异常,整个with函数内部的数据库操作都会回滚 with transaction.atomic(): tpl.save() # 准备批量插入数据 tpl_quota_list_to_insert = list() for quota in quotas: tpl_quota_list_to_insert.append( CheckSystemTplQuta(tpl_id=tpl.id, quota_id=quota['id'], quota_threshold=str( quota['quota_threshold']))) CheckSystemTplQuta.objects.bulk_create( tpl_quota_list_to_insert) field_names = Log.get_model_field(Tpl) field_names['quotas'] = "巡检指标" req['author'] = request.user.username req['tpl_os'] = CheckSystemOs.objects.get( pk=req['tpl_os']).os_name req['quotas'] = tpl_quotas(quotas) Log.operation_log(request, table_name=Tpl._meta.verbose_name, update_fields=req, operation_module_name="模板管理", field_names=field_names) data = req_body_to_json(request) data['tpl_id'] = tpl.id except: logger.error( f"新增模板失败 接口名称({request.path}) 请求参数({req_body_to_json(request)})" ) return Request.succFcun(msg="添加成功", data=data) else: return Request.errorFcun(msg="添加失败", data=[])
def post(cls, request, *args, **kwargs): """ 获取机器运行详情 参数:os 操作系统,task_id 任务ID host 操作主机IP 逻辑:1,根据系统调用不同的方法(不同系统获取参数有差异) 2,获取对应任务的任务结果 3,在任务结果中获取对应的机器信息 """ try: req = req_body_to_json(request) except: req = { 'os': request.POST.get('os'), 'execute_id': request.POST.get('execute_id'), 'host': request.POST.get('host') } # if req.get('os') == 'linux': # return linux_host_detail(req) # # return detail(req) # # if req.get('os') == 'centos': # # return linux_host_detail(req, 1) # # elif req.get('os') == 'ubuntu': # # return linux_host_detail(req, 2) # else: # return windows_host_detail(req) fun = {'linux': linux_host_detail, 'windows': windows_host_detail} return fun[req.get('os')](req)
def fetch_report(request): """ 查询报告 """ req = req_body_to_json(request) # 获取参数 task_id = req.get("task_id", 0) # task_id = request.GET.get("task_id", 0) # 数据校验 if int(task_id) <= 0: return JsonResponse({"result": False, "message": "参数错误"}) task = Task.objects.filter(id=task_id) if not task.exists(): return JsonResponse({"result": False, "message": "没有查询到这个任务"}) task = task.first() task_result_list = [] for tr in TaskResult.objects.filter(task=task): task_result_dict = tr.to_dict() task_result_temp = { "quota_name": task_result_dict["quota_name"], "task_state": task_result_dict["task_state"], "task_step_state": task_result_dict["task_step_state"], "result": [], } if task_result_dict["result"]: for ip, val in task_result_dict["result"].items(): temp = { "ip": ip, "val": val[task_result_dict["quota_name"]], "threshold": task_result_dict["quota_threshold"], } warn_name = task_result_dict["quota_name"] + "_warning" if val.get(warn_name, False): temp["warning"] = val[task_result_dict["quota_name"] + "_warning"] show_name = task_result_dict["quota_name"] + "_show" if val.get(show_name, False): temp["show"] = val[task_result_dict["quota_name"] + "_show"] task_result_temp["result"].append(temp) task_result_list.append(task_result_temp) return JsonResponse({ "result": True, "data": task_result_list, "message": "" })
def add_quota(request): """ 添加模板指标 """ req = req_body_to_json(request) # 获取参数 tpl_id = req.get("tpl_id", 0) quota_name = req.get("quota_name", "") script_type = req.get("script_type", 0) script_content = req.get("script_content", "") quota_handler = req.get("quota_handler", "") quota_threshold = req.get("quota_threshold", "") # 数据校验 if tpl_id <= 0 or quota_name == "" or \ script_type <= 0 or script_content == "" or \ quota_handler == "" or quota_threshold == "": return JsonResponse({"result": False, "message": "参数错误"}) # 查询模板 tpl = Tpl.objects.filter(id=tpl_id) if not tpl.exists(): return JsonResponse({"result": False, "message": "参数错误 找不到这个模板ID"}) tpl_obj = tpl.first() # 判断指标名字是否存在 (区分操作系统) if Quota.objects.filter(quota_name=quota_name, quota_os=tpl_obj.tpl_os).exists(): return JsonResponse({ "result": False, "message": "这个操作系统[" + tpl_obj.tpl_os + "]已经有这个名字的指标了" }) quota = Quota.objects.create( quota_name=quota_name, quota_os=tpl_obj.tpl_os, quota_handler=quota_handler, quota_threshold=quota_threshold, script_type=script_type, script_content=script_content, ) # 查模板之前的指标 tpl_quota_list = eval(tpl_obj.tpl_quotas) # 简易去重 tpl_quota_set = set(tpl_quota_list) tpl_quota_set.add(quota.id) # 模板添加刚刚创建的指标 tpl.update(tpl_quotas=json.dumps(list(tpl_quota_set))) return JsonResponse({"code": 0, "msg": "添加成功", "data": []})
def post(self, request): req = req_body_to_json(request) quota_name = req.get("quota_name", "") quota_os = req.get("quota_os", 0) script_type = req.get("script_type", "") script_content = req.get("script_content", "") quota_handler = req.get("quota_handler", "cmp_show") quota_threshold = req.get("quota_threshold", "") username = req.get("username", "") if not all( [quota_name, username, quota_os, script_type, script_content]): return Request.errorFcun("参数异常", data=[]) quota_obj = Quota.objects.filter(quota_name=quota_name, is_deleted=0).first() if quota_obj: return Request.errorFcun(msg="添加失败 名称重复", data=[]) quota = Quota( quota_name=quota_name, quota_os=quota_os, script_type=script_type, script_content=script_content, quota_handler=quota_handler, quota_threshold=quota_threshold, author=username, quota_class=18, ) if quota: try: # 下面的代码在一个事务中执行,一但出现异常,整个with函数内部的数据库操作都会回滚 with transaction.atomic(): quota.save() field_names = Log.get_model_field(Quota) req['author'] = username req['quota_os'] = CheckSystemOs.objects.get( pk=quota_os).os_name req['quota_class'] = "自定义巡检" Log.operation_log(request, table_name=Quota._meta.verbose_name, update_fields=req, operation_module_name="自定义巡检", field_names=field_names) except: logger.error( f"新增自定义巡检失败 接口名称({request.path}) 请求参数({req_body_to_json(request)})" ) return Request.succFcun(msg="添加成功", data=[]) else: return Request.errorFcun(msg="添加失败", data=[])
def put(self, request): req = req_body_to_json(request) quota_id = req.get("quota_id", 0) quota_name = req.get("quota_name", "") quota_os = req.get("quota_os", 0) script_type = req.get("script_type", "") script_content = req.get("script_content", "") quota_handler = req.get("quota_handler", "cmp_show") quota_threshold = req.get("quota_threshold", "") if not all([ quota_id, quota_name, quota_os, script_type, script_content, quota_handler ]): return Request.errorFcun("参数异常", data=[]) # 如果设置了对比方式 但未设置值 if quota_handler != "cmp_show" and not quota_threshold: return Request.errorFcun("请设置阈值", data=[]) # 判断是否存在 quota_obj = Quota.objects.filter(id=quota_id) if quota_obj.exists(): quota = Quota.objects.get(pk=quota_id) try: # 下面的代码在一个事务中执行,一但出现异常,整个with函数内部的数据库操作都会回滚 with transaction.atomic(): req.pop("quota_id") Quota.objects.filter(id=quota_id).update(**req) field_names = Log.get_model_field(Quota) req['quota_threshold'] = quota.quota_threshold req['author'] = quota.author req['quota_os'] = CheckSystemOs.objects.get( pk=quota.quota_os).os_name req['quota_class'] = CheckSystemClass.objects.get( pk=quota.quota_class).class_name Log.operation_log(request, Quota._meta.verbose_name, quota, update_fields=req, operation_module_name="自定义巡检", field_names=field_names) except: logger.error( f"修改自定义巡检失败 接口名称({request.path}) 请求参数({req_body_to_json(request)})" ) return Request.succFcun(msg="修改成功", data=[]) else: return Request.errorFcun(msg="修改失败", data=[])
def execute_task(request): """ 执行任务 按脚本执行 """ req = req_body_to_json(request) # req = request.GET task_id = int(req.get('task_id', 99)) # 数据校验 if task_id <= 0: return Request.errorFcun(msg='参数错误') # 校验数据库是否存在已经执行的任务 res = redis_link.hget(name="current_task", key=task_id) if not res: redis_link.hset(name="current_task", key=task_id, value="True") else: return Request.errorFcun(msg='任务已经在执行中') # 查询所在任务数据 tasks = Task.objects.filter(id=task_id) if not tasks.exists(): return Request.errorFcun(msg='参数错误,找不到这个任务') # 获取任务数据行 task = tasks.first() # 查询模板 tpl = Tpl.objects.filter(id=task.task_tpl_id) if not tpl.exists(): return Request.errorFcun(msg='参数错误,找不到这个模板ID') tplLogic = TplLogic() tpl_quota_list = tplLogic.getQuotas(task.task_tpl_id) if len(tpl_quota_list) == 0: return Request.errorFcun(msg='模板的指标是空的,请先添加模板指标') # 启动celery任务 task_celery.delay(task, task.id, request.user) field_names = Log.get_model_field(Task) Log.operation_log(request, Task._meta.verbose_name, task, update_fields={}, operation_module_name="任务管理", field_names=field_names, method="EXECUTE") return Request.succFcun()
def put(self, request): req = req_body_to_json(request) notify_configs = req.get("notify_configs") config_value = ",".join(notify_configs) try: # 下面的代码在一个事务中执行,一但出现异常,整个with函数内部的数据库操作都会回滚 with transaction.atomic(): SystemConfig.objects.filter(config_type="消息通知").update( **{"config_value": config_value}) except: logger.error( f"修改通知配置 接口名称({request.path}) 请求参数({req_body_to_json(request)})" ) notify_conf = SystemConfig.objects.filter(config_type="消息通知").first() if notify_conf.config_value == config_value: return Request.succFcun('更改通知配置成功', data=[]) else: return Request.errorFcun('更改通知配置失败', data=[])
def get_post_params(request): try: req = req_body_to_json(request) except: req = request.POST return req
def task_add(request): """ 新增任务 """ # req = request.POST # 获取参数 req = req_body_to_json(request) task_tpl_id = int(req.get("task_tpl_id", -1)) # 模板ID ip_list = req.get("exec_hosts", []) # ip列表 exec_hosts = str(ip_list) # [{'bk_host_innerip': "127.0.0.1",....}] # 主机系统 task_os = int(req.get("task_os", 0)) # 通知人列表 notify_usernames = req.get("notify_usernames", "") # exec_schedule的注释 # 1. instant 立即执行 # 2. interval 定期执行 示例: interval,2020-12-31 (表示从什么时候开始) # 3. crontab 周期执行 示例: crontab,1 (表示1天执行一次) exec_schedule = req.get("exec_schedule", 0) exec_start_time = req.get("exec_start_time", "") exec_timece = req.get("exec_timec", 0) old_task_id = int(req.get('task_id', 0)) # 数据校验 if task_tpl_id <= 0 or exec_schedule == "" or int(req.get( "biz_id", 0)) <= 0 or exec_start_time == "" or int(task_os) <= 0: return Request.errorFcun(msg="参数错误") # 查询模板 tpl = Tpl.objects.filter(id=task_tpl_id) if not tpl.exists(): return Request.errorFcun(msg="参数错误,找不到模板ID") tpl_obj = tpl.first() # # 模板的指标列表 # tpl_quota_list = eval(tpl_obj.tpl_quotas) # 根据模板iD 查询模板关联指标中间表 tpl_quota_list = CheckSystemTplQuta.objects.filter(tpl_id=tpl_obj.id).all() if len(tpl_quota_list) == 0: return Request.errorFcun(msg="参数错误,模板指标是空") fields = { 'task_name': req.get("task_name", tpl_obj.tpl_name), 'task_tpl': tpl_obj, 'task_op': request.user.username, 'task_os': task_os, 'exec_hosts': exec_hosts, 'exec_biz_id': req.get("biz_id", 0), 'exec_acc': req.get( "exec_acc", "root"), # 此处写死了root,但后期应该修改为可以配置的 因为系统可能是windows,或者有专门的系统用户执行脚本 'exec_schedule': exec_schedule, 'exec_state': 0, 'exec_progress': 0, 'exec_quota_total': len(tpl_quota_list), 'exec_start_time': exec_start_time, 'exec_timece': exec_timece, 'start_time': datetime.datetime.now() } task_obj = {} if old_task_id > 0: with transaction.atomic(): old_task_obj = Task.objects.get(pk=old_task_id) task_obj = Task.objects.filter(id=old_task_id) task_obj.update(**fields) old_task_notifys = TaskNotify.objects.filter( task_id=old_task_id).all() old_notify_username_list = [ old_task_notify.username for old_task_notify in old_task_notifys ] to_delete_notify_username_list = [] to_add_notify_username_list = [] for old_notify_username in old_notify_username_list: if old_notify_username not in notify_usernames: to_delete_notify_username_list.append(old_notify_username) for new_notify_username in notify_usernames: if new_notify_username not in old_notify_username_list: to_add_notify_username_list.append(new_notify_username) TaskNotify.objects.filter( Q(task_id=old_task_id) & Q(username__in=to_delete_notify_username_list)).delete() to_add_task_notify_list = [] for username in to_add_notify_username_list: new_task_notify = TaskNotify(task_id=old_task_id, username=username) to_add_task_notify_list.append(new_task_notify) TaskNotify.objects.bulk_create(to_add_task_notify_list) fields['start_time'] = fields['start_time'].strftime( "%Y-%m-%d %H:%M:%S") fields['end_time'] = '' fields['task_tpl'] = fields['task_tpl'].id fields['task_os'] = CheckSystemOs.objects.get(pk=task_os).os_name field_names = Log.get_model_field(Task) Log.operation_log(request, Task._meta.verbose_name, old_task_obj, update_fields=fields, operation_module_name="任务管理", method="PUT", field_names=field_names) else: # 校验任务名称是否已经存在 task_name = Task.objects.filter(task_name=req.get("task_name", '')) if len([x for x in task_name]) >= 1: return Request.errorFcun(msg="任务名重复") with transaction.atomic(): task = Task.objects.create(**fields) task_obj = Task.objects.filter(id=task.id) task_notify_list = [] for username in notify_usernames: task_notify = TaskNotify(task_id=task.id, username=username) task_notify_list.append(task_notify) TaskNotify.objects.bulk_create(task_notify_list) fields['start_time'] = fields['start_time'].strftime( "%Y-%m-%d %H:%M:%S") fields['end_time'] = '' fields['task_tpl'] = fields['task_tpl'].id fields['task_os'] = CheckSystemOs.objects.get(pk=task_os).os_name field_names = Log.get_model_field(Task) Log.operation_log(request, table_name=Task._meta.verbose_name, update_fields=fields, operation_module_name="任务管理", field_names=field_names) return Request.succFcun(data=[info.to_dict_detail() for info in task_obj])
def execute_tpl(request): """ 执行巡检模板 """ req = req_body_to_json(request) # 获取参数 tpl_id = req.get("tpl_id", 0) ip_list = req.get("ip_list", "") # 测试的设置 立即执行 exec_schedule = req.get("exec_schedule", "instant") # 数据校验 if tpl_id <= 0 or ip_list == "" or exec_schedule == "": return JsonResponse({"result": False, "message": "参数错误"}) # 查询模板 tpl = Tpl.objects.filter(id=tpl_id) if not tpl.exists(): return JsonResponse({"result": False, "message": "参数错误 找不到这个模板ID"}) tpl_obj = tpl.first() # 模板的指标列表 tpl_quota_list = eval(tpl_obj.tpl_quotas) if len(tpl_quota_list) == 0: return JsonResponse({"result": False, "message": "模板的指标是空的,请先添加模板指标"}) task_obj = Task.objects.create( task_name=tpl_obj.tpl_name, task_tpl=tpl_obj, task_op=request.user.username, exec_hosts=ip_list, exec_acc="root", # 此处写死了root,但后期应该修改为可以配置的 因为系统可能是windows,或者有专门的系统用户执行脚本 exec_schedule=exec_schedule, exec_state=0, exec_progress=0, exec_quota_total=len(tpl_quota_list), start_time=datetime.datetime.now(), # 通知部分后续考虑 notify_type="", notify_receiver="") # exec_schedule的注释 # 1. instant 立即执行 # 2. interval 定期执行 示例: interval 5 (表示5秒执行一次) # 3. crontab 周期执行 示例: crontab minute hour day_of_week day_of_month month_of_year # https://docs.celeryproject.org/en/latest/userguide/periodic-tasks.html#crontab-schedules if exec_schedule == "instant": # 模板任务立即执行 for quota in Quota.objects.filter(id__in=tpl_quota_list): task_result_obj = TaskResult.objects.create(task=task_obj, quota=quota, task_state=0, task_step_state=0) track_task_result.apply_async(args=(task_result_obj, )) elif exec_schedule.startswith("interval"): pass elif exec_schedule.startswith("crontab"): pass return JsonResponse({"result": True})
def put(self, request): req = req_body_to_json(request) tpl_id = req.get("tpl_id", '') tpl_name = req.get("tpl_name", '') tpl_os = req.get("tpl_os", '') description = req.get("description", '') quotas = req.get("quotas", '') if not all([tpl_id, tpl_name, tpl_os, len(quotas)]): return Request.errorFcun("参数异常", data=[]) tpl_obj = Tpl.objects.filter(id=tpl_id).first() if not tpl_obj: return Request.errorFcun(msg="模板不存在", data=[]) quota_objs = list() for quota in quotas: # 新添加 quota_objs.append( CheckSystemTplQuta(tpl_id=tpl_obj.id, quota_id=quota['id'], quota_threshold=str( quota['quota_threshold']))) if len(quota_objs): # 备份对象用于记录日志 old_model_obj = copy.deepcopy(tpl_obj) # 如果系统更改 tasks = list() if tpl_os != tpl_obj.tpl_os: for task in tpl_obj.task_set.all(): task.task_os = tpl_os tasks.append(task) tpl_obj.tpl_os = tpl_os tpl_obj.tpl_name = tpl_name tpl_obj.description = description try: # 下面的代码在一个事务中执行,一但出现异常,整个with函数内部的数据库操作都会回滚 with transaction.atomic(): # 删除旧系统指标 CheckSystemTplQuta.objects.filter( tpl_id=tpl_obj.id).delete() # 批量创建新系统指标 CheckSystemTplQuta.objects.bulk_create(quota_objs) if tasks: Task.objects.bulk_update(tasks, fields=["task_os"]) tpl_obj.save() dict_update_fields = { "tpl_name": tpl_name, "tpl_os": CheckSystemOs.objects.get(pk=tpl_os).os_name, "author": tpl_obj.author, "description": description, "quotas": tpl_quotas(quotas) } field_names = Log.get_model_field(Tpl) field_names['quotas'] = "巡检指标" Log.operation_log(request, Tpl._meta.verbose_name, old_model_obj, update_fields=dict_update_fields, operation_module_name="模板管理", field_names=field_names) except: logger.error( f"修改模板失败 接口名称({request.path}) 请求参数({req_body_to_json(request)})" ) return Request.succFcun(msg="修改成功", data=[]) else: return Request.errorFcun(msg="修改失败", data=[])