在树莓派 5 上部署 Gemma 4 E4B 过程记录
目标
在一台树莓派 5 上部署 Gemma 4 E4B,让局域网内其他设备可以通过 IP 访问模型,并提供:
- OpenAI 兼容聊天接口
- 浏览器可直接访问的网页聊天页面
- 基于现有文本能力的文件输入支持
本次最终对外访问地址为:
- 主页面:
http://192.168.9.241/ - 手机简洁版:
http://192.168.9.241/lite.html - 原生
llama.cppWeb UI:http://192.168.9.241:8080/ - OpenAI 兼容接口:
http://192.168.9.241:8080/v1/chat/completions
设备与环境
- 设备:Raspberry Pi 5
- 系统:Debian Bookworm aarch64
- 内存:8GB
- CPU:4 核 Cortex-A76
- 存储:NVMe 系统盘
- 树莓派地址:
192.168.9.241
部署时检查到的大致资源情况:
- 可用内存约
5.4GiB - 根分区剩余空间约
24G
为什么选择这种方案
官方 Hugging Face 仓库里的 google/gemma-4-E4B / google/gemma-4-E4B-it 不是为树莓派这种 CPU-only 小内存场景直接准备的。
因此实际采用的是:
- 推理框架:
llama.cpp - 模型格式:
GGUF - 模型量化:
IQ4_XS
原因:
GGUF更适合llama.cppIQ4_XS在 8GB 内存的树莓派 5 上可运行- 比全精度或大体积量化更容易稳定部署
第一步:连上树莓派并检查系统
通过 SSH 登录树莓派,确认系统、CPU、内存、磁盘:
bash
ssh -o StrictHostKeyChecking=no pi@192.168.9.241
登录后检查:
bash
uname -a
free -h
df -h /
nproc
lscpu | sed -n '1,20p'
确认结果:
- 系统为
aarch64 - CPU 为
Cortex-A76 - 内存
7.9GiB - 根分区剩余约
24G
第二步:安装编译依赖
安装 llama.cpp 所需依赖:
bash
sudo apt-get update
sudo apt-get install -y git cmake build-essential libcurl4-openssl-dev pkg-config
第三步:获取并编译 llama.cpp
拉取源码:
bash
cd ~
git clone https://github.com/ggml-org/llama.cpp
cd llama.cpp
用 ARM CPU 优化参数编译:
bash
cmake -B build -DGGML_CURL=ON -DGGML_CPU_KLEIDIAI=ON -DCMAKE_BUILD_TYPE=Release
cmake --build build --config Release -j 4
这里开启了:
GGML_CURL=ON
用于直接从 Hugging Face 下载模型GGML_CPU_KLEIDIAI=ON
启用 ARM CPU 优化内核
编译完成后,关键可执行文件位于:
bash
~/llama.cpp/build/bin/llama-cli
~/llama.cpp/build/bin/llama-server
~/llama.cpp/build/bin/llama-bench
第四步:选择并下载模型
目标模型为:
Gemma 4 E4B Instruct
实际下载的 GGUF 量化模型为:
- 仓库:
unsloth/gemma-4-E4B-it-GGUF - 文件:
gemma-4-E4B-it-IQ4_XS.gguf
下载目录:
bash
mkdir -p ~/models/gemma4
cd ~/models/gemma4
由于直接使用 llama-cli --hf-repo 时遇到 SSL 校验失败,改用 curl 直链下载:
bash
curl -L -C - --progress-bar \
'https://huggingface.co/unsloth/gemma-4-E4B-it-GGUF/resolve/main/gemma-4-E4B-it-IQ4_XS.gguf?download=true' \
-o gemma-4-E4B-it-IQ4_XS.gguf
下载完成后文件大小约:
4.4G
第五步:本机推理冒烟测试
先用 llama-cli 做最小可用性验证:
bash
~/llama.cpp/build/bin/llama-cli \
-m ~/models/gemma4/gemma-4-E4B-it-IQ4_XS.gguf \
-c 1024 \
-ctk q4_0 \
-ctv q4_0 \
-t 4 \
-n 48 \
--temp 0.2 \
--reasoning off \
-p "你好,请用一句中文自我介绍。"
这里使用了更保守的参数:
-c 1024
将上下文控制在树莓派可承受范围-ctk q4_0 -ctv q4_0
压缩 KV cache,降低内存压力--reasoning off
避免模型输出思考内容,减少额外开销
测试结果正常,模型可以输出中文回答。
第六步:部署成常驻服务
创建 systemd 服务:
文件:
bash
/etc/systemd/system/gemma4.service
内容:
ini
[Unit]
Description=Gemma 4 E4B llama.cpp server
After=network-online.target
Wants=network-online.target
[Service]
Type=simple
User=pi
WorkingDirectory=/home/pi/models/gemma4
ExecStart=/home/pi/llama.cpp/build/bin/llama-server -m /home/pi/models/gemma4/gemma-4-E4B-it-IQ4_XS.gguf --host 0.0.0.0 --port 8080 -c 1024 -ctk q4_0 -ctv q4_0 -t 4 --reasoning off -np 1 --threads-http 1
Restart=always
RestartSec=5
[Install]
WantedBy=multi-user.target
启用并启动:
bash
sudo systemctl daemon-reload
sudo systemctl enable --now gemma4.service
检查状态:
bash
systemctl is-active gemma4.service
journalctl -u gemma4.service -n 50 --no-pager
为什么后来又加了 -np 1 --threads-http 1
在较早版本的服务参数里,llama-server 自动使用多个 slot。树莓派 5 的内存很紧,后续在文件分析和较长 prompt 场景下出现了:
Context size has been exceededfailed to find free space in the KV cache
为提高稳定性,最终改为:
-np 1
单槽运行--threads-http 1
控制 HTTP 处理线程数
这会牺牲并发,但能明显提升小内存环境的稳定性。
第七步:验证 HTTP 接口
健康检查:
bash
curl http://127.0.0.1:8080/health
应返回:
json
{"status":"ok"}
聊天接口测试:
bash
curl http://127.0.0.1:8080/v1/chat/completions \
-H 'Content-Type: application/json' \
-d '{
"model": "gemma4",
"messages": [
{"role": "user", "content": "请用一句中文介绍你自己。"}
],
"max_tokens": 48,
"temperature": 0.2
}'
验证结果正常,局域网访问测试也成功:
bash
curl http://192.168.9.241:8080/health
第八步:暴露网页聊天入口
虽然 llama-server 自带网页,但为了更方便地在浏览器和手机上访问,额外部署了 nginx 和一套轻量前端页面。
安装 nginx
bash
sudo apt-get install -y nginx
站点目录
静态页面最终放在:
bash
/var/www/gemma-web
nginx 配置
文件:
bash
/etc/nginx/sites-available/gemma-web
主要逻辑:
/提供主聊天页/lite.html提供手机简洁版/chat-api/反代文件网关服务/nas-api/反代 NAS 自动化服务/v1/反代到llama-server/health反代到模型健康检查
启用:
bash
sudo ln -sf /etc/nginx/sites-available/gemma-web /etc/nginx/sites-enabled/gemma-web
sudo nginx -t
sudo systemctl restart nginx
第九步:增加文件输入能力
由于当前运行的是文本模型,不能原生理解图片、视频、音频,因此增加了一层本地文件处理网关。
安装依赖
bash
sudo apt-get install -y python3-flask poppler-utils tesseract-ocr tesseract-ocr-chi-sim ffmpeg
文件网关功能
部署了一个 Flask 服务,负责:
- 文本文件:直接读取
- 图片:OCR 提取文字
- PDF:优先文本提取,失败后回退 OCR
- 视频:抽取元数据和首帧 OCR
- 音频:抽取元数据
服务进程:
bash
gemma-web.service
监听:
bash
127.0.0.1:8090
nginx 将 /chat-api/ 反代到该服务。
第十步:增加 NAS 自动化接口
后续又增加了一层 NAS 自动化服务,用于:
- 规划任务
- 整理文件
- 为未来的 NAS 搜索/下载/归档流程打底
服务进程:
bash
nas-automation.service
监听:
bash
127.0.0.1:8091
并通过:
bash
/nas-api/
对外暴露。
性能测试结果
使用本机聊天接口实际测得:
- Prompt 处理速度:约
9.6 tok/s - 生成速度:约
3.7 tok/s
后续某些请求中,生成速度大约在:
3.4 ~ 4.4 tok/s
之间波动。
服务进程内存占用大致观察到:
- RSS 约
4.38G
对于树莓派 5 8GB 来说,这已经接近一个可接受但偏紧的状态,因此最终选择:
- 小上下文
- 压缩 KV cache
- 单槽运行
运行中遇到的问题与处理方式
1. Hugging Face SSL 校验失败
现象:
llama-cli --hf-repo ...下载失败- 报错
SSL server verification failed
处理:
- 改用
curl -L -C -直接下载模型文件
2. 上下文超限
现象:
- 文件网关处理较长媒体元数据时,模型报
Context size has been exceeded
处理:
- 限制文件提取文本长度
- 降低
max_tokens - 调整
llama-server为单槽模式
3. nginx 500 错误
现象:
- 页面初期部署时,
nginx读取/home/pi/gemma-web失败
原因:
nginx对该目录没有访问权限
处理:
- 将页面迁移到
/var/www/gemma-web
4. 多并发 slot 导致 KV cache 紧张
现象:
- 多请求时模型服务容易因 KV cache 不足失败
处理:
-np 1 --threads-http 1
最终可用能力
树莓派上的最终能力包括:
Gemma 4 E4B本地文本问答- OpenAI 兼容 HTTP 接口
- 浏览器网页聊天
- 手机简洁版页面
- 图片 OCR / PDF 提取 / 视频元数据 / 音频元数据
- NAS 本地目录整理 API
结论
Gemma 4 E4B 可以在树莓派 5 上跑起来,但必须使用:
GGUF量化模型llama.cpp- 保守的上下文和内存参数
它适合作为:
- 局域网本地问答节点
- 轻量文档分析入口
- 小规模本地 AI 网关
但不适合作为:
- 高并发大规模知识库主机
- 重型多模态推理平台
如果目标是更完整的私有知识库、RAG、复杂检索和更大的本地模型,建议使用更强的本地硬件,例如带大显存 GPU 的主机,或类似 DGX Spark 这类更适合本地 AI 工作负载的设备。