12 KiB
student-bff 下游工作清单(Next Steps)
负责人:ai04 更新日期:2026-07-13 关联:student-portal_contract.md、student-portal_workline.md
1. 概述
student-bff 已完成全部 35 Query + 23 Mutation + 1 Subscription 的 schema 与 resolver 实现,Docker 镜像本地构建与运行验证通过(MOCK_UPSTREAM=false)。下游 gRPC 服务未启动时,BFF 进入降级模式(方案 B),返回 degraded: true + degradedReason + degradedFields。
本地 Docker 测试结果(2026-07-13):
- ✅ 镜像构建成功(
edu/student-bff:test) - ✅ 容器启动正常(端口 3009,NestFactory + GraphQL Yoga 初始化完成)
- ✅
/healthz返回 200 - ✅
MOCK_UPSTREAM=false,下游未启动时进入降级模式 - ✅
serverTimeQuery 返回本地时间(无下游依赖) - ✅
myProfileQuery 返回degraded=true,原因为DOWNSTREAM_FAILURE: iam.GetUserProfile failed after 3 attempts - ✅
myScheduleQuery 返回空 items +degraded=true - ✅
markAsReadMutation 返回success=false+error.code=BFF_STUDENT_BAD_GATEWAY - ✅
createLeaveRequestMutation 返回success=false+error.code=BFF_STUDENT_BAD_GATEWAY - ✅ B4 越权防御生效:无
x-user-idheader 时返回 401 UnauthorizedError - ✅ Kafka 软失败(不影响服务启动,仅 EventSubscriber 不工作)
2. 上游依赖(api-gateway 路由)
2.1 api-gateway(ai01 负责)
阻塞级别:P0(必须完成才能端到端联调)
| # | 工作项 | 详情 |
|---|---|---|
| 1 | 新增 /api/v1/student/graphql 路由 |
当前 api-gateway 无此路由。需新增 POST /api/v1/student/graphql 代理到 student-bff :3009/graphql(ARB-019 §21) |
| 2 | JWT 校验 + 用户身份注入 | api-gateway 校验 JWT 后,注入 x-user-id / x-user-roles / x-request-id header 到 student-bff |
| 3 | 学生角色校验 | /api/v1/student/* 路由组上添加 student 角色门禁,拒绝非 student 角色访问 |
| 4 | 限流配置 | student-bff 路由组配置 IP 级令牌桶限流 |
| 5 | 熔断/重试 | 对 student-bff 后端配置熔断器(opossum 已在 student-bff 内部启用,gateway 层可加外层熔断) |
相关文件:
services/api-gateway/main.go(路由注册)services/api-gateway/internal/middleware/auth.go(JWT 校验)services/api-gateway/internal/proxy/proxy.go(反向代理)services/api-gateway/internal/config/config.go(路由配置)
3. 下游依赖(gRPC 微服务)
3.1 iam 服务(ai06 负责)
阻塞级别:P0(影响用户身份相关功能)
| # | gRPC 方法 | 用途 | 当前状态 |
|---|---|---|---|
| 1 | GetUserProfile |
myProfile Query |
❌ 缺失 |
| 2 | UpdateProfile |
updateProfile Mutation |
❌ 缺失 |
| 3 | ChangePassword |
changePassword Mutation |
❌ 缺失 |
proto 位置: packages/shared-proto/proto/iam/v1/iam.proto
3.2 core-edu 服务(ai08 负责)
阻塞级别:P0(影响学生核心学习功能)
| # | gRPC 方法 | 用途 | 当前状态 |
|---|---|---|---|
| 1 | GetExam |
examDetail Query |
❌ 缺失 |
| 2 | SubmitExam |
submitExam Mutation |
❌ 缺失 |
| 3 | SaveExamDraft |
saveExamDraft Mutation |
❌ 缺失 |
| 4 | RecordExamViolation |
recordExamViolation Mutation |
❌ 缺失 |
| 5 | GetHomework |
homeworkDetail Query |
❌ 缺失 |
| 6 | GetScheduleByStudent |
mySchedule Query |
❌ 缺失 |
| 7 | ListLeaveRequestsByStudent |
myLeaveRequests Query |
❌ 缺失 |
| 8 | CreateLeaveRequest |
createLeaveRequest Mutation |
❌ 缺失 |
| 9 | CancelLeaveRequest |
cancelLeaveRequest Mutation |
❌ 缺失 |
| 10 | GetReportCard |
myReportCard Query |
❌ 缺失 |
proto 位置: packages/shared-proto/proto/core_edu/v1/core_edu.proto
3.3 content 服务(ai09 负责)
阻塞级别:P0(影响学生内容浏览功能)
| # | gRPC 方法 | 用途 | 当前状态 |
|---|---|---|---|
| 1 | ListElectiveSelectionsByStudent |
myElectiveSelections Query |
❌ 缺失 |
| 2 | ListAvailableElectiveCourses |
availableElectiveCourses Query |
❌ 缺失 |
| 3 | SelectCourse |
selectElectiveCourse Mutation |
❌ 缺失 |
| 4 | DropCourse |
dropElectiveCourse Mutation |
❌ 缺失 |
| 5 | ListLessonPlansByStudent |
myLessonPlans Query |
❌ 缺失 |
| 6 | GetLessonPlan |
lessonPlanDetail Query |
❌ 缺失 |
| 7 | ListCoursePlansByStudent |
myCoursePlans Query |
❌ 缺失 |
| 8 | GetCoursePlan |
coursePlanDetail Query |
❌ 缺失 |
proto 位置: packages/shared-proto/proto/content/v1/content.proto
3.4 data-ana 服务(ai12 负责)
阻塞级别:P0(影响学生学情分析功能)
| # | gRPC 方法 | 用途 | 当前状态 |
|---|---|---|---|
| 1 | GetStudentGrowth |
studentGrowth Query |
❌ 缺失 |
| 2 | GetAssignmentAnalysis |
assignmentAnalysis Query |
❌ 缺失 |
| 3 | GetMasterySummary |
myMasterySummary Query |
❌ 缺失 |
| 4 | ListDiagnosticReports |
myDiagnosticReports Query |
❌ 缺失 |
| 5 | ListErrorBookItems |
myErrorBook Query |
❌ 缺失 |
| 6 | ListPracticeSessionsByStudent |
myPracticeSessions Query |
❌ 缺失 |
| 7 | StartPracticeSession |
startPracticeSession Query |
❌ 缺失 |
| 8 | SubmitPracticeAnswer |
submitPracticeAnswer Mutation |
❌ 缺失 |
proto 位置: packages/shared-proto/proto/data_ana/v1/data_ana.proto
3.5 msg 服务(ai10 负责)
阻塞级别:P0(影响学生通知与公告功能)
| # | gRPC 方法 | 用途 | 当前状态 |
|---|---|---|---|
| 1 | ListAnnouncements |
announcements Query |
❌ 缺失 |
| 2 | GetAnnouncement |
announcementDetail Query |
❌ 缺失 |
| 3 | MarkNotificationAsRead |
markAsRead Mutation |
❌ 缺失 |
| 4 | MarkAllNotificationsAsRead |
markAllAsRead Mutation |
❌ 缺失 |
| 5 | UpdateNotificationPreference |
updateNotificationPreference Mutation |
❌ 缺失 |
| 6 | MarkAnnouncementRead |
markAnnouncementRead Mutation |
❌ 缺失 |
proto 位置: packages/shared-proto/proto/msg/v1/msg.proto
3.6 ai 服务(ai11 负责)
阻塞级别:P1(影响 AI 辅助功能,可降级)
| # | gRPC 方法 | 用途 | 当前状态 |
|---|---|---|---|
| 1 | StreamAIChat |
aiStream Subscription |
❌ 缺失 |
proto 位置: packages/shared-proto/proto/ai/v1/ai.proto
3.7 push-gateway(ai13 负责)
阻塞级别:P1(影响实时推送)
| # | 工作项 | 详情 |
|---|---|---|
| 1 | WebSocket 推送端点 | student-bff EventSubscriber 接收 Kafka 事件后转发到 push-gateway |
| 2 | Kafka topic 对齐 | student-bff 订阅 student.notification.* 等 topic |
4. student-bff 已完成项汇总
| 工作项 | 状态 | 验证方式 |
|---|---|---|
| Schema 扩展(13Q+2M → 35Q+23M+1S) | ✅ | pnpm typecheck + GraphQL Playground 校验 |
| 22 个扩展 Query Resolver | ✅ | Docker 容器 GraphQL 请求测试 |
| 21 个扩展 Mutation Resolver | ✅ | Docker 容器 GraphQL 请求测试 |
| Zod 输入校验(21 个 Mutation Input Schema) | ✅ | typecheck + 运行时校验 |
| B4 越权防御(assertOwnData) | ✅ | 无 x-user-id 返回 401 |
| 降级模式(方案 B) | ✅ | 下游不可用时返回 degraded=true + 原因 |
| Redis 缓存(B6 5-30s TTL) | ✅ | CacheService 已注入,TTL 预设已配置 |
| Kafka EventSubscriber(软失败) | ✅ | Kafka 不可用时不阻塞启动 |
| DataLoader 批量加载 | ✅ | createDataLoaders 已注入 context |
| Dockerfile 多阶段构建 | ✅ | edu/student-bff:test 构建成功 |
| Docker 本地测试(MOCK_UPSTREAM=false) | ✅ | healthz + GraphQL Query/Mutation 全部按预期 |
5. 联调顺序建议
- ai06 完成 iam gRPC(GetUserProfile / UpdateProfile / ChangePassword)
- ai08 完成 core-edu gRPC(GetExam / SubmitExam / GetHomework / GetScheduleByStudent 等 10 个)
- ai09 完成 content gRPC(8 个选修/教案/课程计划相关)
- ai12 完成 data-ana gRPC(8 个学情分析相关)
- ai10 完成 msg gRPC(6 个通知/公告相关)
- ai01 完成 api-gateway
/api/v1/student/graphql路由 + JWT 注入 - ai11 完成 ai gRPC StreamAIChat(P1)
- ai13 完成 push-gateway WebSocket(P1)
- 端到端联调(student-portal → api-gateway → student-bff → 6 个下游 gRPC 服务)
6. 已知限制
| # | 限制 | 说明 |
|---|---|---|
| 1 | Kafka 未启动时 EventSubscriber 软失败 | 服务正常启动,但实时事件推送(通知/AI 流式响应)不工作 |
| 2 | 下游 gRPC 未就绪时进入降级模式 | 所有 Query 返回 degraded=true + 空数据;所有 Mutation 返回 success=false + BAD_GATEWAY |
| 3 | DEV_MODE=true 时跳过 B4 越权校验 | 生产环境必须 DEV_MODE=false,由 api-gateway 注入 x-user-id header |
| 4 | pino-pretty 仅 devDependencies | 生产环境 NODE_ENV=production 时不启用 pino-pretty transport(输出结构化 JSON) |
| 5 | OTEL_EXPORTER_OTLP_ENDPOINT 未配置 | Tracer 被禁用,需配置 OTLP endpoint 启用全链路追踪 |
本文件由 ai04 维护,下游工作项请各负责 AI 完成后通知 ai04 更新状态。