AskaEth da3a386daf
CI / Backend (build / vet / test / cross-compile) (push) Has been cancelled
CI / Frontend (tsc + vite build) (push) Has been cancelled
feat(cyrene,config,loop): 护栏/压缩/身份知识三条落地(P0-5/P0-10/P0-11)+ 身份注入收窄到主人会话
- P0-5 护栏不再是空壳:挂 WithSensitiveInfo(阻断) + 长度上限(输入 262144 / 输出 65536 字符,依据=
  组装完成的请求体量级与「不误伤正常对话」) + 关键词**仅在配置时**挂;正常对话有用例证明放行
- P0-11 上下文压缩默认启用:CONTEXT_MAX_TOKENS 默认 32768(=loop.DefaultMaxContextTokens,两常量由测试锁死),
  0/负 = 关闭(行为退回接线前);长对话真压缩且摘要消息进请求首位、最近一轮保留
- P0-10 身份说明书(owner.yaml identityFile)注入人格上下文,并且**收窄为仅主人会话**:
  · 新增最小钩子 loop.Options.PersonaKnowledgeFor(env):**按该轮会话环境**解析(不看提示词、不看会话 id),
    块只进每轮视图、**不进 messages**(不进 checkpoint、不进记忆提取面)
  · 开关 OWNER_IDENTITY_INJECTION:owner_only(默认) / always(仅自测) / off;非法值与读不动 → WARN + 回退默认(不静默)
  · **顺手关掉第二条同型泄漏**:channelbridge 群聊参与度判定器的 PersonaPrompt 此前带身份正文 ⇒ 现改为纯人格指令
  · 回归:缺文件/目录/未配置逐字节等于旧输出;静态指令与角色池 Instructions() 全不含正文;
    文件里点名的陌生账号仍 IsOwner==false(身份知识绝不参与权限判定)
- 复核:build/vet 绿 + cmd/config/loop 包测试绿;四类断言(主人含 / **群聊与陌生人不含** / always·off 两档 /
  回归不变)+ 4 条变异反证(含把判定改成恒真 → 提示词里真的出现身份说明书)均已还原
- 未做(登记):knowledge 块启动时读一次(改文件需重启);`.env.example` 的 OWNER_IDENTITY_INJECTION 行随后补;
  `internal/user/owner.go` 注释与 design/01 §2.2、design/11 §0 待同步
2026-10-04 14:30:26 +08:00
2026-08-09 20:04:49 +08:00

Cyrene v2 — 昔涟

自托管的「人格化通用智能体运行时」。一个 Go 单二进制,默认以「全能小女友」的人格陪伴你;在聊天/开发/家庭/工作等模式间无感切换;如 OpenClaw 般接入聊天平台(KOOK / 微信 iLink 已接通,QQ / Telegram 待接通);各人格独立记忆与情绪、共享同一套能力。

状态:按里程碑 M0–M12 推进中;每一项能力以「当前能力」三档清单(已实现 / 降级 / 未实现)为准,不作整体完成宣称。 | 分支:dev | 设计文档见 DevDocs/00-overview.md


当前能力(按真实状态分三档,不虚标)

状态以实际开发进度为准;标注「降级 / 占位」的项依赖外部凭据 / endpoint 才能达到完整形态。

✅ 已实现

  • 单二进制、进程内协作 — 所有服务同进程打包,仅 gateway :8080 对外;模块间走进程内接口 + 事件总线,零跨进程 IPC
  • 人格化陪伴 — 多人格 / 情绪状态机 / 好感度;per-persona 记忆隔离,能力全局共享
  • 通用 Agent 运行时 — 多供应商 LLM(per-role 路由 + 降级)、工具调用(8 轮上限)、子代理编排(生命周期 / 合并 / 上限)、记忆三类作用域 + RAG、会话持久化 / 主·次级会话
  • 多平台 IM 渠道插件(已接通) — KOOK、微信 iLink 已打通;OneBot v11 QQ / Telegram / Webhook 渠道插件均内置、可配置、随二进制分发
  • 微信 iLink 扫码绑定 + 自动认主 — 扫码登录(login-qr / login-status)已打通;绑定确认时自动把主人 id 登记进 owner 白名单(热生效,无需人工补录)
  • 多渠道主会话同步 — AI 渠道(web / kook / weixin)主人私聊汇聚到主会话,Web 端免刷新镜像;群聊 / 陌生人走独立隔离会话
  • 参与度引擎、backthink 自主思考(读写记忆 + 调工具 + 主动推送)、全链路流程可视化 P1(graph_update)
  • 系统设置(4 个可写操作) — 吊销全部 API key / 轮换 JWT / 备份 / 恢复,后端 + 前端真实操作已接通(owner-only + 审计 + 前端确认弹窗)
  • 语境感知 UI — 同一会话上下文下切换 聊天/开发/家庭/工作/知识/语音/视觉/子代理监控/设置 模式(Miuix 设计语言)
  • 超级详尽后台管理面板(/admin)— 15 大模块统一管理(RBAC + 审计)
  • 多平台部署 — Linux / Windows / macOS / ARM / Termux;SQLite 默认(PG + pgvector 可选增强,配置后真生效)

⚠️ 部分实现(降级 / 占位)

  • 视觉(真实模型未接通) — vision 分层路由与推理入口已实现,但真实视觉 / OCR 模型服务未接入:需配置 LLM_VISION_MODEL 及凭据;无凭据时降级为主模型直接看图 / 视觉·OCR 工具文本描述
  • 语音(ASR / TTS 真模型未接通) — STT→chat→TTS 链路已接,但真实 ASR / TTS provider 未接入:cloud STT 端点为占位(空 endpoint → 降级),edge-tts / espeak 为未实现占位;无凭据时全程降级(silent 返回空音频)。需配 ASR / TTS endpoint
  • RAG 语义 / 向量检索 — 导入文档当前走 keyword / line 路径(知识库 store 无直属向量索引),向量语义为优雅降级;配置 PG + pgvector 增强后真走语义路径
  • 微信 iLink 绑定依赖微信侧资格 — 扫码协议已对齐官方并打通;仍需微信账号侧具备 iLink bot 绑定资格(账号环境依赖)
  • checkpoint(durable execution) — 仅有 saveCheckpoint 保存、无恢复 / Resume(长任务中断不可回放,半壳)

❌ 未实现(当前不提供)

  • QQ(OneBot v11) / Telegram — 渠道插件代码存在,但未接通(需真 OneBot/Bot token)
  • 系统设置:编辑环境变量 / 重启服务 / 检查更新 — 后端未实现,不提供
  • 知识库删除(POST /api/v1/admin/rag/delete 写操作)— 当前返回 501 not_implemented
  • 全链路 P2 — 并行子代理分支 / 泳道 / 节点实时日志(当前 loop 未在 span 上记录事件,log[] 常空)
  • LLM 异步记忆提取 — 仅手工提取接线,LLM 异步提取未接入

本地部署(用户侧 · 全流程)

0. 前置

  • Go 1.26、Node 22(前端构建用)、Docker(用于 PostgreSQL + pgvector;不用 PG 可仅用 SQLite)。

1. 一键启动(最快,推荐)

bash scripts/dev-up.sh
# 依次拉起:PG+pgvector → llama.cpp embedding(Qwen3) → 前端 build → cyrene
# 访问 http://localhost:8080(按 .env 的 PORT)

scripts/dev-up.sh 约定:llama.cpp 放 ~/apps/llama.cpp/、GGUF 放 ~/.models/、cyrene 二进制 ~/apps/cyrene/cyrene。已运行的服务会自动跳过。

2. 配置 .env(复制 .env.example)

# 认证(JWT_SECRET 必填 ≥32)
JWT_SECRET=<≥32 字符随机串>
ADMIN_USERNAME=admin
ADMIN_PASSWORD=<你的密码>

# LLM(LLM_PROVIDER 显式声明协议:openai / anthropic)
LLM_PROVIDER=anthropic
ANTHROPIC_BASE_URL=https://api.deepseek.com/anthropic
ANTHROPIC_API_KEY=<key>
ANTHROPIC_MODEL=deepseek-flash
# 或 OpenAI 兼容:LLM_PROVIDER=openai + LLM_BASE_URL/API_KEY/MODEL

# 数据库(可选增强:PG + pgvector 向量检索;不配则用 SQLite)
DB_PG_URL=postgres://cyrene:cyrene_pass@localhost:5432/cyrene_ai?sslmode=disable

# 记忆嵌入(真语义;EMBEDDING_API_URL 必须是【完整 /v1/embeddings 端点】,不是 base)
EMBEDDING_API_URL=http://localhost:11434/v1/embeddings
EMBEDDING_MODEL=Qwen3-Embedding-0.6B

3. 数据库(PG + pgvector,Docker)

docker compose -f docker-compose.dev.yml up -d pg
# 首次:vector 扩展由应用自动 CREATE(本地 cyrene 用户为 superuser)

不用 PG 可跳过;SQLite 默认即用。若 Docker 未安装 compose 插件(部分精简版 29.x 只有 docker run), scripts/dev-up.sh 会自动回退 docker run 拉起 cyrene-pg,无需手动处理。

4. 本地 embedding(llama.cpp + Qwen3 GGUF,走 Vulkan/GPU)

# 一次准备(llama.cpp 放 ~/apps/llama.cpp/,模型放 ~/.models/;勿用 /tmp)
mkdir -p ~/apps/llama.cpp ~/.models
# llama.cpp release(Vulkan)解压到 ~/apps/llama.cpp/
# Qwen3-Embedding-0.6B-Q8_0.gguf(~639MB,ModelScope 下载)→ ~/.models/
chmod 644 ~/.models/Qwen3-Embedding-0.6B-Q8_0.gguf

# 启动
~/apps/llama.cpp/llama-server -m ~/.models/Qwen3-Embedding-0.6B-Q8_0.gguf \
  --embedding -ngl 99 --host 127.0.0.1 --port 11434 &

模型来源:HuggingFace 国内不可访问,请从 ModelScope(魔搭) 下载 Qwen3-Embedding-0.6B-Q8_0.gguf。llama.cpp 只认 GGUF(model.safetensors 是 transformers/HF 用的,不能直接喂)。

5. 构建并启动(单二进制,go:embed 前端)

cd frontend/web && npm ci && npm run build && cd ../..   # 产 dist(含拷到 internal/webui/dist)
go build -ldflags="-s -w" -trimpath -o cyrene ./cmd/cyrene/
./cyrene       # 访问 http://localhost:8080(按 .env 的 PORT)

6. 服务端口 / 路径速查

服务 地址 / 路径 说明
Cyrene 网关 http://localhost:8080(.env:PORT) SPA + REST/WS + 面板 /admin
PG + pgvector localhost:5432(docker cyrene-pg) 向量索引在 cyrene_ai
llama.cpp embedding http://localhost:11434/v1/embeddings Qwen3,Vulkan

7. 注意事项

  • 勿用 /tmp 放二进制/模型(tmpfs 在内存里,堆多了会炸);一律 ~/apps/、~/.models/。
  • EMBEDDING_API_URL 必须是完整 /v1/embeddings(不是 base),否则 404。
  • 切换 embedding 模型会改维度(Qwen3=1024,n-gram=256)→ 换模型前清一次向量表:docker exec cyrene-pg psql -U cyrene -d cyrene_ai -c "TRUNCATE vec_items;"(懒创建的真向量表)。
  • LLM 用 anthropic 协议时填 ANTHROPIC_*;用 openai 兼容时填 LLM_*。LLM_PROVIDER 二选一。

Embedding 模型推荐

用于长记忆/知识库语义向量检索(默认不配 = 内置 n-gram 向量,dim=256,离线但质量一般)。 配了 EMBEDDING_API_URL/MODEL 后走真语义。维度 = 模型 dim,与向量索引一致;切换模型会改维度,需清空旧向量数据。

模型 dim 大小 推理内存 质量 建议
Qwen3-Embedding-0.6B 1024 Q8_0 639MB / f16 1.2GB ~0.7–1GB ★★★★★(多语言、2025 新、MTEB 榜前列) ⭐ 首选(ModelScope 国内可下 + GGUF;Q8_0 639MB 契合低内存)
bge-m3 1024 ~2.2GB(fp16) / ~1.2GB(Q4) ~2–3GB ★★★★★(跨语言标杆) 内存 / GPU 充裕时可用
bge-small-zh-v1.5 512 ~30–100MB ~几十MB ★★★★ 极轻量备选
nomic-embed-text 768 ~270MB ~400–600MB ★★★☆ 可
mxbai-embed-large 768 ~350–670MB ~0.8–1GB ★★★★ 可

首选说明:Qwen3-Embedding-0.6B(阿里通义 2025-06 开源,覆盖 100+ 语言,MTEB 多语言榜前列)——有 GGUF、ModelScope(魔搭)国内直连可下(HuggingFace 在国内已不可访问);Q8_0 仅 639MB,即使内存紧张(如 ~3GB 可用、无独立显存的 UMA GPU)也能跑,且质量≈f16。比 bge-m3 更新、比 bge-small 强。若内存非常宽裕再考虑 bge-m3。

.env 示例(本地 Ollama / llama.cpp):

# EMBEDDING_API_URL 必须是【完整 /embeddings 端点】(不是 base)
EMBEDDING_API_URL=http://localhost:11434/v1/embeddings
EMBEDDING_MODEL=Qwen3-Embedding-0.6B
# EMBEDDING_API_KEY=

llama.cpp 能替代 Ollama 吗? —— 能,且更省内存。llama.cpp 的 llama-server(服务模式)同样暴露 OpenAI 兼容 /v1/embeddings,用单二进制 + 一个 GGUF:

./llama-server -m Qwen3-Embedding-0.6B-Q8_0.gguf --embedding -ngl 99 --port 11434
# 然后 EMBEDDING_API_URL=http://localhost:11434/v1/embeddings 照用(dim=1024;切换前清一次向量表)
  • Ollama:模型管理方便(pull)、开箱即用,但常驻偏重。
  • llama.cpp:单文件更轻(内存更省,适合资源受限 / 单机部署)、可离线自制 GGUF;但模型要自己下/转(无 registry)。注意:llama.cpp 只认 GGUF,model.safetensors 是 transformers/HF 用的,不能直接喂 llama.cpp。
  • 二者对上层代码等价(都是 OpenAI 兼容 embedding 端点);资源受限时 llama.cpp 更省内存,追求易用则选 Ollama。

技术栈

层 技术
后端 Go 1.26(单二进制运行时)、进程内总线(可换 NATS)、slog(日志带 source 来源标注)
前端 React 19、TypeScript、Vite 6、Tailwind 4、Zustand 5、PWA(Miuix 设计语言)
数据库 SQLite 默认(纯 Go、单二进制);PG + pgvector 可选增强(配置后真生效)
多模态 vision(分层路由:主/视觉/OCR;真模型未接通,无凭据降级主模型)、async voice(STT→agent→TTS 降级链;真 ASR/TTS 未接通,无凭据降级 silent)
LLM 多供应商(OpenAI 兼容/订阅/本地/网关)、per-role 路由 + 降级

目录

Cyrene_v2/
├── cmd/cyrene/            # 唯一入口(mapping 全部子系统 + go:embed 前端)
├── internal/              # config/logger/platform/db/bus/errors/auth/user/
│                           # runtime(核心: model/agent/loop/tool/guardrail/trace/persist/
│                           #   memory/embedding/multimodal/orchestration/exec/task)
│                           # persona/capability/channel/services(gateway/automations/backthink)/iot/webui
├── plugins/               # tools(basic/io) + channels(qq_obv11/weixin_ilink/telegram/webhook)
├── pkg/plugins/sdk/       # 插件 SDK(第三方)
├── frontend/web/          # React SPA(mode 系统)+ /admin 面板(Miuix)
├── Docs/                  # 用户文档(含 api-client.md 客户端 API 契约)
├── DevDocs/               # 开发文档(本地,不入库)
└── configs/               # 配置模板(personas/ + users/ 主人档案)

文档

文档 位置 说明
架构总览/重构蓝图 DevDocs/00-overview.md 产品定位、架构、渠道插件、后台面板、阶段计划
开发约束 DevDocs/02-development-constraints.md 编码规范 + 性能要求
客户端 API Docs/api-client.md 跨平台客户端 API 契约(REST/WS/admin,版本化)
开发铁律 AGENTS.md 每会话自动注入;含全球红线(单二进制/身份识别/前端 Miuix 等)

License

Apache-2.0 © 2026 Aska