在 Apple Silicon Mac 上如何打出 h2oGPT 一键安装器:PyInstaller 的 CPU/MPS 打包实操
【免费下载链接】h2ogptPrivate chat with local GPT with document, images, video, etc. 100% private, Apache 2.0. Supports oLLaMa, Mixtral, llama.cpp, and more. Demo: https://gpt.h2o.ai/ https://gpt-docs.h2o.ai/项目地址: https://gitcode.com/gh_mirrors/h2/h2ogpt
给 Mac 用户分发 h2oGPT 的本地大模型能力,最省心的做法是交付一个"双击即跑"的安装器:把 PyInstaller 打包的运行时、模型推理依赖和 OCR 工具链都装进一个二进制里,用户不再需要碰 conda。本文带你走通这条链路——从 conda 构建环境准备,到 llama-cpp-python 的 CPU/MPS 双版本编译,再到产物启动原理与常见坑,目标是让你在本机产出 h2ogpt-osx-m1-cpu 或 h2ogpt-osx-m1-gpu 两个可分发的 macOS 一键安装器。先泼一盆冷水:这套方案在 dev_installers/mac/ 的文档里被明确标为实验性、仍在开发中,正式分发前请先评估稳定性,必要时回退到 docs/README_MACOS.md 的手动安装流程。
出包前先备好的三样东西
- conda:构建脚本用它创建隔离环境,脚本开头会执行
command -v conda,找不到直接退出; - Mac 实体机:PyInstaller 的打包动作运行在哪个平台就只能产出哪个平台的二进制,没有交叉编译一说,所以 macOS 安装器只能在 Mac 上做;
- Tesseract 与 poppler:文档 OCR 与 PDF 文本抽取靠这两个外部工具,脚本会把 Homebrew 装好的版本整体复制进包内,最终用户无需再装。
| 前置项 | 用途 |
|---|---|
| conda | 隔离构建环境(Python 3.10 + Rust) |
| Homebrew 的 tesseract | 扫描件 OCR |
| Homebrew 的 poppler | PDF 解析(pdftotext) |
Rust 看着像个意外来客,其实不是:conda 环境里要装它,因为构建时会现场编译 llama-cpp-python 的本地扩展。CPU 版与 MPS 版(MPS 是 Apple Silicon 的 GPU 加速后端,通过 llama-cpp-python 的-DLLAMA_METAL=on编译开关启用)的差别,本质就在这一个编译参数。
一条命令出包 🚀
结论先行:默认走官方脚本 dev_installers/mac/build_mac_installer.sh。它在仓库根目录执行,环境检查、依赖安装、工具链拷贝、wheel 构建、打包全在里面,你一行都不用记。
git clone https://gitcode.com/gh_mirrors/h2/h2ogpt cd h2ogpt . ./dev_installers/mac/build_mac_installer.sh注意命令开头的.(即 source):脚本里有conda activate,它要修改的是"当前 shell"的状态,用bash script.sh方式跑会让激活发生在子进程里,等于白干。想要 MPS 加速版,只差一个环境变量:
BUILD_MPS=1 . ./dev_installers/mac/build_mac_installer.sh脚本内部干的事可以概括成一段流程:先确认 conda 可用,顺手删掉上次留下的Tesseract-OCR与poppler目录;然后删旧建新,执行conda env remove -n h2ogpt-mac再conda create -n h2ogpt-mac python=3.10 rust -y,保证每次构建从零开始可复现。接着按序安装 requirements.txt 和 langchain、PyMuPDF、Selenium/PlayWright、DocTR OCR 等五个可选依赖清单(统一用 reqs_optional/reqs_constraints.txt 做版本约束),装 weasyprint、nltk 数据;随后先卸载再重装 llama-cpp-python,用CMAKE_ARGS="-DLLAMA_METAL=off/on"加FORCE_CMAKE=1、--no-cache-dir强制按目标编译;再装 PyInstaller,并把/opt/homebrew/Cellar下的 poppler 与 tesseract 拷进项目根目录供打包。收尾动作是make clean dist(对应 Makefile 里rm -rf dist build h2ogpt.egg-info加setup.py bdist_wheel),把 wheel 装回环境,最后pyinstaller按 BUILD_MPS 开关选定 spec。
CPU/MPS 两条线只有两处分叉:
- llama-cpp-python 的
-DLLAMA_METAL取值 off 或 on; - 最终执行 h2ogpt-osx-m1-cpu.spec 还是 h2ogpt-osx-m1-gpu.spec,产物名也随之不同。
两份 spec 的打包逻辑完全一致。
需要改打包参数时:手动走一遍 PyInstaller
只有要调依赖清单、改收集配置时才值得进手动路径。思路是照着 build_mac_installer.sh 的清单自己搭环境,然后用pyi-makespec重新生成 spec:
conda create -n h2ogpt-mac python=3.10 rust -y conda activate h2ogpt-mac pyi-makespec mac_run_app.py -F --name=h2ogpt-osx-m1-cpu \ --collect-all=h2ogpt --collect-all=gradio \ --collect-all=sentencepiece --collect-all=gradio_pdf \ --collect-all=llama_cpp --collect-all=tiktoken_ext \ --collect-data=langchain --collect-data=gradio_client \ --recursive-copy-metadata=transformers \ --add-data=../../Tesseract-OCR:Tesseract-OCR --add-data=../../poppler:poppler参数不用逐个背:-F是单文件模式;--name定产物名(CPU 用 h2ogpt-osx-m1-cpu,MPS 换 h2ogpt-osx-m1-gpu);--collect-all让 h2ogpt、gradio、sentencepiece、gradio_pdf、llama_cpp、tiktoken_ext 六个库的模块和数据文件全部入包;--collect-data单独补上 langchain 与 gradio_client 的资源文件;--recursive-copy-metadata=transformers保证运行时能递归读到包元数据;--add-data把项目根下的 Tesseract-OCR、poppler 目录直接塞进包(路径相对 spec 所在的 dev_installers/mac/ 目录,所以是../../)。手动模式下这两个目录要自己从 Homebrew 拷好。
生成后打开 spec,在Analysis()里补上一段(这是整个手动流程最容易被漏掉、也最会出事故的一步):
module_collection_mode={ 'gradio' : 'py', 'gradio_pdf' : 'py', }gradio 必须按 py 源码模式收集——它内部大量动态注册与运行时导入,PyInstaller 静态分析看不见,默认按字节码收集的结果就是启动即崩。脚本第 65-84 行的注释里正好保留了这套配置,改完依赖清单后照着重新生成即可。
pyinstaller h2ogpt-osx-m1-cpu.spec产物落在dist/下。
双击之后发生了什么
入口是 dev_installers/mac/mac_run_app.py,干三件事。第一,修环境:把h2ogpt/src、h2ogpt/iterators、h2ogpt/gradio_utils等子目录逐个塞进sys.path,NLTK_DATA指向包内nltk_data,poppler/bin、poppler/lib、Tesseract-OCR拼进PATH——这样 PDF 抽取和 OCR 调用的外部命令不需要用户再装。第二,启动:调用 generate.py 的entrypoint_main(内部用 H2O_Fire 调src.gen的main),启动前设好h2ogpt_block_gradio_exit=False与h2ogpt_score_model=''两个环境变量(后者关掉评分模型省内存),CLI 参数体系照旧生效。第三,收尾:按h2ogpt_server_name/H2OGPT_SERVER_NAME(默认 localhost)与GRADIO_SERVER_PORT(默认 7860)拼出地址,webbrowser.open()自动打开浏览器,然后死循环 sleep 保活。
spec 的EXE()段开了 upx 压缩和 console(保留终端窗口看日志),codesign_identity与entitlements_file都是 None——产物未做 Apple 签名,换台机器首次运行会被 Gatekeeper 拦,正式分发前得补签名与公证。另外 spec 头部的datas里就挂着 Tesseract-OCR 与 poppler 两个目录,外加 transformers 的递归元数据,这就是"开箱能解析扫描件"的来源。
验证产物
- Finder 进
dist/,双击h2ogpt-osx-m1-cpu(或 gpu 版); - 控制台窗口会先打印 PYTHONPATH、NLTK_DATA、PATH 等调试行——排查启动失败就看这里;
- 确认 7860 端口监听、浏览器自动弹出聊天界面;
- 首次启动明显慢:单文件要先解包资源再加载模型,属正常现象;模型权重不随包分发,首次会从 Hugging Face 下载,离线环境参考 docs/README_offline.md 预置。
常见坑,每条一句话
- 方案仍是实验性的,翻车时回退 docs/README_MACOS.md 手动安装;
- 构建只能发生在 Mac 上,Linux/Windows 产出不了 macOS 安装器;
- 脚本里 poppler
24.02.0、tesseract5.3.4_1是硬编码的 Homebrew Cellar 路径,本机版本不同要先改这两行cp -R; - 模型选择建议见 docs/README_CPU.md 与 docs/README_GPU.md;
- 单文件包了完整运行时加六个核心库加 OCR 工具链,体积大,llama-cpp 的 CMake 编译也耗时,留足耐心。
快速回顾与下一步
一条source命令出 CPU 包,加BUILD_MPS=1出 MPS 包;手动路径的核心是pyi-makespec加module_collection_mode的 py 收集;产物未签名、模型需下载、Homebrew 版本路径硬编码——这三点决定它目前适合内部分发而非公开投放。下一步:先拿 CPU 版跑通一次端到端问答,再决定是否上 MPS;要对外发,先去补签名与公证流程。
【免费下载链接】h2ogptPrivate chat with local GPT with document, images, video, etc. 100% private, Apache 2.0. Supports oLLaMa, Mixtral, llama.cpp, and more. Demo: https://gpt.h2o.ai/ https://gpt-docs.h2o.ai/项目地址: https://gitcode.com/gh_mirrors/h2/h2ogpt
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考