47c6589e1d
- scripts/gen_icon.py: generates 256x256 SSH client icon (dark terminal window with >_ prompt and SSH connection nodes), outputs multi-size ICO (16-256px) + PNG - resources/icon.ico + icon.png: generated icon files - main.py: _get_icon_path() searches _MEIPASS (onefile), exe dir, source dir; sets app + window icon - build.spec: bundles icon files via datas=, sets exe icon=icon.ico - Windows taskbar will now show the custom icon instead of default PyInstaller icon
85 lines
2.4 KiB
RPMSpec
85 lines
2.4 KiB
RPMSpec
# -*- mode: python ; coding: utf-8 -*-
|
|
"""
|
|
PyInstaller spec for SSHClient
|
|
在 Windows 上构建:
|
|
pip install -r requirements.txt
|
|
pyinstaller build.spec --clean --noconfirm
|
|
产物: dist/SSHClient.exe (单文件, ~50MB)
|
|
"""
|
|
import sys
|
|
from pathlib import Path
|
|
|
|
block_cipher = None
|
|
|
|
# 项目根
|
|
ROOT = Path(SPECPATH).resolve() if 'SPECPATH' in dir() else Path('.').resolve()
|
|
|
|
# 隐式导入(PyQt5 + paramiko 有动态导入,PyInstaller 偶尔抓不全)
|
|
hiddenimports = [
|
|
"paramiko",
|
|
"cryptography",
|
|
"requests",
|
|
"psutil",
|
|
# PyQt5 子模块
|
|
"PyQt5.QtCore",
|
|
"PyQt5.QtGui",
|
|
"PyQt5.QtWidgets",
|
|
]
|
|
|
|
a = Analysis(
|
|
['main.py'],
|
|
pathex=[str(ROOT)],
|
|
binaries=[],
|
|
datas=[
|
|
('resources/icon.png', 'resources'),
|
|
('resources/icon.ico', 'resources'),
|
|
],
|
|
hiddenimports=hiddenimports,
|
|
hookspath=[],
|
|
hooksconfig={},
|
|
runtime_hooks=[],
|
|
excludes=[
|
|
# 砍掉体积
|
|
"tkinter", "matplotlib", "numpy", "pandas", "scipy",
|
|
"PyQt5.QtBluetooth", "PyQt5.QtDBus", "PyQt5.QtDesigner",
|
|
"PyQt5.QtHelp", "PyQt5.QtLocation", "PyQt5.QtMultimedia",
|
|
"PyQt5.QtMultimediaWidgets", "PyQt5.QtNetwork", "PyQt5.QtNetworkAuth",
|
|
"PyQt5.QtNfc", "PyQt5.QtOpenGL", "PyQt5.QtPositioning",
|
|
"PyQt5.QtPrintSupport", "PyQt5.QtQml", "PyQt5.QtQuick",
|
|
"PyQt5.QtQuickWidgets", "PyQt5.QtRemoteObjects", "PyQt5.QtSensors",
|
|
"PyQt5.QtSerialPort", "PyQt5.QtSql", "PyQt5.QtSvg",
|
|
"PyQt5.QtTest", "PyQt5.QtWebChannel", "PyQt5.QtWebSockets",
|
|
"PyQt5.QtXml", "PyQt5.QtXmlPatterns",
|
|
],
|
|
win_no_prefer_redirects=False,
|
|
win_private_assemblies=False,
|
|
cipher=block_cipher,
|
|
noarchive=False,
|
|
)
|
|
|
|
pyz = PYZ(a.pure, a.zipped_data, cipher=block_cipher)
|
|
|
|
# 单文件 exe(启动稍慢但分发简单);如需启动更快可改成 COLLECT + EXE
|
|
exe = EXE(
|
|
pyz,
|
|
a.scripts,
|
|
a.binaries,
|
|
a.zipfiles,
|
|
a.datas,
|
|
[],
|
|
name='SSHClient',
|
|
debug=False,
|
|
bootloader_ignore_signals=False,
|
|
strip=False,
|
|
upx=True, # 如果装了 UPX 会进一步压缩
|
|
upx_exclude=[],
|
|
runtime_tmpdir=None,
|
|
console=False, # GUI 模式不弹黑窗
|
|
disable_windowed_traceback=False,
|
|
argv_emulation=False,
|
|
target_arch=None,
|
|
codesign_identity=None,
|
|
entitlements_file=None,
|
|
icon='resources/icon.ico' if Path('resources/icon.ico').exists() else None,
|
|
)
|