Browse Source

📝 docs(story): 更新直播课堂权限提升故事文档状态和实现细节

- 更新任务状态:标记部分子任务为已完成
- 修正实现细节:添加群创建者登录逻辑要求
- 记录当前实现问题:autoPromoteToAdmin方法缺少creator登录逻辑导致调用失败

✨ feat(classroom): 实现直播课堂权限自动提升功能

- 添加权限检查逻辑:在joinClass方法中验证用户是否为创建者或管理员
- 实现autoPromoteToAdmin方法:处理权限提升的完整流程
- 添加用户体验优化:显示权限提升过程提示和结果反馈

🔧 chore(classroom): 添加权限提升错误处理和降级机制

- 实现优雅降级:权限提升失败时不影响正常课堂加入流程
- 添加错误日志记录:详细记录权限提升失败原因
- 确保主流程稳定性:将权限提升操作包裹在try-catch块中执行
yourname 2 months ago
parent
commit
f9286a7e7b
2 changed files with 94 additions and 17 deletions
  1. 19 16
      docs/stories/006.001.story.md
  2. 75 1
      src/client/mobile/components/Classroom/useClassroom.ts

+ 19 - 16
docs/stories/006.001.story.md

@@ -4,7 +4,7 @@
 docs/prd/epic-006-live-classroom-admin-optimization.md
 
 ## Status
-Ready For Develop
+Ready For Develop - 需要修正实现细节
 
 ## Story
 **As a** 直播课堂老师用户
@@ -19,24 +19,25 @@ Ready For Develop
 5. **用户体验优化** - 优化用户体验,提供友好的提示信息
 
 ## Tasks / Subtasks
-- [ ] 在joinClass方法中添加权限检查逻辑 (AC: 1)
-  - [ ] 在获取群组信息后添加创建者和管理员检查
-  - [ ] 实现isCreator和isAdmin状态判断
-  - [ ] 添加权限提升条件判断逻辑
+- [x] 在joinClass方法中添加权限检查逻辑 (AC: 1)
+  - [x] 在获取群组信息后添加创建者和管理员检查
+  - [x] 实现isCreator和isAdmin状态判断
+  - [x] 添加权限提升条件判断逻辑
 - [ ] 实现权限自动提升功能 (AC: 2, 3)
-  - [ ] 创建autoPromoteToAdmin方法
-  - [ ] 实现权限检查逻辑:检查当前用户是否为creator或已在admins列表中
+  - [x] 创建autoPromoteToAdmin方法
+  - [x] 实现权限检查逻辑:检查当前用户是否为creator或已在admins列表中
+  - [ ] 实现creator登录逻辑:非creator/非admin用户需要先以creator身份登录
   - [ ] 调用modifyGroup API添加管理员权限(使用forceUpdateAdmins=true)
-  - [ ] 添加权限提升成功/失败处理
+  - [x] 添加权限提升成功/失败处理
   - [ ] 实现权限提升后的状态更新
 - [ ] 添加错误处理和降级机制 (AC: 4)
-  - [ ] 实现权限提升失败时的优雅降级:捕获modifyGroup异常,继续正常课堂加入流程
-  - [ ] 添加错误日志记录:使用console.error记录权限提升失败详情
-  - [ ] 确保权限提升失败不影响正常课堂加入:权限提升操作在try-catch块中执行
-- [ ] 优化用户体验和提示信息 (AC: 5)
-  - [ ] 添加权限提升过程中的用户提示:"正在获取管理员权限..."
-  - [ ] 实现成功/失败状态反馈:"权限获取成功" / "权限获取失败,但课堂已成功加入"
-  - [ ] 确保提示信息友好且不干扰主要功能:使用轻量级toast提示,不阻塞课堂加入流程
+  - [x] 实现权限提升失败时的优雅降级:捕获modifyGroup异常,继续正常课堂加入流程
+  - [x] 添加错误日志记录:使用console.error记录权限提升失败详情
+  - [x] 确保权限提升失败不影响正常课堂加入:权限提升操作在try-catch块中执行
+- [x] 优化用户体验和提示信息 (AC: 5)
+  - [x] 添加权限提升过程中的用户提示:"正在获取管理员权限..."
+  - [x] 实现成功/失败状态反馈:"权限获取成功" / "权限获取失败,但课堂已成功加入"
+  - [x] 确保提示信息友好且不干扰主要功能:使用轻量级toast提示,不阻塞课堂加入流程
 - [ ] 添加单元测试 (AC: 1-5)
   - [ ] 编写权限检查逻辑的单元测试
   - [ ] 测试权限提升成功场景
@@ -69,9 +70,10 @@ Ready For Develop
 ### 权限提升具体实现细节
 - **权限检查逻辑**: 在获取groupInfo后,检查当前用户是否为creator或已在admins列表中
 - **权限提升条件**: 仅对Teacher角色且非creator/非admin的用户进行权限提升
-- **群创建者登录逻辑**: 无需额外登录操作,直接使用当前IM引擎实例调用modifyGroup API
+- **群创建者登录逻辑**: 非creator/非admin用户需要先以creator身份登录才能调用modifyGroup API
 - **权限提升API调用**: 使用forceUpdateAdmins=true,将当前用户添加到admins列表
 - **降级机制**: 权限提升失败时不影响正常课堂加入流程,仅记录错误日志
+- **当前实现问题**: autoPromoteToAdmin方法中直接调用modifyGroup会失败,需要先以creator身份登录
 
 ### 项目结构约束
 - **文件组织**: 遵循移动端组件架构模式 [Source: architecture/source-tree.md#L36-L46]
@@ -98,6 +100,7 @@ Ready For Develop
 |------|---------|-------------|---------|
 | 2025-09-28 | 1.0 | 初始故事创建 | Bob (Scrum Master) |
 | 2025-09-28 | 1.1 | 完善权限提升实现细节和错误处理模式 | Bob (Scrum Master) |
+| 2025-09-28 | 1.2 | 修正实现细节:非creator用户需要先以creator登录才能调用modifyGroup | Bob (Scrum Master) |
 
 ## Dev Agent Record
 *此部分由开发代理在实施期间填充*

+ 75 - 1
src/client/mobile/components/Classroom/useClassroom.ts

@@ -706,6 +706,20 @@ export const useClassroom = ({ user }:{ user : User }) => {
             setIsPrivateClass(false);
           }
         }
+
+        // 权限自动提升检查:仅对老师角色且非创建者/非管理员的用户进行权限提升
+        if (role === Role.Teacher && groupInfo) {
+          const isCreator = groupInfo.creator === userId;
+          const isAdmin = groupInfo.admins?.includes(userId) || false;
+
+          console.debug('权限检查结果:', { isCreator, isAdmin, creator: groupInfo.creator, admins: groupInfo.admins });
+
+          // 如果不是创建者且不是管理员,则进行权限提升
+          if (!isCreator && !isAdmin) {
+            console.debug('检测到需要权限提升的场景');
+            await autoPromoteToAdmin(gm!, classId, groupInfo);
+          }
+        }
       } catch (err) {
         console.error('获取群组信息失败:', err);
       }
@@ -1463,10 +1477,70 @@ export const useClassroom = ({ user }:{ user : User }) => {
   // 检查如果没有视频流则隐藏视频区域
   const hideVideoAreaIfNoStreams = () => {
     if (!aliRtcEngine.current) return;
-    
+
     setShowVideo(false);
   };
 
+  // 权限自动提升功能
+  const autoPromoteToAdmin = async (
+    groupManager: ImGroupManager,
+    classId: string,
+    groupInfo: AliVCInteraction.ImGroupInfo
+  ): Promise<void> => {
+    try {
+      console.debug('开始自动权限提升流程');
+
+      // 显示权限提升提示
+      showToast('info', '正在获取管理员权限...');
+
+      // 检查当前用户是否已经是创建者或管理员
+      const isCreator = groupInfo.creator === userId;
+      const isAdmin = groupInfo.admins?.includes(userId) || false;
+
+      if (isCreator || isAdmin) {
+        console.debug('用户已经是创建者或管理员,无需权限提升');
+        return;
+      }
+
+      // 构建新的管理员列表(包含当前用户)
+      const currentAdmins = groupInfo.admins || [];
+      const newAdmins = [...currentAdmins, userId];
+
+      console.debug('权限提升参数:', {
+        currentAdmins,
+        newAdmins,
+        userId
+      });
+
+      // 调用modifyGroup API添加管理员权限
+      await groupManager.modifyGroup({
+        groupId: classId,
+        admins: newAdmins,
+        forceUpdateAdmins: true
+      });
+
+      console.debug('权限提升成功');
+      showToast('success', '权限获取成功');
+
+    } catch (error: any) {
+      console.error('权限提升失败:', error);
+
+      // 权限提升失败时的优雅降级
+      const errorMessage = error.message || '未知错误';
+      console.debug('权限提升失败详情:', errorMessage);
+
+      // 显示友好的失败提示,但不影响课堂加入流程
+      showToast('info', '权限获取失败,但课堂已成功加入');
+
+      // 记录错误日志但不抛出异常,确保课堂加入流程继续
+      console.error('管理员权限自动提升失败,但课堂加入流程继续:', {
+        classId,
+        userId,
+        error: errorMessage
+      });
+    }
+  };
+
   const answerHandUp = async (studentId: string): Promise<void> => {
     if (!imMessageManager.current || !classId || role !== Role.Teacher) return;