## P1 安全加固 - 原子化每日限额(tryConsumeDailyQuota)解决 TOCTOU 竞态 - 流式端点补齐 Zod 校验 + rate limit + 服务端强制 systemPrompt - 配额回退机制(refundDailyQuota):过滤/失败不扣配额 - PII 最小化:移除 AI prompt 中的学生姓名 ## P1 数据一致性 - 修复 capability 埋点缺失 child_summary/study_path 类型 - 创建 data-access.ts:真实统计聚合替代硬编码零 - 修复 generateChildSummary/recommendStudyPath 的 capability 标记 ## P2 可靠性 - AI 调用重试机制(withRetry 指数退避,429/5xx,2 次重试) - 30s 超时配置 - 流式 controller 安全 enqueue(防已关闭抛错) - localStorage 防抖持久化(500ms,流式过程中跳过) ## P2 TypeScript/规则合规 - 移除 as 断言(VariantType 类型守卫、Permission 类型、StreamErrorKey) - 补齐返回类型标注(POST/getStatusFromError/DashboardLayout) - 拆分 use-ai-chat-stream hook(190→107 行,函数体≤80 行) - 抽取 stream-utils.ts(SSE 解析/错误映射/消息工具) - Tailwind 任意值添加注释说明(max-w-[80%] 聊天气泡) ## P3 竞品对标 - 苏格拉底式辅导强化(对标 Khanmigo): - SOCRATIC_TUTOR_SYSTEM_PROMPT 3 级提示升级 - 强化 STUDENT_BLOCKED_PATTERNS 正则(中英文答案拦截) - validateSocraticOutput 服务端校验(问号结尾+连续陈述句限制) - socratic_warning SSE 事件类型 - 知识图谱集成(对标 Squirrel AI): - StudyPathInput 新增 knowledgeGraph/textbookId 字段 - recommendStudyPathAction 自动从 textbooks 模块获取图谱+掌握度 - STUDY_PATH_SYSTEM_PROMPT 增加前置依赖链规则 - WEAKNESS_ANALYSIS_SYSTEM_PROMPT 增加 rootCause 字段 ## 架构文档同步 - 004 更新 AI 模块章节(V3 标记/新导出/依赖关系/安全机制/文件清单) - 005 更新 modules.ai 节点(dependsOn/exports/dataAccess/streamUtils/dependencyMatrix)
53 lines
1.8 KiB
TypeScript
53 lines
1.8 KiB
TypeScript
import { AppSidebar } from "@/modules/layout/components/app-sidebar"
|
|
import { SidebarProvider } from "@/modules/layout/components/sidebar-provider"
|
|
import { SiteHeader } from "@/modules/layout/components/site-header"
|
|
import {
|
|
AiClientProvider,
|
|
} from "@/modules/ai/context/ai-client-provider"
|
|
import { AiAssistantWidget } from "@/modules/ai/components/ai-assistant-widget"
|
|
import {
|
|
aiChatAction,
|
|
suggestSimilarQuestionsAction,
|
|
suggestGradingAction,
|
|
generateLessonContentAction,
|
|
generateQuestionVariantAction,
|
|
analyzeWeaknessAction,
|
|
generateChildSummaryAction,
|
|
recommendStudyPathAction,
|
|
getAiUsageStatsAction,
|
|
} from "@/modules/ai/actions"
|
|
import type { AiClientService } from "@/modules/ai/types"
|
|
|
|
const aiClientService: AiClientService = {
|
|
chat: aiChatAction,
|
|
suggestSimilarQuestions: suggestSimilarQuestionsAction,
|
|
suggestGrading: suggestGradingAction,
|
|
generateLessonContent: generateLessonContentAction,
|
|
generateQuestionVariant: generateQuestionVariantAction,
|
|
analyzeWeakness: analyzeWeaknessAction,
|
|
generateChildSummary: generateChildSummaryAction,
|
|
recommendStudyPath: recommendStudyPathAction,
|
|
getAiUsageStats: getAiUsageStatsAction,
|
|
}
|
|
|
|
export default function DashboardLayout({
|
|
children,
|
|
}: {
|
|
children: React.ReactNode
|
|
}): React.ReactNode {
|
|
return (
|
|
<AiClientProvider service={aiClientService}>
|
|
<SidebarProvider sidebar={<AppSidebar />}>
|
|
<a href="#main-content" className="sr-only focus:not-sr-only focus:absolute focus:z-50 focus:p-4 focus:bg-background focus:text-foreground focus:border focus:border-border focus:rounded-md focus:m-2">
|
|
Skip to main content
|
|
</a>
|
|
<SiteHeader />
|
|
<main id="main-content" className="flex-1 overflow-auto p-6">
|
|
{children}
|
|
</main>
|
|
<AiAssistantWidget />
|
|
</SidebarProvider>
|
|
</AiClientProvider>
|
|
)
|
|
}
|