首页
学习
活动
专区
圈层
工具
发布
社区首页 >专栏 >OpenViking 多后端架构:让记忆存在 S3/本地/SQL

OpenViking 多后端架构:让记忆存在 S3/本地/SQL

作者头像
heidsoft
发布2026-07-15 18:29:56
发布2026-07-15 18:29:56
880
举报

源码解读 · 第 5 篇

OpenViking 多后端架构

让 AI 记忆存在 S3 / 本地磁盘 / SQL / 内存

OPC

云与数字化

1 人公司 · LLM 协作 · 工程底座

+ 关注

核心判断:ObjectStore trait 用三个异步方法(put/get/exists)屏蔽底层存储差异,四种后端无缝切换。多租户隔离通过 account 路径前缀实现,既简单又安全。

📚 OpenViking 源码解读

#1 架构解析 · #2 Git 对象存储 · #3 Fast Path · #4 PyO3 桥接 · #5 多后端架构(本文)

01为什么需要多后端?

AI 记忆系统存储需求多样:本地开发需要零网络开销,生产环境需要跨机器共享,大规模部署需要 S3 的弹性,嵌入式设备只需要内存存储。OpenViking 的解法是:定义统一 trait 接口,四种实现满足不同需求。

🖥️ 本地:开发调试、单机部署、零网络开销 ☁️ S3:大规模生产、多 Agent 集群、弹性扩展 📊 SQL:需要事务保证、审计日志、行级权限 💾 内存:嵌入式设备、测试环境、零 IO

02ObjectStore trait:统一存储接口

所有后端实现同一个 trait,三个方法含义清晰:

代码语言:javascript
复制
#[async_trait] pub trait ObjectStore: Send + Sync + 'static {
async fn put(&self, account: &str, oid: &ObjectId, zlib_body: Bytes) -> Result<()>;
async fn get(&self, account: &str, oid: &ObjectId) -> Result<Bytes>;
async fn exists(&self, account: &str, oid: &ObjectId) -> Result<bool>;
}

put:写入 Git 对象(已 zlib 压缩),account 隔离租户 get:读取 Git 对象,返回压缩原始字节 exists:Fast Path 3 前置检查,避免重复写入 S3 请求

"

最小接口原则:只需三个方法就完整抽象存储系统所有操作,任何新后端实现这三个方法即可无缝接入。

03四种后端对比

后端

介质

适用场景

优点

缺点

LocalObjectStore

本地磁盘

开发调试

零开销

不跨机器

S3ObjectStore

S3/TOS

生产集群

弹性扩展

计费成本

SqlObjectStore

SQLite/PG

事务场景

事务+查询

大对象低效

MemoryObjectStore

内存

嵌入式/测试

最快

重启丢失

04LocalObjectStore:本地磁盘实现

路径格式:Git loose object 标准,两级目录避免单目录超过 10000 文件。格式:{account}/objects/{aa}/{bb...}

代码语言:javascript
复制
// 路径格式:{account}/objects/{aa}/{bb...}
base_dir/{account}/objects/{aa}/{bb...}
// aa = OID 前2位(子目录,避免单目录 >10000 文件)
// bb = OID 剩余38位(文件名)

put 操作:写临时文件再 rename。POSIX 下 rename 是原子的——要么完全成功,要么目标文件不存在。

代码语言:javascript
复制
// 原子写入:写临时文件再 rename
let tmp = path.with_extension(format!("tmp.{}.{}", pid, seq));
await tokio::fs::write(&tmp, &zlib_body)?;
await tokio::fs::rename(&tmp, &path)?;  // POSIX 原子

put 操作信任调用方传入的 oid(SHA-1 哈希)。如果 oid 错误,对象存储在错误地址,下次 get 找不到。

05S3ObjectStore:对象存储后端

S3 的存储模型天然契合 Git 内容寻址。S3ObjectStore 直接调用 AWS S3 SDK:

putPutObject · getGetObject · existsHeadObject

S3 按请求计费。Fast Path 3 的 exists precheck 就是为降低 S3 成本——写前先查是否存在,避免重复写入。

06SqlObjectStore & MemoryObjectStore

SqlObjectStore:支持 SQLite(单节点)和 PostgreSQL(多 Agent 集群),切换只需改数据库连接 URL,不改代码。适合审计日志、多租户行级权限控制。

MemoryObjectStore:用 DashMap(并发 HashMap)存储:

代码语言:javascript
复制
struct MemoryObjectStore {
objects: DashMap<(String, ObjectId), Bytes>,
}

适用测试环境、嵌入式设备、短期缓存。三大限制:重启丢失、无法跨进程、受内存限制。

07多租户隔离:account 前缀

所有方法第一个参数都是 account: &str,参与存储路径构造:

本地:{base}/{account}/objects/... S3:{bucket}/{account}/objects/... SQL:WHERE account = ? 内存:(account, oid) 作为 HashMap key

account 隔离在存储层实现,而非业务层。无论哪种后端,租户隔离都内建于存储层,业务代码只传 account。

08后端选型决策树

单机开发/快速原型? → LocalObjectStore,零配置 跨机器共享? → S3ObjectStore 或 SqlObjectStore 数据量大/流量高? → S3ObjectStore,弹性扩展 需要事务保证? → SqlObjectStore + PostgreSQL 嵌入式/资源受限? → MemoryObjectStore 测试环境? → MemoryObjectStore 或 MockObjectStore

· · ·

核心洞察

ObjectStore trait 最小接口(3 方法)+ 路径格式统一({account}/objects/{aa}/{bb})+ 存储层多租户隔离 = 后端切换不改代码,数据迁移不需路径转换。

09设计总结

设计要点

OpenViking 做法

工程价值

接口抽象

ObjectStore trait,3 方法

后端可插拔

路径格式统一

{account}/objects/{aa}/{bb...}

数据迁移无需转换

多租户隔离

account 透传所有操作

存储层内建安全

幂等写入

rename 失败 → exists → 幂等

分布式并发安全

Fast Path

exists precheck

降低 S3 请求成本

行动建议

本周 clone OpenViking,用 LocalObjectStore 跑通 Git 对象存取全流程 本月 调研 S3ObjectStore 接入 TOS(字节火山引擎),测写放大防护效果 永远 设计任何新存储层,优先抽象 trait 接口,避免绑定特定后端

END · 完

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2026-07-15,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 云与数字化 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • OpenViking 多后端架构
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档