给现有系统加 AI:连接数据库,而不是先迁移
在自管部署的 ObjectOS(企业版)里,把已经运行的数据库接入(默认只读),让 agent 把关键数据表建模为对象,再在你的权限边界内叠加 AI 能力;原系统继续运行,AI 走受控对象层。
先给结论:让现有系统支持 AI,不必先迁移或重建——把 ObjectOS 连到你正在跑的数据库,让 agent 在你的权限之下读懂真实数据、叠加 AI,优先连接,而不是先重建。
大多数“给你的业务加上 AI”的说辞,都悄悄假设了一次重建:把数据搬到新平台、重新实现工作流、重新培训团队,然后祈祷迁移顺利落地。而这正是没人想做的部分。那套记录系统 —— CRM、ERP、工单工具、自研的后办公系统 —— 已经在运转,数据也已经在那里。
ObjectOS 采取相反的立场。你不迁移。你连接。
一句话 讲清这个 想法
在自管部署的 ObjectOS(企业版,跑在你自己的基础设施上、数据库可达)里,把 ObjectOS 指向你现有的数据库——默认只读——将你关心的数据表描述为对象,于是每一个 AI Agent、流程、API 和仪表盘都立刻在这些数据上工作 —— 自动路由到正确的系统,并受你的用户已经拥有的同一套权限治理。
原有的应用不会改变。数据行不会移动。ObjectOS 成为你已运行系统之上那层原生支持 AI、感知权限的界面。
一个 具体的 画面
假设你的销售团队跑在一个 40 张表的 Postgres CRM 上。客户、联系人、商机、明细行、活动 —— 多年的真实数据,一个销售每天都在用的生产应用。管理层想要两件事:让大家用自然语言向数据提问(“哪些企业级商机滑出了 Q2,分别是谁在负责?”),以及让自动化安全地操作这些数据。
重建的答案可能是一个数月项目。ObjectOS 的路径是先做一个低风险连接:
- 把 CRM 数据库连接为一个只读数据源。
- 让编码 Agent 把你真正关心的那十来张表建模为对象。
- 向你的数据提问,并接上第一条自动化。
不用先替换 CRM,也不用先搬走数据。你在相同的数据行之上,得到一层支持 AI 的对象与权限边界。
它今天 如何 运作
一共四步,而且没有一步是“重建你的应用”。
1. 将数据库 连接 为数据源
数据源是一个具名连接 —— Postgres、MySQL、MongoDB、SQLite。凭据来自环境变量,绝不写死在源码里。如果你想先做分析,把它指向只读副本或只读数据库用户,写入便根本无从发生。
import type { Datasource } from '@objectstack/spec';
export const BusinessDb: Datasource = {
name: 'business_primary',
label: 'Business System (Postgres)',
driver: 'postgres',
config: {
connection: {
host: process.env.BIZ_DB_HOST,
user: process.env.BIZ_DB_USER,
password: process.env.BIZ_DB_PASSWORD,
database: process.env.BIZ_DB_NAME,
},
},
pool: { min: 1, max: 10 },
active: true,
};
2. 将数据 表建模为对象 —— 交给 编码 Agent
这一步人们以为会很慢,其实不然。你不必为每张表手工敲对象。把像 Claude Code 这样的编码 Agent 指向已连接的 schema,让它完成内省与初稿。一句朴素的提示就够了:
“连接到
business_primary数据源。为这几张表 ——accounts、contacts、opportunities、line_items—— 各生成一个src/objects/<name>.object.ts文件,使用ObjectSchema.create。把 SQL 列映射到合适的Field.*类型,把外键转成Field.lookup(...),并在每个对象上设置datasource: 'business_primary'。”
Agent 会读取真实的列、类型和外键,写出源级别的对象文件。我们的
hotcrm 参考应用展示了输出的确切形态:
import { ObjectSchema, Field } from '@objectstack/spec/data';
export const Opportunity = ObjectSchema.create({
name: 'biz_opportunity',
label: 'Opportunity',
datasource: 'business_primary',
fields: {
name: Field.text({ label: 'Name', required: true }),
account: Field.lookup({ label: 'Account', reference_to: 'biz_account' }),
amount: Field.currency({ label: 'Amount' }),
stage: Field.select({ label: 'Stage', options: [/* … */] }),
close_date: Field.date({ label: 'Close Date' }),
},
});
因为产物是你拥有并提交的普通源码,你始终掌握控制权:保留重要的列、丢弃不想暴露的列,再叠加 label、校验与权限。Agent 几分钟内把你带到一份可审阅的初稿;你来让它达到生产级别。
3. 将对象 绑定到数据源
每个对象都带有 datasource。可以逐个对象设置,也可以为整个命名空间声明一条路由规则,让其下每个对象继承:
datasourceMapping: [
{ namespace: 'biz', datasource: 'business_primary' },
{ default: true, datasource: 'default' },
]
规则按命名空间、包名或对象名 glob 匹配;首个命中者生效。数据驻留的决策集中在一处,而不是散落在各个文件里。
4. 让 AI 开始 工作
一旦一张表成为对象,AI 层就能在它上面工作。ObjectOS 的 agent 与工具 ——
list_objects、describe_object、query_records、aggregate_data 以及
data-chat agent —— 都经由 ObjectQL,由它将每个对象路由到所绑定的数据源,并在驱动支持时把过滤、排序与聚合下推进数据库。
于是当用户问:
“哪些企业级商机滑出了 Q2,分别是谁在负责?”
Agent 不会把整张表灌进提示词。它会把这句话编译成一条针对 biz_opportunity
的 ObjectQL 查询 —— 对阶段和关闭日期的 WHERE、对负责人的 join —— 在你的
Postgres 上以 SELECT … WHERE … 执行,并基于真实、当前的数据行作答。而且关键在于,它以已登录用户的身份运行这条查询:如果某个销售在 CRM 里看不到其他区域的商机,Agent 也同样看不到。
为什么 这是安全的
对“在我们的业务数据上跑 AI”的质疑总是关于治理,而这恰恰是运行时发挥作用的地方:
- AI 以用户身份行动,绝不凌驾其上。 Agent 看到的,恰好是它背后那个人被允许看到的内容 —— 对象级、记录级、字段级权限由运行时强制,而非由提示词约束。
- 如果你愿意,默认只读。 把对象绑定到只读连接或只读数据库用户。安全地分析生产数据;再有意识地、一个对象一个对象地开启写入。
- 一切皆有审计。 每一次读取、写入和提权 —— 无论来自人还是 Agent —— 都记录下何人、何事、何时、何因。
- 你的数据留在你的网络里。 自管部署时(ObjectOS Enterprise),ObjectOS 跑在你的环境中;运行同一份本体的开源 ObjectStack 运行时也是如此。业务数据留在你的数据库里;提示词只会发给你配置的 AI 提供方(ObjectOS Cloud 则代为运行模型),模型能看到什么由权限决定。
重建 vs. 连接
| 重建到新平台 | 用 ObjectOS 连接 | |
|---|---|---|
| 首次见效时间 | 数月 | 从少量对象开始,逐步扩展 |
| 对记录系统的风险 | 高 —— 数据迁移、双写、切换上线 | 低 —— 先只读连接,源应用继续运行 |
| 数据存放在哪 | 被搬走 | 原地不动 |
| 建模工作量 | 手工重新实现每个实体 | 编码 Agent 从真实 schema 起草对象 |
| 权限 | 重建并重新审计 | 继承;AI 遵守同一套模型 |
| 可逆性 | 难以撤销 | 断开数据源 —— 什么都没变 |
第一 天你就能得到 什么
一旦几张表被建模并绑定:
- 自然语言分析作用于实时记录,经由 ObjectQL 计算 —— 而非一份过期的导出。
- 受治理的自动化。 流程与动作读取、并(在允许处)写入同一批数据,每一步皆有审计。
- 生成式 API 与控制台。 REST/GraphQL 端点与管理界面源自同一份元数据 —— 无需另建集成层。
- 同一套权限模型。 适用于人的边界,同样适用于 AI 流量。
已经 交付的 vs. 即将 到来的
上面这套流程今天就能用,凭借的是已交付的构建块:数据源、按对象路由、感知能力的 ObjectQL 下推,以及 AI Agent 层。对象的建模由一个编码 Agent 针对你已连接的 schema 完成 —— 与 hotcrm 的对象被编写出来的方式相同。
那套更丰富的开箱即用联邦(turn-key federation)体验 —— 一步式 schema 导入、绑定到外部拥有的 schema、内建的写入安全闸门 —— 已经交付。 ADR-0015 现在是 Accepted(后端、REST 与 CLI 均已实现), ADR-0062 则是其运行时那一半的规范决策。具体来说:
- schema 导入是一条命令,而不是一个项目。
os datasource list-tables <name>列出远端的表,os datasource introspect <name> --table <table>从活的表生成对象草稿 —— 列、类型、外键。草稿依然是你自己评审并提交的普通源码。 - 绑定到你并不拥有的 schema,是一次声明。 在数据源上设置
schemaMode: 'external',ObjectStack 就不会对那个数据库执行任何 DDL;每个对象通过external.remoteName/remoteSchema/columnMap指明自己的远端表。声明与真实的列不一致时,启动会带着 diff 失败(validation: { onMismatch: 'fail' };起草阶段可以用validate-only只告警),os datasource validate <name>则按需检查。 - 写入需要两次分别开启,落在两个文件里。 数据源上的
external.allowWrites: true,以及对象上的external.writable: true。任一道闸门关着,insert、update、delete 都会被拒绝。
这些闸门属于联邦:它们回答的是这个数据库归谁所有,因此只作用于外部数据源,不作用于 ObjectStack 自己管理的数据源。对于 ObjectStack 拥有的数据库,只读依然是数据库层的 GRANT —— 与下面常见问题里写的完全一致。
ADR-0015 上仍未完成的,是联邦的 Studio 界面,以及更多 SQL 方言的驱动。无论如何,本文走的这条路径 —— 连接、建模、绑定、查询 —— 没有变化,也依然受支持。
常见 问题
我必须把每张表都建模吗? 不必。只建模你想让 AI 和自动化触及的表。数据库其余部分会被忽略。
这会写入我的生产数据库吗? 只有你允许才会。绑定到只读连接或只读数据库用户,写入便不可能发生;准备好后,再有意识地、按对象开启写入。
我的数据会发给模型厂商吗? 自管部署(ObjectOS Enterprise)或开源 ObjectStack 运行时跑在你的环境中,查询在你的数据库上执行,AI 提供方由你配置;ObjectOS Cloud 则代为运行模型。无论哪个版本,模型能看到什么都由权限决定。
如果我的 schema 变了怎么办? 针对更新后的 schema 重新运行编码 Agent,重新生成或对受影响的对象做 diff —— 它们不过是你仓库里的源码文件。
如果你已经有一个业务数据库,那你已经走完了大半路程。连上它,建模几张表,然后向你的数据提个问题。
