ArticleReplaceBatch/deepseek-clien/clear_setup.py
2025-08-06 15:57:14 +08:00

267 lines
7.7 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#!/usr/bin/env python3
"""
完全清理环境并重新构建的脚本
"""
import os
import sys
import shutil
import glob
import subprocess
from pathlib import Path
def deep_cleanup():
"""深度清理所有相关文件"""
print("开始深度清理...")
# 要清理的目录
dirs_to_clean = [
"build", "dist", "__pycache__",
".pytest_cache", "*.egg-info"
]
# 要清理的文件模式
files_to_clean = [
"*.exe", "*.spec", "*_encrypted*",
"setup_main.py", "setup_validator.py",
"*.pyc", "*.pyo"
]
# 清理目录
for dir_pattern in dirs_to_clean:
for dir_path in glob.glob(dir_pattern):
if os.path.exists(dir_path):
print(f"删除目录: {dir_path}")
try:
shutil.rmtree(dir_path)
except Exception as e:
print(f"删除 {dir_path} 失败: {e}")
# 清理文件
for file_pattern in files_to_clean:
for file_path in glob.glob(file_pattern):
if os.path.exists(file_path):
print(f"删除文件: {file_path}")
try:
os.remove(file_path)
except Exception as e:
print(f"删除 {file_path} 失败: {e}")
# 清理Python缓存
for root, dirs, files in os.walk("."):
for dir_name in dirs[:]:
if dir_name == "__pycache__":
pycache_path = os.path.join(root, dir_name)
print(f"删除缓存: {pycache_path}")
try:
shutil.rmtree(pycache_path)
dirs.remove(dir_name)
except Exception as e:
print(f"删除缓存失败: {e}")
print("清理完成")
def create_single_file_setup(script_name, output_name, base_type="Console"):
"""创建单文件构建的setup.py"""
setup_content = f'''
import sys
from cx_Freeze import setup, Executable
# 基础构建选项
build_exe_options = {{
"packages": [
"mysql.connector", "cryptography", "uuid", "hashlib",
"datetime", "platform", "subprocess", "json",
"tempfile", "atexit", "ctypes"
],
"build_exe": "dist_{output_name.replace('.exe', '')}",
"excludes": ["unittest", "test"]
}}
# 如果是主程序添加tkinter和pyperclip
if "{script_name}" == "main.py":
build_exe_options["packages"].extend(["tkinter", "pyperclip"])
executables = [
Executable("{script_name}", base="{base_type}")
]
setup(
name="{output_name.replace('.exe', '')}",
version="1.0",
options={{"build_exe": build_exe_options}},
executables=executables
)
'''
return setup_content
def build_single_executable(script_name, output_name, base_type="Console"):
"""构建单个可执行文件"""
print(f"构建 {script_name} -> {output_name}")
# 创建临时setup文件
setup_filename = f"setup_{output_name.replace('.exe', '')}.py"
setup_content = create_single_file_setup(script_name, output_name, base_type)
try:
with open(setup_filename, "w", encoding="utf-8") as f:
f.write(setup_content)
# 运行构建
result = subprocess.run(
[sys.executable, setup_filename, "build"],
capture_output=True, text=True, cwd="."
)
success = result.returncode == 0
if success:
print(f"{output_name} 构建成功")
else:
print(f"{output_name} 构建失败:")
print(result.stderr)
return success
except Exception as e:
print(f"构建 {output_name} 时发生异常: {e}")
return False
finally:
# 清理临时文件
if os.path.exists(setup_filename):
try:
os.remove(setup_filename)
except:
pass
def organize_final_dist():
"""整理最终的发布目录"""
print("整理最终发布目录...")
final_dir = Path("dist_final")
final_dir.mkdir(exist_ok=True)
# 收集所有构建的文件
dist_dirs = [d for d in Path(".").iterdir() if d.is_dir() and d.name.startswith("dist_")]
all_files = {}
for dist_dir in dist_dirs:
for file_path in dist_dir.rglob("*"):
if file_path.is_file():
all_files[file_path.name] = file_path
# 复制文件到最终目录
for filename, filepath in all_files.items():
dest_path = final_dir / filename
if not dest_path.exists() or filename.endswith('.exe'):
try:
shutil.copy2(filepath, dest_path)
print(f"复制: {filename}")
except Exception as e:
print(f"复制 {filename} 失败: {e}")
# 重命名主程序
main_exe = final_dir / "main.exe"
target_exe = final_dir / "EXE加密工具.exe"
if main_exe.exists() and not target_exe.exists():
try:
main_exe.rename(target_exe)
print("主程序重命名为: EXE加密工具.exe")
except Exception as e:
print(f"重命名失败: {e}")
# 清理临时构建目录
for dist_dir in dist_dirs:
try:
shutil.rmtree(dist_dir)
except:
pass
print(f"最终文件已整理到: {final_dir.absolute()}")
return final_dir
def try_pyinstaller_fallback():
"""尝试使用PyInstaller作为备选方案"""
print("尝试使用PyInstaller作为备选方案...")
try:
# 检查PyInstaller是否可用
result = subprocess.run([sys.executable, "-c", "import PyInstaller"],
capture_output=True)
if result.returncode != 0:
print("PyInstaller未安装正在安装...")
subprocess.run([sys.executable, "-m", "pip", "install", "pyinstaller"],
check=True)
# 使用PyInstaller构建
commands = [
[sys.executable, "-m", "PyInstaller", "--onefile", "--windowed",
"--name=EXE加密工具", "main.py"],
[sys.executable, "-m", "PyInstaller", "--onefile", "--console",
"validator.py"]
]
for cmd in commands:
print(f"运行: {' '.join(cmd)}")
result = subprocess.run(cmd, capture_output=True, text=True)
if result.returncode != 0:
print(f"PyInstaller构建失败: {result.stderr}")
return False
print("PyInstaller构建成功文件位于 dist/ 目录")
return True
except Exception as e:
print(f"PyInstaller构建异常: {e}")
return False
def main():
"""主函数"""
print("=== EXE加密工具构建脚本 ===")
# 1. 深度清理
deep_cleanup()
# 2. 尝试使用cx_Freeze分别构建
print("\n尝试使用cx_Freeze构建...")
builds = [
("main.py", "main.exe", "Win32GUI"),
("validator.py", "validator.exe", "Console")
]
all_success = True
for script, output, base in builds:
if not build_single_executable(script, output, base):
all_success = False
break
if all_success:
final_dir = organize_final_dist()
print(f"\n✅ cx_Freeze构建成功")
print(f"📁 文件位置: {final_dir.absolute()}")
return True
# 3. 如果cx_Freeze失败尝试PyInstaller
print("\n❌ cx_Freeze构建失败尝试PyInstaller...")
deep_cleanup() # 再次清理
if try_pyinstaller_fallback():
print("\n✅ PyInstaller构建成功")
print("📁 文件位置: dist/")
return True
print("\n❌ 所有构建方法都失败了")
print("建议手动检查依赖和环境配置")
return False
if __name__ == "__main__":
success = main()
if not success:
print("失败")