安全边界
PPX 把本地 Python 能力开放给 Web 页面,因此安全不能只依赖“这是桌面应用”。本章说明当前框架已经提供的保护、仍由应用开发者负责的部分,以及发布前必须验证的事项。
威胁模型
需要重点防范:
- 页面调用了原本不打算暴露的 Python 方法。
- 恶意或被篡改的更新清单引导安装错误依赖。
- 安装包下载不完整或被替换。
- 框架更新覆盖业务代码。
- RPC 错误把本机路径、密钥或堆栈泄露给页面。
- 应用把不可信 URL、路径或命令直接交给系统执行。
PPX 不能代替应用自身的权限设计。前端页面与 Python 运行在同一个桌面应用信任域内,但远程内容、用户输入和外部 API 返回值仍然是不可信数据。
API 暴露采用白名单
pywebview 只接收 Bridge,并不会自动暴露业务对象。业务方法必须使用包含命名空间的 @api_method("namespace.method");ppx-py 只扫描 python.modules 声明模块中的这些白名单函数。
建议:
- 只暴露完成一个业务动作所需的最小方法。
- 在 Python 端验证类型、长度、路径范围和当前用户权限。
- 不提供“执行任意命令”“导入任意模块”或“读取任意文件”一类通用接口。
- 不把数据库口令、访问令牌和完整异常堆栈返回给页面。
- 对修改数据、删除文件和网络提交等操作增加业务确认与审计。
命名重复会在启动注册阶段报错,避免后注册的方法静默替换已有实现。
RPC 错误边界
可预期的 BridgeError 会返回受控错误码和消息;未知异常只向页面返回 INTERNAL_ERROR。完整异常由 Python 日志记录。发布版本应妥善存放日志,并在日志中清理敏感字段。
requestId 用于关联两端记录,但它不是身份凭证,也不能用于授权。
JavaScript 事件注入保护
Python 主动事件通过 json.dumps 序列化事件名与数据。默认 ASCII 转义也保护 U+2028/U+2029 等 JavaScript 分隔字符。传入的数据必须可 JSON 序列化;不要把任意 Python 对象交给事件接口。
文件和 URL 打开能力
内置 system.openPath 可以打开 HTTP(S) URL 或本机路径。这是有实际权限的系统能力:
- 不要把来自远程页面或未经校验的字符串直接传入。
- 如需限定工作目录,应在业务 API 中解析并验证路径属于允许的根目录。
- 对 URL 建议维护协议和域名白名单。
- PPX 内置实现不执行 shell 字符串,但打开目标仍可能触发系统注册的外部程序。
文件选择对话框由用户主动选择,仍应在 Python 端校验扩展名和实际文件内容。
框架更新保护
ppx update 的保护包括:
- 只接受同一主版本(6.x)内的目标版本,拒绝降级。
- 更新通道必须与项目配置相同。
- 更新清单必须包含完整兼容字段和两个包版本。
- Release 版本必须与清单版本相同。
- 清单内容必须匹配 GitHub Release API 提供的 SHA-256 digest。
- Python 依赖使用精确版本并要求 wheel;pnpm 依赖使用精确版本且禁止安装脚本。
- 更新前后比较
api/、gui/src/、ppx/assets/的 SHA-256 文件树。 - 更新失败时恢复更新器直接管理的文件,并尝试恢复旧依赖。
保护范围不等于完整事务。包管理器、网络和系统进程可能在任意时刻失败,因此执行更新前仍应提交代码或备份项目,并先运行 --dry-run。
用户数据保护
内置 JSON 存储使用应用数据目录和原子替换写入。框架更新不扫描或修改该目录。
应用开发者仍需负责:
- 敏感数据加密以及密钥的系统安全存储。
- 数据结构升级和回滚策略。
- 大文件、并发写入和多进程场景改用合适数据库。
- 备份、恢复、数据导出和用户删除机制。
dataSchema 是更新兼容契约,不会自动执行数据库迁移。
成品应用下载的边界
applicationUpdate.download 会:
- 按当前系统和 CPU 架构选择候选安装包。
- 拒绝包含目录分隔符的不安全文件名。
- 要求 GitHub 资源提供合法 SHA-256 digest。
- 写入
.part,校验摘要后再原子替换下载文件。 - 在取消、超时和失败时删除临时文件。
它不会验证操作系统代码签名,也不会自动静默安装。正式发布还应完成:
- Windows Authenticode 签名与安装器发布者验证。
- macOS Developer ID 签名、公证和 Gatekeeper 验证。
- Linux 仓库签名或明确的包来源与校验流程。
- 安装后启动健康检查和失败回滚。
在这些能力完整之前,应准确描述为“一键检查、安全下载并打开安装包”,不能宣称完全无感升级。
Web 内容策略
正式应用默认加载随安装包发布的静态前端。若应用改为加载远程页面,远程站点将能够调用暴露的桌面 API,风险显著增加。除非已经实现来源校验、内容安全策略、证书和权限隔离,否则不要把任意远程 URL 作为主窗口页面。
前端依赖和 Python 依赖都应使用锁文件、自动化漏洞检查和可信发布账号。发布到 PyPI/npm 后,同一版本不能覆盖;发现问题时应撤回或弃用错误版本并发布补丁版本。
发布前安全清单
ppx doctor全部通过。- Python、Bridge 和前端测试全部通过。
- 三端安装包在真实系统安装、启动和卸载。
- 安装包签名、公证和发布者信息正确。
- RPC 白名单中没有调试接口或通用命令执行接口。
- 更新地址指向自己的应用仓库,不是 PPX 框架仓库。
- 更新清单及安装包 digest 可用。
- 用户数据升级、备份和回滚经过测试。
- 日志、错误提示和 Release 附件不包含密钥。