diff --git a/update/migrations/0021_updatecommand_comment.py b/update/migrations/0021_updatecommand_comment.py new file mode 100644 index 0000000..bd61b84 --- /dev/null +++ b/update/migrations/0021_updatecommand_comment.py @@ -0,0 +1,18 @@ +# Generated by Django 4.2.7 on 2024-01-31 10:25 + +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('update', '0020_cinema_is_cloud_cinema_remote_label'), + ] + + operations = [ + migrations.AddField( + model_name='updatecommand', + name='comment', + field=models.TextField(default='', help_text='页面显示提示', verbose_name='页面显示提示'), + ), + ] diff --git a/update/migrations/0022_updatecommand_run.py b/update/migrations/0022_updatecommand_run.py new file mode 100644 index 0000000..5ade178 --- /dev/null +++ b/update/migrations/0022_updatecommand_run.py @@ -0,0 +1,18 @@ +# Generated by Django 4.2.7 on 2024-02-01 06:42 + +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('update', '0021_updatecommand_comment'), + ] + + operations = [ + migrations.AddField( + model_name='updatecommand', + name='run', + field=models.BooleanField(default=False, help_text='在teardown前运行还是之后运行', verbose_name='在teardown前运行还是之后运行 true为之前,false为之后'), + ), + ] diff --git a/update/models.py b/update/models.py index f23700d..76cb853 100644 --- a/update/models.py +++ b/update/models.py @@ -16,8 +16,10 @@ class Cinema(BaseModels): sys_ver = models.CharField(verbose_name='鼎新系统版本', max_length=50, null=False, help_text='鼎新系统版本') client_ver = models.CharField(verbose_name='鼎新客户端版本', max_length=50, null=False, help_text='鼎新客户端版本') user = models.CharField(verbose_name='使用人', max_length=10, null=True, help_text='当前使用人') - is_cloud = models.CharField(verbose_name='是否是云版本', max_length=10, null=True, default='', help_text='是否是云版本') - remote_label = models.CharField(verbose_name='远程办公id', max_length=20, null=True, default='', help_text='远程办公id') + is_cloud = models.CharField(verbose_name='是否是云版本', max_length=10, null=True, default='', + help_text='是否是云版本') + remote_label = models.CharField(verbose_name='远程办公id', max_length=20, null=True, default='', + help_text='远程办公id') def __str__(self): return self.ip @@ -108,7 +110,9 @@ class UpdateCommand(BaseModels): is_checked = models.BooleanField(verbose_name='默认勾选', default=False, help_text='前台页面默认是否勾选') is_force = models.BooleanField(verbose_name='必选项', default=False, help_text='必选项') is_delete = models.BooleanField(verbose_name='是否有效', default=True, help_text='是否有效') - comment = models.TextField(verbose_name='页面显示提示', default='',help_text='页面显示提示') + comment = models.TextField(verbose_name='页面显示提示', default='', help_text='页面显示提示') + run = models.BooleanField(verbose_name='在teardown前运行还是之后运行 true为之前,false为之后', default=False, + help_text='在teardown前运行还是之后运行') def __str__(self): return self.desc diff --git a/update/utils/cmd_extcute.py b/update/utils/cmd_extcute.py index 92f2cb8..f59a948 100644 --- a/update/utils/cmd_extcute.py +++ b/update/utils/cmd_extcute.py @@ -53,19 +53,31 @@ class UpdateCommandUtil: Q(is_delete='0') & Q(id__in=cmd_list) & Q(process='setup')).order_by('run_num').all() checked_teardown_result = self.model.objects.filter( Q(is_delete='0') & Q(id__in=cmd_list) & Q(process='teardown')).order_by('run_num').all() - sys_cmd = [sys.command for sys in sys_result] - checked_setup_cmd = [setup.command for setup in checked_setup_result] - checked_teardown_cmd = [teardown.command for teardown in checked_teardown_result] + sys_cmd = [{'desc': sys.desc, 'cmd': sys.command} for sys in sys_result] + checked_setup_cmd = [{'desc': setup.desc, 'cmd': setup.command} for setup in checked_setup_result] + checked_teardown_cmd = [{'desc': teardown.desc, 'cmd': teardown.command} for teardown in + checked_teardown_result] return {'sys': sys_cmd, 'setup': checked_setup_cmd, 'teardown': checked_teardown_cmd} def exec_cmd(self, cinema_ip, _exec_cmd_list): self.connect(cinema_ip) + exec_output = [] for exec_cmd in _exec_cmd_list: print(exec_cmd) - stdin, stdout, stderr = self.client.exec_command(exec_cmd) - print(stdout.read().decode('utf-8')) - print(stderr.read().decode('utf-8')) + stdin, stdout, stderr = self.client.exec_command(exec_cmd['cmd']) + out = stdout.read().decode('utf-8') + err = stderr.read().decode('utf-8') + print('out', out, 'err', err) + if err == '': + if out == '': + exec_output.append(exec_cmd['desc'] + ':执行成功') + else: + exec_output.append(exec_cmd['desc'] + ':执行成功 ' + out.strip()) + else: + exec_output.append(exec_cmd['desc'] + ':执行失败 ' + err.strip()) self.disconnect() + print(exec_output) + return '\n'.join(exec_output) def exec_cmd_by_type(self, cinema_ip, _type, cmd_list, short_release): print(cinema_ip, _type, cmd_list, short_release) @@ -78,47 +90,50 @@ class UpdateCommandUtil: else: cmds = exec_cmd_data['sys'] for cmd in cmds: - if '' in cmd: - cmd = cmd.replace('', short_release) + if '' in cmd['cmd']: + cmd['cmd'] = cmd['cmd'].replace('', short_release) exec_cmd_list.append(cmd) - elif cmd.startswith(''): - cmd = cmd.replace('', '') - for c in cmd.split('|||'): - exec_cmd_list.append(c) + elif cmd['cmd'].startswith(''): + cmd['cmd'] = cmd['cmd'].replace('', '') + for c in cmd['cmd'].split('|||'): + exec_cmd_list.append({'desc': cmd['desc'], 'cmd':c}) else: exec_cmd_list.append(cmd) - self.exec_cmd(cinema_ip, exec_cmd_list) + output = self.exec_cmd(cinema_ip, exec_cmd_list) + return output # 执行设置相关 class UpdateConfigUtil: - def __init__(self, cinema_ip, checked_list): + def __init__(self, cinema_ip, checked_list, run_before_teardown): self.ip = cinema_ip self.checked_list = checked_list + self.run_before_teardown = run_before_teardown def exec_config(self): cmd_list = self.get_all_exec_cmd() db_config = Cinema.objects.filter(ip=self.ip).values()[0] - print(db_config) - print(db_config['db_user'], db_config['db_pwd']) db_conn = pymysql.Connect(host=self.ip, port=3306, user=db_config['db_user'], passwd=db_config['db_pwd'], database='cine') db_cursor = db_conn.cursor() + result_list = [] for cmds in cmd_list: - for cmd in cmds: - db_cursor.execute(cmd) + for cmd in cmds['cmd']: + r = db_cursor.execute(cmd) + print("exec_config", cmds['desc'], r) + result_list.append(cmds['desc'] + (':执行失败(设置无需修改)' if r == 0 else ':执行成功')) db_conn.commit() db_cursor.close() db_conn.close() + return '\n'.join(result_list) def get_all_exec_cmd(self): - all_config_obj = UpdateCommand.objects.filter(Q(process='config') & Q(is_delete=False)).values() - print(all_config_obj) + all_config_obj = UpdateCommand.objects.filter( + Q(process='config') & Q(run=self.run_before_teardown) & Q(is_delete=False)).values() cmd_list = [] for config_item in all_config_obj: - print(config_item) if config_item['id'] in self.checked_list: - cmd_list.append(json.loads(config_item['command'])['checked']) + cmd_list.append({"desc": config_item['desc'], "cmd": json.loads(config_item['command'])['checked']}) else: - cmd_list.append(json.loads(config_item['command'])['unchecked']) + cmd_list.append({"desc": config_item['desc'], "cmd": json.loads(config_item['command'])['unchecked']}) return cmd_list diff --git a/update/utils/db_compare.py b/update/utils/db_compare.py index b3a22c6..2e9fac7 100644 --- a/update/utils/db_compare.py +++ b/update/utils/db_compare.py @@ -138,3 +138,4 @@ class DbCompare: print('diff_result', diff_result) create_result = os.system(create_cmd) print('create_result', create_result) + return '数据库对比成功' if diff_result == 0 and create_result == 0 else '数据库对比失败' diff --git a/update/utils/git_util.py b/update/utils/git_util.py index 362ab01..63976ee 100644 --- a/update/utils/git_util.py +++ b/update/utils/git_util.py @@ -50,7 +50,7 @@ class GitUtil: # 如果cine.sql和cine_xxx_org.sql文件md5不一致,则重新拷贝cine_xxx_org.sql并生成cine_xxx.sql # 如果生成新的cine_xxx.sql则返回True,否则返回False def create_cine_sql(self): - result = self.checkout_release() + output = self.checkout_release() org_path = os.path.join(self.local_code_path, 'install', 'cine.sql') target_org_path = os.path.join(self.cine_sql_path, f'{self.db_name}_org.sql') target_path = os.path.join(self.cine_sql_path, f'{self.db_name}.sql') @@ -86,14 +86,15 @@ class GitUtil: f.close() target_file.writelines(target_lines) target_file.close() - return {'git_pull': result} + print('create_cine_sql', output) + return True # 将生成的cine.sql写入数据库 def write_cine_sql_by_mysql(self): if os.path.exists(sql_path := os.path.join(self.cine_sql_path, f'{self.db_name}.sql')): cmd = f'mysql -h{self.db_config["host"]} -P{self.db_config["port"]} -u{self.db_config["user"]} -p{self.db_config["password"]} < {sql_path}' r = os.system(cmd) - print(r) + print('write_cine_sql_by_mysql', r) # 获取数据库名称 def get_db_name(self, _release=''): @@ -111,6 +112,7 @@ class GitUtil: # 如果生成了新的文件则写库,如果sql没有变化则跳过 if self.create_cine_sql(): self.write_cine_sql_by_mysql() + return '成功' # # 获取release信息 # def get_release(self, _release=''): diff --git a/update/views.py b/update/views.py index 46a5a94..6bccd12 100644 --- a/update/views.py +++ b/update/views.py @@ -102,13 +102,15 @@ def update_cine(request): else: cmd_dict[cmd['process']] = [cmd['id']] print(cmd_dict) + + # 增加状态 update_status = { - 'git': {'result': 'success', 'msg': ''}, - 'setup': {'result': 'success', 'msg': ''}, - 'db_compare': {'result': 'success', 'msg': ''}, - 'teardown': {'result': 'success', 'msg': ''}, - 'config': {'result': 'success', 'msg': ''}, - 'client': {'result': 'success', 'msg': ''}, + 'git': {'result': '', 'msg': ''}, + 'setup': {'result': '', 'msg': ''}, + 'sql': {'result': '', 'msg': ''}, + 'teardown': {'result': '', 'msg': ''}, + 'config': {'result': '', 'msg': ''}, + 'client': {'result': '', 'msg': ''}, } short_release = req.get('version') @@ -121,41 +123,98 @@ def update_cine(request): # 获取并写入cine.sql print('获取并写入cine.sql') - git_util = GitUtil(short_release) - git_result = git_util.handle_create_cine() + try: + git_util = GitUtil(short_release) + git_output = git_util.handle_create_cine() + update_status['git']['result'] = 'success' + update_status['git']['msg'] = git_output + except Exception as e: + print('git', e) + update_status['git']['result'] = 'fail' + update_status['git']['msg'] = str(e) # 执行setup print('执行setup') - setup_list = list(set(cmd_list) & set(cmd_dict['setup'])) - update_cmd = UpdateCommandUtil() - update_cmd.exec_cmd_by_type(cinema_ip, 'setup', setup_list, short_release) + try: + setup_list = list(set(cmd_list) & set(cmd_dict['setup'])) + update_cmd = UpdateCommandUtil() + setup_output = update_cmd.exec_cmd_by_type(cinema_ip, 'setup', setup_list, short_release) + update_status['setup']['result'] = 'success' + update_status['setup']['msg'] = setup_output + except Exception as e: + print('setup', e) + update_status['setup']['result'] = 'fail' + update_status['setup']['msg'] = str(e) # 数据库对比 sql_list = list(set(cmd_list) & set(cmd_dict['sql'])) if len(sql_list) > 0: print('数据库对比') - db_compare = DbCompare(cinema_ip, short_release) - db_compare.exec_diff_sql() + try: + db_compare = DbCompare(cinema_ip, short_release) + sql_output = db_compare.exec_diff_sql() + update_status['sql']['result'] = 'success' + update_status['sql']['msg'] = sql_output + except Exception as e: + print('sql', e) + update_status['sql']['result'] = 'fail' + update_status['sql']['msg'] = str(e) + + # 修改设置 + print('执行config(teardown前)') + try: + config_list = list(set(cmd_list) & set(cmd_dict['config'])) + update_config = UpdateConfigUtil(cinema_ip, config_list, True) + config_before_output = update_config.exec_config() + update_status['config']['result'] = 'success' + update_status['config']['msg'] = config_before_output + except Exception as e: + print('config', e) + update_status['config']['result'] = 'fail' + update_status['config']['msg'] = str(e) # 执行teardown teardown_list = list(set(cmd_list) & set(cmd_dict['teardown'])) if len(teardown_list) > 0: print('执行teardown') - update_cmd.exec_cmd_by_type(cinema_ip, 'teardown', teardown_list, short_release) + try: + update_cmd = UpdateCommandUtil() + teardown_output = update_cmd.exec_cmd_by_type(cinema_ip, 'teardown', teardown_list, short_release) + update_status['teardown']['result'] = 'success' + update_status['teardown']['msg'] = '执行升级脚本:执行成功' + except Exception as e: + print('teardown', e) + update_status['teardown']['result'] = 'fail' + update_status['teardown']['msg'] = str(e) # 修改设置 - print('执行config_list') - config_list = list(set(cmd_list) & set(cmd_dict['config'])) - update_config = UpdateConfigUtil(cinema_ip, config_list) - update_config.exec_config() + print('执行config(teardown后)') + try: + config_list = list(set(cmd_list) & set(cmd_dict['config'])) + update_config = UpdateConfigUtil(cinema_ip, config_list, False) + config_after_output = update_config.exec_config() + update_status['config']['result'] = 'success' + update_status['config']['msg'] = update_status['config']['msg'] + '\n' + config_after_output + except Exception as e: + print('config', e) + update_status['config']['result'] = 'fail' + update_status['config']['msg'] = update_status['config']['msg'] + '\n' + str(e) # 传输客户端 client_list = list(set(cmd_list) & set(cmd_dict['client'])) if len(client_list) > 0: print('传输客户端') - client_release = ClientUtil() - client_release.client_process(cinema_ip, short_release) + try: + client_release = ClientUtil() + client_release.client_process(cinema_ip, short_release) + update_status['client']['result'] = 'success' + update_status['client']['msg'] = '客户端上传成功' + except Exception as e: + print('client', e) + update_status['client']['result'] = 'fail' + update_status['client']['msg'] = str(e) + print(update_status) return JsonResponse({'result': 'success', 'ip': cinema_ip})