6.4 KiB
LobeChat 项目分析报告
基于对 lobe-chat 项目的深入探索,以下是值得 aitu 借鉴的关键模式和架构决策。
1. 状态管理 - Zustand Slice 模式
文件路径: src/store/chat/store.ts
LobeChat 使用了非常优雅的 Zustand 切片组合模式:
// 每个功能是独立的 slice
export interface ChatStoreAction extends
ChatMessageAction,
ChatThreadAction,
ChatAIChatAction,
ChatTopicAction {}
// 组合 slices 创建 store
const createStore: StateCreator<ChatStore> = (...params) => ({
...initialState,
...chatMessage(...params),
...chatAiChat(...params),
...chatTopic(...params),
});
export const useChatStore = createWithEqualityFn<ChatStore>()(
subscribeWithSelector(devtools(createStore)),
shallow,
);
借鉴价值: aitu 的 DrawnixContext 可以重构为类似的切片模式,提高可维护性和测试性。
2. AI 流式响应 - 平滑动画系统
文件路径: packages/fetch-sse/src/fetchSSE.ts
独立的 @lobehub/fetch-sse 包处理 SSE 流,特别是 平滑文本动画:
const createSmoothMessage = (params) => {
let buffer = '';
let outputQueue: string[] = [];
const startAnimation = (speed) => {
// 使用 requestAnimationFrame 实现平滑更新
// 动态速度调整基于队列长度
const targetSpeed = Math.max(speed, outputQueue.length);
currentSpeed += (targetSpeed - currentSpeed) * speedChangeRate;
};
};
借鉴价值: 可提取到独立包用于 aitu 的 AI 聊天功能,避免 UI 卡顿。
3. 模块化包结构
packages/
├── agent-runtime/ # AI 代理执行引擎
├── database/ # Drizzle ORM 模型
├── fetch-sse/ # SSE 流处理
├── model-runtime/ # LLM 提供商集成
├── types/ # 共享类型
├── utils/ # 通用工具
└── builtin-tool-*/ # 模块化工具包
借鉴价值: aitu 可以提取为:
@aitu/generation-service- AI 图片/视频生成@aitu/task-queue- 异步任务管理@aitu/media-cache- IndexedDB 缓存
4. 数据库架构 - Drizzle ORM
文件路径: packages/database/src/schemas/
Schema-first 的设计,自动生成 Zod 验证:
export const sessions = pgTable('sessions', {
id: text('id').$defaultFn(() => idGenerator('sessions')).primaryKey(),
slug: varchar('slug', { length: 100 }).notNull(),
title: text('title'),
userId: text('user_id').references(() => users.id, { onDelete: 'cascade' }),
}, (t) => [
uniqueIndex('slug_user_id_unique').on(t.slug, t.userId),
]);
export const insertSessionSchema = createInsertSchema(sessions);
借鉴价值: 如果 aitu 需要服务端持久化,Drizzle 是很好的选择。
5. 环境变量验证 - Zod + @t3-oss/env
文件路径: src/envs/auth.ts
类型安全的环境变量配置:
export const getAuthConfig = () => createEnv({
client: {
NEXT_PUBLIC_ENABLE_CLERK_AUTH: z.boolean().optional().default(false),
},
server: {
AUTH_SECRET: z.string().optional(),
},
runtimeEnv: {
AUTH_SECRET: process.env.AUTH_SECRET || process.env.NEXT_AUTH_SECRET,
},
});
借鉴价值: aitu 的 API Key 配置可以采用类似模式,提供更好的类型安全和默认值处理。
6. SWR 数据获取模式
文件路径: src/libs/swr/index.ts
针对不同场景的 SWR 封装:
// 灵活数据 - 支持焦点刷新
export const useClientDataSWR = (key, fetch, config) =>
useSWR(key, fetch, {
focusThrottleInterval: 5 * 60 * 1000,
revalidateOnFocus: true,
});
// 一次性获取 - 用于初始化
export const useOnlyFetchOnceSWR = (key, fetch, config) =>
useSWR(key, fetch, {
revalidateOnFocus: false,
revalidateOnReconnect: false,
});
借鉴价值: aitu 可以创建类似的 hooks 区分不同数据刷新策略。
7. 国际化 - 扁平化 key 结构
文件路径: locales/en-US/common.json
{
"about": "About",
"alert.cloud.action": "Try now",
"alert.cloud.desc": "All users get {{credit}} free credits...",
"cmdk.about": "About"
}
配合懒加载:
resourcesToBackend(async (lng, ns) => {
return loadI18nNamespaceModule({ lng, ns });
})
借鉴价值: 比嵌套结构更易维护,支持按需加载减少包体积。
8. 测试配置
文件路径: tests/setup.ts
import 'fake-indexeddb/auto'; // 模拟 IndexedDB
import { vi } from 'vitest';
// 集中 mock 外部服务
vi.mock('@lobehub/analytics/react', () => ({
useAnalytics: () => ({ analytics: { track: vi.fn() } }),
}));
借鉴价值: aitu 使用 localforage,可以用 fake-indexeddb 进行测试。
9. tRPC API 层
文件路径: src/libs/trpc/lambda/
分层的 procedure 设计:
const baseProcedure = trpc.procedure.use(openTelemetry);
export const publicProcedure = baseProcedure;
export const authedProcedure = baseProcedure.use(oidcAuth).use(userAuth);
借鉴价值: 如果 aitu 需要后端 API,tRPC 提供端到端类型安全。
10. 关键建议总结
| 领域 | 当前 aitu 状态 | 可借鉴改进 |
|---|---|---|
| 状态管理 | DrawnixContext + RxJS | Zustand slice 模式 |
| AI 流式 | 自定义实现 | 提取 fetchSSE 包 + 平滑动画 |
| 包结构 | Nx monorepo | 提取服务为独立包 |
| 环境配置 | 直接读取 | Zod 验证 + 类型安全 |
| 测试 | 基础配置 | fake-indexeddb + 集中 mock |
| i18n | 简单实现 | 扁平 key + 懒加载 |
11. 优先级建议
高优先级(立即可用)
- Zustand Slice 模式 - 重构状态管理,提高可维护性
- 环境变量验证 - 使用 Zod 确保配置正确性
- SWR 封装 - 统一数据获取策略
中优先级(下一阶段)
- fetchSSE 包 - 提取流式响应处理
- fake-indexeddb 测试 - 改进测试覆盖率
- 扁平化 i18n - 简化国际化维护
低优先级(长期规划)
- 模块化包结构 - 大规模重构
- Drizzle ORM - 需要后端时考虑
- tRPC - 需要后端 API 时考虑
参考链接
- LobeChat GitHub: https://github.com/lobehub/lobe-chat
- Zustand 文档: https://docs.pmnd.rs/zustand
- Drizzle ORM: https://orm.drizzle.team
- tRPC: https://trpc.io
- @t3-oss/env: https://env.t3.gg