# -*- coding: utf-8 -*- # @Time : 2019/8/24 17:58 # @Author : ricky # @File : main.py # @Software: vscode """主界面""" import sys import os import subprocess import threading import zipfile import datetime import wx import wx.adv import ui from . import main_frame as frame from loguru import logger from constant import constant from spider import upgradespider from utils import configini from utils import path from core import alterparam from core import ruoyi from core import ruoyicloud from core import ruoyifast from core import ruoyivue import platform class TaskThread(threading.Thread): def __init__(self, parent, select_file_path, alter_param: alterparam.AlterParam, rbm_index): """ :param parent: 主线程UI """ super(TaskThread, self).__init__() self.parent = parent self.select_file_path = select_file_path alter_param.context = self self.alter_param = alter_param self.rbm_index = rbm_index self.setDaemon(True) def show_operate_log(self, log): """ 统一显示日志到控件 参数: self (object): 当前对象 log (str): 日志内容 """ # 这里要在主线程更新UI,否则会报错 wx.CallAfter(self.parent.receive_call_after, log + '\n') def run(self): wx.CallAfter(self.parent.task_start) self.show_operate_log('正在检测文件...') select_dir_path = os.path.dirname(self.select_file_path) # 目标目录 target_dir = os.path.join( select_dir_path, datetime.datetime.now().strftime('%Y%m%d%H%M%S')) # 记录输出目录 globals()['output_directory'] = target_dir # 解压到指定的文件夹 with zipfile.ZipFile(self.select_file_path, 'r') as zip_file: zip_file.extractall(target_dir) self.show_operate_log('输出目录:' + target_dir) self.show_operate_log('解压完成,正在修改文件请稍后...') # 读取配置文件 config_dict = configini.Config().get_dict() # 读取模板配置文件 template_config_path = path.resource_path('template_config.ini') if not os.path.exists(template_config_path): template_config_path = path.resource_path( os.path.join('conf', 'template_config.ini')) template_dict = configini.Config(template_config_path).get_dict() # 实例化核心修改类 self.alter_param.targetdir = target_dir if self.rbm_index == 0: ry = ruoyi.RuoYi(self.alter_param, config_dict, template_dict, self.show_operate_log) elif self.rbm_index == 1: ry = ruoyivue.RuoYiVue( self.alter_param, config_dict, template_dict, self.show_operate_log) elif self.rbm_index == 2: ry = ruoyifast.RuoYiFast( self.alter_param, config_dict, template_dict, self.show_operate_log) elif self.rbm_index == 3: ry = ruoyicloud.RuoYiCloud( self.alter_param, config_dict, template_dict, self.show_operate_log) try: # 开始修改 ry.start() except Exception as error: self.show_operate_log('-------------------\n\r') self.show_operate_log('修改发生异常:\n{}'.format(error)) self.show_operate_log('\r----------------------') logger.error('修改发生异常:{}', error) finally: self.parent.task_finally() logger.info('修改完成,输出目录:{}', target_dir) self.show_operate_log('输出目录:' + target_dir) self.show_operate_log('任务结束!') class Main(frame.MainFrame): def __init__(self, parent): frame.MainFrame.__init__(self, parent) app_name = wx.GetApp().GetAppName() if app_name != 'run' and platform.system().lower().startswith('win'): icon = wx.Icon(f'{app_name}.exe', wx.BITMAP_TYPE_ICO) self.SetIcon(icon) self.m_filePicker.GetPickerCtrl().SetLabel('选择文件') self.m_filePicker.GetTextCtrl().SetHint('请选择从官网下载下来的“.zip”后缀的压缩文件') self.m_text_ctrl_project_dir_name.SetHint('请输入目录名称') self.m_text_ctrl_project_name.SetHint('请输入项目名称') self.m_text_ctrl_package_name.SetHint('请输入包名') self.m_text_ctrl_artifact_id.SetHint('请输入artifactId') self.m_text_ctrl_group_id.SetHint('请输入groupId') self.m_text_ctrl_site_name.SetHint('请输入站点名称') self.m_statusbar.SetFieldsCount(4) # 状态栏分成4个区域 # self.m_statusbar.SetStatusWidths([-5,-2]) #区域宽度比列,用负数 self.m_statusbar.SetStatusText(' 软件版本:' + constant.APP_VERSION_STRING, 0) self.m_statusbar.SetStatusText( ' Python版本:' + constant.PYTHON_VERSION_STRING, 1) self.m_statusbar.SetStatusText( ' WxPython版本:' + constant.WXPYTHON_VERSION_STRING, 2) self.m_statusbar.SetStatusText(' 联系作者(RICKY):QQ11748854', 3) self.Centre() def task_start(self): """ 任务开始 """ self.m_text_log.Clear() # 禁用按钮 self.m_btn_start.Disable() self.m_btn_clear.Disable() self.m_btn_open_output_directory.Disable() def task_finally(self): """ 任务结束 """ self.m_btn_open_output_directory.Enable() # 启用按钮 self.m_btn_start.Enable() self.m_btn_clear.Enable() def show_message(self, message): """ 统一显示对话框 参数: message (str): 对话框内容 """ wx.MessageDialog(self, message, '操作提醒', wx.OK).ShowModal() def receive_call_after(self, message): """ 接收子线程传递消息,刷新UI线程 参数: self (object): 当前对象 message (str): 日志内容 """ self.m_text_log.AppendText(message) self.m_text_log.ShowPosition(self.m_text_log.GetLastPosition()) def upgrade_call_after(self, is_new_version, show_no_new_version_tip, title=None, message=None): """ 接收更新程序线程传递消息,弹窗提示框 参数: self (object): 当前对象 is_new_version (bool): 是否是新版本 show_no_new_version_tip (bool): 是否显示提示 title (str): 标题 message (str): 消息 """ if is_new_version: logger.info('检查更新结果:发现新的版本-{}', title) dlg = wx.GenericMessageDialog( self, '新版本:%s\n\n更新日志:\n%s' % (title, message), '版本更新提醒', wx.OK | wx.CANCEL) dlg.SetOKCancelLabels('前往升级', '忽略更新') if dlg.ShowModal() == wx.ID_OK: wx.LaunchDefaultBrowser( 'https://gitee.com/lpf_project/RuoYi-MT/releases') dlg.Destroy() else: logger.info('检查更新结果:当前版本是最新版本!') if show_no_new_version_tip: wx.MessageDialog(self, '当前版本是最新版本!', '检测更新', wx.OK).ShowModal() def check_input(self): """ 校验输入框 参数: self (object): 当前对象 Return: 提示消息,校验通过返回'' """ message = '' # 验证输入框是否有值 if len(self.m_text_ctrl_project_dir_name.GetValue()) == 0: message = '请填写目录名称' if len(self.m_text_ctrl_project_name.GetValue()) == 0: message = '请填写项目名' if len(self.m_text_ctrl_package_name.GetValue()) == 0: message = '请填写包名' if len(self.m_text_ctrl_artifact_id.GetValue()) == 0: message = '请填写artifactId' if len(self.m_text_ctrl_group_id.GetValue()) == 0: message = '请填写groupId' if len(self.m_text_ctrl_site_name.GetValue()) == 0: message = '请填写站点名称' return message # 实现开始执行按钮的事件 def OnClickEventStart(self, event): select_file_path = self.m_filePicker.GetPath() if len(select_file_path) == 0: self.show_message('请选择文件') return if select_file_path.endswith('.zip') is False: self.show_message('请选择标准的.zip文件') return if os.path.exists(select_file_path) is False: self.show_message('请选择有效的.zip文件') return message = self.check_input() if len(message) != 0: self.show_message(message) return dlg = wx.MessageDialog(None, '确认开始执行吗?', '操作提醒', wx.YES_NO) if dlg.ShowModal() == wx.ID_YES: dlg.Destroy() # 构造参数 params = alterparam.AlterParam() params.sitename = self.m_text_ctrl_site_name.GetValue() params.projectdirname = self.m_text_ctrl_project_dir_name.GetValue() params.packagename = self.m_text_ctrl_package_name.GetValue() params.projectname = self.m_text_ctrl_project_name.GetValue() params.artifactid = self.m_text_ctrl_artifact_id.GetValue() params.groupid = self.m_text_ctrl_group_id.GetValue() rbm_index = self.m_radio_box_mode.GetSelection() t = TaskThread(self, select_file_path, params, rbm_index) t.start() # 实现退出菜单事件 def OnMenuClickEventExit(self, event): dlg = wx.MessageDialog(self, '确认退出程序吗?', '退出提醒', wx.YES_NO) dlg.SetYesNoLabels('退出', '取消') if dlg.ShowModal() == wx.ID_YES: self.Destroy() dlg.Destroy() def OnMenuClickEventConfig(self, event): dlg = ui.config.config.Config(self) dlg.ShowModal() dlg.Destroy() def OnMenuClickEventTemplateConfig(self, event): dlg = ui.config.templateConfig.TemplateConfig(self) dlg.ShowModal() dlg.Destroy() # 实现清空按钮的事件 def OnClickEventClear(self, event): self.m_filePicker.SetPath('') self.m_text_ctrl_project_dir_name.SetValue('') self.m_text_ctrl_project_name.SetValue('') self.m_text_ctrl_package_name.SetValue('') self.m_text_ctrl_artifact_id.SetValue('') self.m_text_ctrl_group_id.SetValue('') self.m_text_ctrl_site_name.SetValue('') self.m_text_log.SetValue('') self.m_btn_open_output_directory.Disable() self.m_radio_box_mode.SetSelection(0) # 实现打开输出目录按钮的事件 def OnClickEventOpenOutputDirectory(self, event): directory = globals()['output_directory'] try: os.startfile(directory) except: subprocess.Popen(['open', directory]) # 实现打赏作者事件 def OnMenuClickEventReward(self, event): dlg = ui.reward.Reward(self) dlg.ShowModal() dlg.Destroy() # 实现druid秘钥生成事件 def OnMenuClickEventDruidEncrypt(self, event): dlg = ui.druidencrypt.DruidEncrypt(self) dlg.ShowModal() dlg.Destroy() # 实现批量删除文件事件 def OnMenuClickEventDeleteFile(self, event): dlg = ui.filedel.FileDel(self) dlg.ShowModal() dlg.Destroy() # 实现关于事件 def OnAbout(self, event): dlg = ui.about.About(self) dlg.ShowModal() dlg.Destroy() # 实现检测更新事件 def OnUpgrade(self, event): t = upgradespider.UpgradeThread(self, True) t.start() # 实现使用指南事件 def OnManual(self, event): dlg = ui.manual.Manual(self) dlg.ShowModal() dlg.Destroy() # 实现打开程序目录事件 def OnOpenAppDir(self, event): dir = path.resource_path('') try: os.startfile(dir) except: subprocess.Popen(['open', dir])