# Copyright: (c) OpenSpug Organization. https://github.com/openspug/spug
# Copyright: (c) <spug.dev@gmail.com>
# Released under the AGPL-3.0 License.
from django.views.generic import View
from django.db.models import F
from django.conf import settings
from django.http.response import HttpResponseBadRequest
from django_redis import get_redis_connection
from libs import json_response, JsonParser, Argument, human_datetime, human_time, auth
from apps.deploy.models import DeployRequest
from apps.app.models import Deploy, DeployExtend2
from apps.repository.models import Repository
from apps.deploy.utils import dispatch, Helper
from apps.host.models import Host
from collections import defaultdict
from threading import Thread
from datetime import datetime
import subprocess
import json
import os
class RequestView(View):
@auth('deploy.request.view')
def get(self, request):
data, query, counter = [], {}, {}
if not request.user.is_supper:
perms = request.user.deploy_perms
query['deploy__app_id__in'] = perms['apps']
query['deploy__env_id__in'] = perms['envs']
for item in DeployRequest.objects.filter(**query).annotate(
env_id=F('deploy__env_id'),
env_name=F('deploy__env__name'),
app_id=F('deploy__app_id'),
app_name=F('deploy__app__name'),
app_host_ids=F('deploy__host_ids'),
app_extend=F('deploy__extend'),
rep_extra=F('repository__extra'),
do_by_user=F('do_by__nickname'),
approve_by_user=F('approve_by__nickname'),
created_by_user=F('created_by__nickname')):
tmp = item.to_dict()
tmp['env_id'] = item.env_id
tmp['env_name'] = item.env_name
tmp['app_id'] = item.app_id
tmp['app_name'] = item.app_name
tmp['app_extend'] = item.app_extend
tmp['host_ids'] = json.loads(item.host_ids)
tmp['fail_host_ids'] = json.loads(item.fail_host_ids)
tmp['extra'] = json.loads(item.extra) if item.extra else None
tmp['rep_extra'] = json.loads(item.rep_extra) if item.rep_extra else None
tmp['app_host_ids'] = json.loads(item.app_host_ids)
tmp['status_alias'] = item.get_status_display()
tmp['created_by_user'] = item.created_by_user
tmp['approve_by_user'] = item.approve_by_user
tmp['do_by_user'] = item.do_by_user
if item.app_extend == '1':
tmp['visible_rollback'] = item.deploy_id not in counter
counter[item.deploy_id] = True
data.append(tmp)
return json_response(data)
@auth('deploy.request.del')
def delete(self, request):
form, error = JsonParser(
Argument('id', type=int, required=False),
Argument('mode', filter=lambda x: x in ('count', 'expire', 'deploy'), required=False, help='参数错误'),
Argument('value', required=False),
).parse(request.GET)
if error is None:
if form.id:
deploy = DeployRequest.objects.filter(pk=form.id).first()
if not deploy or deploy.status not in ('0', '1', '-1'):
return json_response(error='未找到指定发布申请或当前状态不允许删除')
deploy.delete()
return json_response()
count = 0
if form.mode == 'count':
if not str(form.value).isdigit() or int(form.value) < 1:
return json_response(error='请输入正确的保留数量')
counter, form.value = defaultdict(int), int(form.value)
for item in DeployRequest.objects.all():
counter[item.deploy_id] += 1
if counter[item.deploy_id] > form.value:
count += 1
item.delete()
elif form.mode == 'expire':
for item in DeployRequest.objects.filter(created_at__lt=form.value):
count += 1
item.delete()
elif form.mode == 'deploy':
app_id, env_id = str(form.value).split(',')
for item in DeployRequest.objects.filter(deploy__app_id=app_id, deploy__env_id=env_id):
count += 1
item.delete()
return json_response(count)
return json_response(error=error)
class RequestDetailView(View):
@auth('deploy.request.view')
def get(self, request, r_id):
req = DeployRequest.objects.filter(pk=r_id).first()
if not req:
return json_response(error='未找到指定发布申请')
hosts = Host.objects.filter(id__in=json.loads(req.host_ids))
outputs = {x.id: {'id': x.id, 'title': x.name, 'data': f'{human_time()} 读取数据... '} for x in hosts}
response = {'outputs': outputs, 'status': req.status}
if req.is_quick_deploy:
outputs['local'] = {'id': 'local', 'data': ''}
if req.deploy.extend == '2':
outputs['local'] = {'id': 'local', 'data': f'{human_time()} 读取数据... '}
response['s_actions'] = json.loads(req.deploy.extend_obj.server_actions)
response['h_actions'] = json.loads(req.deploy.extend_obj.host_actions)
if not response['h_actions']:
response['outputs'] = {'local': outputs['local']}
rds, key, counter = get_redis_connection(), f'{settings.REQUEST_KEY}:{r_id}', 0
data = rds.lrange(key, counter, counter + 9)
while data:
for item in data:
counter += 1
item = json.loads(item.decode())
if item['key'] in outputs:
if 'data' in item:
outputs[item['key']]['data'] += item['data']
if 'step' in item:
outputs[item['key']]['step'] = item['step']
if 'status' in item:
outputs[item['key']]['status'] = item['status']
data = rds.lrange(key, counter, counter + 9)
response['index'] = counter
if counter == 0:
for item in outputs:
outputs[item]['data'] += '\r\n\r\n未读取到数据,Spug 仅保存最近2周的日志信息。'
if req.is_quick_deploy:
if outputs['local']['data']:
outputs['local']['data'] = f'{human_time()} 读取数据... ' + outputs['local']['data']
else:
outputs['local'].update(step=100, data=f'{human_time()} 已构建完成忽略执行。')
return json_response(response)
@auth('deploy.request.do')
def post(self, request, r_id):
form, _ = JsonParser(Argument('mode', default='all')).parse(request.body)
query = {'pk': r_id}
if not request.user.is_supper:
perms = request.user.deploy_perms
query['deploy__app_id__in'] = perms['apps']
query['deploy__env_id__in'] = perms['envs']
req = DeployRequest.objects.filter(**query).first()
if not req:
return json_response(error='未找到指定发布申请')
if req.status not in ('1', '-3'):
return json_response(error='该申请单当前状态还不能执行发布')
host_ids = req.fail_host_ids if form.mode == 'fail' else req.host_ids
hosts = Host.objects.filter(id__in=json.loads(host_ids))
message = f'{human_time()} 等待调度... '
outputs = {x.id: {'id': x.id, 'title': x.name, 'step': 0, 'data': message} for x in hosts}
req.status = '2'
req.do_at = human_datetime()
req.do_by = request.user
req.save()
Thread(target=dispatch, args=(req, form.mode == 'fail')).start()
if req.is_quick_deploy:
if req.repository_id:
没有合适的资源?快使用搜索试试~ 我知道了~
开源运维平台:面向中小型企业设计的无 Agent的自动化运维平台,整合了主机管理、主机批量执行、主机在线终端、等一系列功能
共387个文件
js:186个
py:118个
png:22个
1.该资源内容由用户上传,如若侵权请联系客服进行举报
2.虚拟产品一经售出概不退款(资源遇到问题,请及时私信上传者)
2.虚拟产品一经售出概不退款(资源遇到问题,请及时私信上传者)
版权申诉
0 下载量 69 浏览量
2024-09-10
14:56:47
上传
评论
收藏 585KB ZIP 举报
温馨提示
开源运维平台:面向中小型企业设计的无 Agent的自动化运维平台,整合了主机管理、主机批量执行、主机在线终端、文件在线上传下载、应用发布、任务计划、配置中心、监控、报警等一系列功能。
资源推荐
资源详情
资源评论
收起资源包目录
开源运维平台:面向中小型企业设计的无 Agent的自动化运维平台,整合了主机管理、主机批量执行、主机在线终端、等一系列功能 (387个子文件)
redis.conf 46KB
nginx.conf 2KB
index.module.css 2KB
index.module.css 1KB
login.module.css 1KB
index.module.css 579B
libs.module.css 569B
index.module.css 452B
index.module.css 380B
index.module.css 356B
index.module.css 186B
Dockerfile 1KB
.gitignore 318B
.gitignore 87B
.gitignore 8B
.gitkeep 0B
.gitkeep 0B
.gitkeep 0B
.gitkeep 0B
index.html 2KB
favicon.ico 9KB
spug.ini 1KB
supervisor-spug.ini 854B
init_spug 151B
Detail.js 11KB
Ext2Setup2.js 10KB
Ext1Form.js 10KB
index.js 10KB
FileManager.js 9KB
Table.js 8KB
Group.js 7KB
Ext2Console.js 7KB
Selector.js 7KB
Ext1Console.js 7KB
Step1.js 7KB
Form.js 7KB
index.js 7KB
index.js 6KB
Table.js 6KB
TableCard.js 6KB
Step1.js 6KB
Step3.js 6KB
Table.js 6KB
Output.js 5KB
Form.js 5KB
PushSetting.js 5KB
index.js 5KB
Output.js 5KB
Form.js 5KB
Ext1Setup1.js 5KB
Ext2Form.js 5KB
Notice.js 5KB
index.js 5KB
serviceWorker.js 5KB
CloudImport.js 5KB
SecuritySetting.js 5KB
AutoDeploy.js 5KB
Ext2Setup1.js 5KB
Table.js 5KB
routes.js 5KB
Step2.js 5KB
codes.js 5KB
store.js 5KB
NavForm.js 4KB
MonitorCard.js 4KB
Notification.js 4KB
BatchDelete.js 4KB
Console.js 4KB
Table.js 4KB
store.js 4KB
Ext1Setup3.js 4KB
Setting.js 4KB
Import.js 4KB
DeployPerm.js 4KB
Repo.js 4KB
Ext1Setup2.js 4KB
index.js 4KB
Table.js 4KB
Table.js 4KB
DiffConfig.js 4KB
Rollback.js 4KB
Form.js 3KB
AppSelector.js 3KB
PagePerm.js 3KB
Nav.js 3KB
Form.js 3KB
Form.js 3KB
Parameter.js 3KB
Detail.js 3KB
About.js 3KB
Terminal.js 3KB
functools.js 3KB
Rel.js 3KB
AlarmSetting.js 3KB
TemplateSelector.js 3KB
HostSelector.js 3KB
TableView.js 3KB
KeySetting.js 3KB
Table.js 3KB
themes.js 3KB
共 387 条
- 1
- 2
- 3
- 4
资源评论
Java程序员-张凯
- 粉丝: 1w+
- 资源: 7154
下载权益
C知道特权
VIP文章
课程特权
开通VIP
上传资源 快速赚钱
- 我的内容管理 展开
- 我的资源 快来上传第一个资源
- 我的收益 登录查看自己的收益
- 我的积分 登录查看自己的积分
- 我的C币 登录后查看C币余额
- 我的收藏
- 我的下载
- 下载帮助
最新资源
- 光伏储能同步发电机VSG并网仿真模型C 光伏阵列搭建的光伏电池模型 光伏:采用扰动观察法最大功率点MPPT跟踪控制 储能:蓄电池
- 光伏MPPT同步发电机(VSG)并网仿真模型 结构:前级光伏板采用扰动观察法最大功率跟踪给定值,然后将该功率通过直流母线电容电压
- 淘小说 10.0.2会员版_暗影.apk
- 基于Java、CSS、JavaScript的菜谱制作与展示设计源码
- 带负载转矩前馈补偿的永磁同步电机无感FOC 1.采用龙伯格负载转矩观测器,可快速准确观测到负载转矩; 2.将观测到的负载转矩用作
- 基于Java语言的学习实践项目设计源码
- 基于Java语言的文件共享与AES加密的Web端设计源码
- 基于Html和JavaScript的图片展示设计源码
- 基于Python开发的智慧养老系统算法端设计源码
- 基于Python和CSS的Chrome插件英雄榜中文说明书设计源码
资源上传下载、课程学习等过程中有任何疑问或建议,欢迎提出宝贵意见哦~我们会及时处理!
点击此处反馈
安全验证
文档复制为VIP权益,开通VIP直接复制
信息提交成功