Deployment
Running Minara Agent in Docker and other production environments
Minara Agent is designed to deploy as a single container with one mounted volume for state. This page explains the Docker image, the common deployment shapes, and the knobs you'll want to tune in production.
The Dockerfile
Dockerfile is a multi-stage build:
- Stage 1:
builder.node:24-slimpluspython3 / make / g++for compilingbetter-sqlite3's native addon. Installs deps, type-checks, and emitsdist/viatsc. - Stage 2:
runtime.node:24-slimwith just the builtdist/,package.json, andnode_modules/copied from the builder. Drops to the non-rootnodeuser and exposes port8080.
最终镜像不包含 TypeScript 源码、测试套件或构建工具链。 大小约为 300 MB(未压缩),取决于 pnpm 锁定文件。
数据目录
MINARA_DATA_DIR=/data所有可变状态都存放在此目录下:
/data
├── minara.db ← SQLite (WAL)
├── minara.db-wal
├── minara.db-shm
├── logs/ ← 按天轮转的 NDJSON
├── sandbox/files/ ← 沙盒用户文件
├── workspace/ ← SOUL.md / AGENTS.md / 等
├── env ← 保存的 `minara config set model.defaultModel` / `minara auth messaging add`
└── auth/ ← 加密的身份验证配置文件将 /data 挂载为卷。容器中的其他所有内容都是不可变的。
没有卷的 docker run --rm 仍可用于临时实验,但退出时会丢失状态。
常见部署形式
1. 容器中的交互式 REPL
docker run --rm -it \
-v minara-data:/data \
-e ANTHROPIC_API_KEY=sk-... \
-e MINARA_API_KEY=... \
minara默认 CMD 运行 dist/gateway/cli.js,进入 REPL。
用于对生产镜像进行本地测试。
2. HTTP 网关服务
docker run -d --name minara \
-v minara-data:/data \
-p 127.0.0.1:8080:8080 \
-e ANTHROPIC_API_KEY=sk-... \
-e MINARA_API_KEY=... \
minara \
node dist/gateway/server.js用 node dist/gateway/server.js 覆盖 CMD 以运行 HTTP 网关而非 REPL。
Dockerfile 中的健康检查已探测端口 8080 的 /healthz,
Docker/Kubernetes 可直接使用。
将网关暴露到 localhost 之外
网关驱动涉及资金的端点,因此绑定到非本地回环地址时必须进行身份验证。 将端口发布到网络接口之前,请先设置 token:
export GATEWAY_AUTH_TOKEN=$(openssl rand -hex 32)此后每个请求都必须携带 Authorization: Bearer $GATEWAY_AUTH_TOKEN。
面向互联网的服务请在前面部署带 TLS 的反向代理。
若在非回环绑定下未设置 token,网关将拒绝启动(交互模式)或自动生成 token(Docker/CI 模式,写入
<dataDir>/gateway-token)。
3. 在同一数据目录上运行 CLI 和网关
将网关作为长期运行的服务,同时针对相同数据目录打开一次性 REPL 进行交互式调试:
docker run --rm -it \
-v minara-data:/data \
-e ANTHROPIC_API_KEY=sk-... \
minara \
node dist/gateway/cli.js两个进程读写同一 SQLite 文件。WAL 模式意味着并发读不会相互阻塞, 但两个进程同时写入仍是坏主意。 附加到运行中的网关时,将 REPL 视为主要用于读取的调试器。
4. 仅 Autopilot 部署
docker run -d \
-v minara-data:/data \
-e ANTHROPIC_API_KEY=sk-... \
-e MINARA_API_KEY=... \
-e MINARA_AUTOPILOT_ENABLED=true \
-e MINARA_DAILY_CAP_USD=500 \
-e MINARA_AUTOPILOT_CAP_USD=50 \
minara \
node dist/gateway/server.js启用 Autopilot 时,HTTP 网关在启动时引导 Autopilot 运行时。 这些限额强制实施硬上限,LLM 无法突破。
环境变量
最低要求:
ANTHROPIC_API_KEY(或OPENROUTER_API_KEY等)用于 LLM 提供商。MINARA_API_KEY用于 Minara 交易后端,除非使用交互式设备登录流程。
生产环境中强烈推荐:
MINARA_DAILY_CAP_USD:每日支出硬上限。MINARA_PER_TX_MAX_USD:每笔交易硬上限。MINARA_DATA_DIR=/data:显式固定数据目录 (避免镜像默认值变更时出现意外)。LOG_LEVEL=info:debug较安全但日志量会增加约 4 倍。
详见 环境变量。
密钥
不要将密钥烘焙到镜像中。Dockerfile 的所有内容都可以公开发布; 所有凭证在运行时通过环境变量或绑定挂载的文件传入。
对于 Kubernetes:使用挂载为环境变量的 Secret 资源。
对于 Docker Compose:使用指向镜像外 .env 文件的 env_file。
对于普通 Docker:从主机环境使用 -e KEY=value。
tools/_shared/result.ts 中的掩码器会在审计日志中隐藏已知敏感密钥。
就算密钥出现在工具参数中,也不会被持久化到磁盘。
这是纵深防御措施,请勿完全依赖。
切勿将密钥放入镜像。
健康检查
镜像包含内置 HEALTHCHECK,探测端口 8080 上的 /healthz。
在以下情况下端点返回 200:
- SQLite 文件可以打开。
- LLM 提供商已解析凭证。
- 工具注册表至少注册了一个工具。
如需更深入的检查,改为查询 /status。
它返回数据库统计、技能计数、活跃触发器计数和上次成功 LLM 调用的时间戳。
升级
两种选择:
- 替换容器。
docker pull minara:latest,停止旧容器, 用相同卷启动新容器。apps/agent/src/platform/db.ts中的模式迁移是幂等的, 在启动时运行,数据得以保留。 - 通过 CLI 自更新。 在容器内运行
minara update检测安装路径并调用适当的升级流程。 用于长期运行的个人部署;对于由编排器管理生命周期的生产环境不太适用。
跨主版本升级前始终备份:
docker exec minara \
sqlite3 /data/minara.db ".backup '/data/backups/minara-pre-upgrade.db'"水平扩展
Minara 设计用于单节点操作。SQLite 是瓶颈:同一时刻只有一个写入者。 对于水平扩展的 HTTP 网关,有两种选择:
- 一个节点拥有状态,其他节点代理。 运行单个"状态"容器 包含 SQLite 卷,副本将写入操作转发到它。读可直接命中副本。
- 切换到 Postgres。
apps/agent/src/storage/下的存储层足够精细,迁移到 Postgres 是可行的,但尚无人实现。 如需此功能,请提交 issue。
实际上大多数部署都是单节点的。package.json 中的 Redis 代码路径
用于水平扩展时的可选分布式锁定,但不是启动时必需项。
可观测性
容器日志是 stdout 上的 NDJSON。直接将其管道到日志聚合器:
docker logs minara | vector --config vector.toml对于 Prometheus 风格指标,抓取 /status 并解析 JSON 响应。
目前没有专用 /metrics 端点;如需 Prometheus 格式,
请提交 issue 或贡献一个。
详见 可观测性。
资源规模
单用户部署的典型资源使用量:
- CPU:空闲 ≈ 1 核的 1%,忙碌(活跃轮次)≈ 1 核的 20%。 真正的工作在 LLM 提供商端进行。
- 内存:150–300 MB 常驻。增长主要是 SQLite 页缓存 和内存日志环形缓冲区。
- 磁盘:日常使用每月 20–100 MB。审计日志是主要消耗者;
MINARA_LOG_RETENTION_DAYS限制它。 - 网络:突发式。空闲接近零;活跃轮次可向 LLM 提供商传送几 MB。
这些是指南。如运行繁重的研究工作负载或包含多个标的的 Autopilot, 预期各项增加 2–4 倍。
不要做的事
- 不要多个进程同时写入同一 SQLite 文件并期望并发写入安全。 SQLite 是单写入者。使用上述单所有者加代理的形式。
- 不要跳过卷挂载。 没有它每次重启都会丢失审计日志、记忆和身份验证状态。
- 不要在未设置
GATEWAY_AUTH_TOKEN且没有终止 TLS 的反向代理的情况下绑定到0.0.0.0(或去掉-p中的127.0.0.1:前缀)。 网关暴露涉及资金的端点; 否则安全绑定守卫将拒绝启动或自动生成 token。 - 不要将密钥放入镜像。 绝对不要。就算只是"今天测试"也不行。
- 不要禁用权限等级钩子链作为 Autopilot 测试的快捷方式。
如想要无操作支出上限,改用
MINARA_AUTOPILOT_CAP_USD=0.01。