Ver código fonte

refactor(backend): 重构10个控制器移除HttpServletRequest手动userId获取改用@RequestAttribute注入

- MembershipController, GuideController, FamilyInviteController
- FamilyUserController, InteractionLogController
- RelationshipQuestionnaireController, FamilyMembersController
- RelationshipQualityController, AuthController
- DanAssessmentExecutionController (含 @GetMapping→@PostMapping 修复)
- AdminSettlementController: 修复Result导入路径+@PostMapping+删除重复SettlementStats
- pom.xml: 删除重复的PDFBox依赖
Xiaogang Liao 1 mês atrás
pai
commit
67b94672c4

+ 0 - 7
cfc-backend/pom.xml

@@ -135,13 +135,6 @@
             <version>1.8.0</version>
         </dependency>
 
-        <!-- PDFBox -->
-        <dependency>
-            <groupId>org.apache.pdfbox</groupId>
-            <artifactId>pdfbox</artifactId>
-            <version>2.0.31</version>
-        </dependency>
-
         <!-- Test -->
         <dependency>
             <groupId>org.springframework.boot</groupId>

+ 14 - 35
cfc-backend/src/main/java/com/etotem/cfc/controller/MembershipController.java

@@ -14,7 +14,6 @@ import io.swagger.v3.oas.annotations.tags.Tag;
 import org.springframework.web.bind.annotation.*;
 
 import javax.annotation.Resource;
-import javax.servlet.http.HttpServletRequest;
 import java.util.ArrayList;
 import java.util.HashMap;
 import java.util.List;
@@ -49,8 +48,7 @@ public class MembershipController {
      */
     @Operation(summary = "获取我的会员信息")
     @PostMapping("/my")
-    public Result<Map<String, Object>> getMyMembership(HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<Map<String, Object>> getMyMembership(@RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("用户未登录");
         }
@@ -85,8 +83,7 @@ public class MembershipController {
      */
     @Operation(summary = "获取当前有效会员等级")
     @PostMapping("/level")
-    public Result<Map<String, Object>> getLevel(HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<Map<String, Object>> getLevel(@RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("用户未登录");
         }
@@ -110,8 +107,7 @@ public class MembershipController {
      */
     @Operation(summary = "获取当前会员等级详情")
     @PostMapping("/current")
-    public Result<MembershipLevelDTO> getCurrentLevel(HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<MembershipLevelDTO> getCurrentLevel(@RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("用户未登录");
         }
@@ -130,9 +126,8 @@ public class MembershipController {
      */
     @Operation(summary = "获取升级记录")
     @PostMapping("/records")
-    public Result<Page<MemberUpgradeRecord>> getUpgradeRecords(HttpServletRequest request,
-                                                                @RequestBody Map<String, Object> params) {
-        Long userId = getUserId(request);
+    public Result<Page<MemberUpgradeRecord>> getUpgradeRecords(@RequestBody Map<String, Object> params,
+        @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("用户未登录");
         }
@@ -153,9 +148,8 @@ public class MembershipController {
      */
     @Operation(summary = "创建会员升级订单")
     @PostMapping("/upgrade")
-    public Result<PaymentOrderDTO> upgradeOrder(HttpServletRequest request,
-                                                 @RequestBody Map<String, Object> params) {
-        Long userId = getUserId(request);
+    public Result<PaymentOrderDTO> upgradeOrder(@RequestBody Map<String, Object> params,
+        @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("用户未登录");
         }
@@ -180,8 +174,7 @@ public class MembershipController {
      */
     @Operation(summary = "激活试用会员")
     @PostMapping("/trial")
-    public Result<PaymentOrderDTO> activateTrial(HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<PaymentOrderDTO> activateTrial(@RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("用户未登录");
         }
@@ -201,9 +194,8 @@ public class MembershipController {
      */
     @Operation(summary = "创建订单")
     @PostMapping("/orders")
-    public Result<PaymentOrderDTO> createOrder(HttpServletRequest request,
-                                                @RequestBody Map<String, Object> params) {
-        Long userId = getUserId(request);
+    public Result<PaymentOrderDTO> createOrder(@RequestBody Map<String, Object> params,
+        @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("用户未登录");
         }
@@ -256,9 +248,8 @@ public class MembershipController {
      */
     @Operation(summary = "检查功能权限")
     @PostMapping("/can-use")
-    public Result<Boolean> canUseFeature(HttpServletRequest request,
-                                          @RequestBody Map<String, Object> params) {
-        Long userId = getUserId(request);
+    public Result<Boolean> canUseFeature(@RequestBody Map<String, Object> params,
+        @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("用户未登录");
         }
@@ -275,9 +266,8 @@ public class MembershipController {
      */
     @Operation(summary = "应用会员折扣")
     @PostMapping("/discount")
-    public Result<Map<String, Object>> applyDiscount(HttpServletRequest request,
-                                                      @RequestBody Map<String, Object> params) {
-        Long userId = getUserId(request);
+    public Result<Map<String, Object>> applyDiscount(@RequestBody Map<String, Object> params,
+        @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("用户未登录");
         }
@@ -292,15 +282,4 @@ public class MembershipController {
         return Result.success(result);
     }
 
-    private Long getUserId(HttpServletRequest request) {
-        Object userIdObj = request.getAttribute("userId");
-        if (userIdObj != null) {
-            return (Long) userIdObj;
-        }
-        String userIdHeader = request.getHeader("X-User-Id");
-        if (userIdHeader != null) {
-            return Long.parseLong(userIdHeader);
-        }
-        return null;
-    }
 }

+ 1 - 1
cfc-backend/src/main/java/com/etotem/cfc/controller/admin/AdminSettlementController.java

@@ -34,7 +34,7 @@ public class AdminSettlementController {
      * 结算详情
      * 服务端点:查看单条结算记录的详细信息
      */
-    @GetMapping("/detail/{settlementId}")
+    @PostMapping("/detail/{settlementId}")
     public Result<ServiceSettlement> detail(@PathVariable Long settlementId) {
         ServiceSettlement settlement = settlementService.getSettlementById(settlementId);
         return Result.success(settlement);

+ 8 - 23
cfc-backend/src/main/java/com/etotem/cfc/controller/auth/AuthController.java

@@ -168,8 +168,7 @@ public class AuthController {
 
     @Operation(summary = "获取当前用户信息")
     @PostMapping("/info")
-    public Result<User> getInfo(HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<User> getInfo(@RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("未登录");
         }
@@ -182,10 +181,9 @@ public class AuthController {
 
     @Operation(summary = "设置密码")
     @PostMapping("/set-password")
-    public Result<Boolean> setPassword(HttpServletRequest request,
-                                           @RequestBody SetPasswordDTO dto) {
-        Long userId = getUserId(request);
-        boolean success = userService.setPassword(userId, dto.getPassword());
+    public Result<Boolean> setPassword(@RequestBody SetPasswordDTO dto,
+                                       @RequestAttribute("userId") Long userId) {
+        boolean success = userService.setPassword(userId, dto.getPassword());
         return Result.success(success);
     }
 
@@ -217,10 +215,9 @@ public class AuthController {
 
     @Operation(summary = "验证密码")
     @PostMapping("/verify-password")
-    public Result<Boolean> verifyPassword(HttpServletRequest request,
-                                             @RequestBody VerifyPasswordDTO dto) {
-        Long userId = getUserId(request);
-        boolean valid = userService.verifyPassword(userId, dto.getPassword());
+    public Result<Boolean> verifyPassword(@RequestBody VerifyPasswordDTO dto,
+                                          @RequestAttribute("userId") Long userId) {
+        boolean valid = userService.verifyPassword(userId, dto.getPassword());
         return Result.success(valid);
     }
 
@@ -297,8 +294,7 @@ public class AuthController {
 
     
     @PostMapping("/switch-role")
-    public Result<LoginResultDTO> switchRole(HttpServletRequest request, @RequestBody SwitchRoleDTO dto) {
-        Long userId = getUserId(request);
+    public Result<LoginResultDTO> switchRole(@RequestBody SwitchRoleDTO dto, @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("未登录");
         }
@@ -310,15 +306,4 @@ public class AuthController {
         }
     }
 
-    private Long getUserId(HttpServletRequest request) {
-        Object userIdObj = request.getAttribute("userId");
-        if (userIdObj != null) {
-            return (Long) userIdObj;
-        }
-        String userIdHeader = request.getHeader("X-User-Id");
-        if (userIdHeader != null) {
-            return Long.parseLong(userIdHeader);
-        }
-        return null;
-    }
 }

+ 38 - 77
cfc-backend/src/main/java/com/etotem/cfc/controller/dan/DanAssessmentExecutionController.java

@@ -1,16 +1,15 @@
 package com.etotem.cfc.controller.dan;
 
 import com.etotem.cfc.common.Result;
-import com.etotem.cfc.config.JwtConfig;
-import com.etotem.cfc.dto.ExecutionDetailResponse;
-import com.etotem.cfc.dto.ServiceRateRequest;
+import com.etotem.cfc.dto.*;
 import com.etotem.cfc.entity.DanAssessmentExecution;
 import com.etotem.cfc.entity.ServiceRating;
 import com.etotem.cfc.service.DanAssessmentExecutionService;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
 import org.springframework.web.bind.annotation.*;
 
 import javax.annotation.Resource;
-import javax.servlet.http.HttpServletRequest;
 import java.util.List;
 
 /**
@@ -21,66 +20,34 @@ import java.util.List;
 @RequestMapping("/api/dan-execution")
 public class DanAssessmentExecutionController {
 
-    @Resource
-    private DanAssessmentExecutionService executionService;
+    private static final Logger log = LoggerFactory.getLogger(DanAssessmentExecutionController.class);
 
     @Resource
-    private JwtConfig jwtConfig;
+    private DanAssessmentExecutionService executionService;
 
     /**
      * 规划师/评估师完成服务
-     * 服务端点:规划师/评估师填写完成后的备注并标记完成
      */
     @PostMapping("/complete")
-    public Result<Void> complete(@RequestBody CompleteRequest req, HttpServletRequest request) {
-        String token = request.getHeader("Authorization");
-        if (token == null || !token.startsWith("Bearer ")) {
-            return Result.error("未提供认证 Token");
-        }
-        Long userId = jwtConfig.getUserIdFromToken(token.replace("Bearer ", ""));
-        if (userId == null) {
-            return Result.error("Token 无效");
-        }
-        
-        // 调用 service 完成服务(assessor/planner角色在 service 层判断)
+    public Result<Void> complete(@RequestBody CompleteRequest req, @RequestAttribute("userId") Long userId) {
         executionService.completeExecution(req.getExecutionId(), "planner", req.getNotes());
         return Result.success();
     }
 
     /**
      * 用户确认服务完成
-     * 服务端点:用户确认服务已完成,触发自动结算
      */
     @PostMapping("/confirm")
-    public Result<Void> confirm(@RequestBody ConfirmRequest req, HttpServletRequest request) {
-        String token = request.getHeader("Authorization");
-        if (token == null || !token.startsWith("Bearer ")) {
-            return Result.error("未提供认证 Token");
-        }
-        Long userId = jwtConfig.getUserIdFromToken(token.replace("Bearer ", ""));
-        if (userId == null) {
-            return Result.error("Token 无效");
-        }
-        
+    public Result<Void> confirm(@RequestBody ConfirmRequest req, @RequestAttribute("userId") Long userId) {
         executionService.confirmExecution(req.getExecutionId(), 1);
         return Result.success();
     }
 
     /**
      * 用户评价服务
-     * 服务端点:用户对评估师和规划师进行评分和评论
      */
     @PostMapping("/rate")
-    public Result<ServiceRatingDTO> rate(@RequestBody ServiceRateRequest req, HttpServletRequest request) {
-        String token = request.getHeader("Authorization");
-        if (token == null || !token.startsWith("Bearer ")) {
-            return Result.error("未提供认证 Token");
-        }
-        Long userId = jwtConfig.getUserIdFromToken(token.replace("Bearer ", ""));
-        if (userId == null) {
-            return Result.error("Token 无效");
-        }
-        
+    public Result<ServiceRatingDTO> rate(@RequestBody ServiceRateRequest req, @RequestAttribute("userId") Long userId) {
         req.setUserId(userId);
         ServiceRating rating = executionService.rateService(req);
         return Result.success(new ServiceRatingDTO(rating));
@@ -88,87 +55,82 @@ public class DanAssessmentExecutionController {
 
     /**
      * 获取执行详情(含结算信息)
-     * 服务端点:查看当前执行记录的完整状态,包括结算进度
      */
-    @GetMapping("/detail/{executionId}")
-    public Result<ExecutionDetailResponse> detail(@PathVariable Long executionId, HttpServletRequest request) {
-        ExecutionDetailResponse resp = executionService.getExecutionDetail(executionId);
+    @PostMapping("/detail")
+    public Result<ExecutionDetailResponse> detail(@RequestBody DetailRequest req) {
+        ExecutionDetailResponse resp = executionService.getExecutionDetail(req.getExecutionId());
         return Result.success(resp);
     }
 
     /**
      * 用户执行记录列表
-     * 服务端点:查看家庭所有服务的执行记录
      */
     @PostMapping("/my-list")
-    public Result<List<DanAssessmentExecution>> myList(@RequestBody MyExecutionFilter filter, HttpServletRequest request) {
-        Long userId = jwtConfig.getUserIdFromToken(request.getHeader("Authorization"));
+    public Result<List<DanAssessmentExecution>> myList(@RequestBody MyExecutionFilter filter, @RequestAttribute("userId") Long userId) {
         List<DanAssessmentExecution> executions = executionService.getByFamilyId(filter.getFamilyId());
         return Result.success(executions);
     }
 
     /**
      * 规划师待执行任务列表
-     * 服务端点:规划师查看自己负责的服务执行任务
      */
-    @GetMapping("/guide/my-tasks")
-    public Result<List<DanAssessmentExecution>> guideMyTasks(
-            @RequestParam Long plannerId, 
-            HttpServletRequest request) {
-        
-        List<DanAssessmentExecution> tasks = executionService.getByPlannerId(plannerId);
+    @PostMapping("/guide/my-tasks")
+    public Result<List<DanAssessmentExecution>> guideMyTasks(@RequestBody GuideTasksRequest req) {
+        List<DanAssessmentExecution> tasks = executionService.getByPlannerId(req.getPlannerId());
         return Result.success(tasks);
     }
 
     /**
-     * 查询某订单对应的执行记录
-     * 服务端点:根据订单 ID 获取执行记录
+     * 按订单ID查询执行记录
      */
-    @GetMapping("/by-order/{orderId}")
-    public Result<DanAssessmentExecution> getByOrder(@PathVariable Long orderId) {
-        DanAssessmentExecution exec = executionService.getByOrderId(orderId);
+    @PostMapping("/by-order")
+    public Result<DanAssessmentExecution> getByOrder(@RequestBody OrderRequest req) {
+        DanAssessmentExecution exec = executionService.getByOrderId(req.getOrderId());
         return Result.success(exec);
     }
 }
 
 // ==================== DTO 定义 ====================
 
-/**
- * 完成服务请求
- */
 class CompleteRequest {
     private Long executionId;
     private String notes;
-    
     public Long getExecutionId() { return executionId; }
     public void setExecutionId(Long executionId) { this.executionId = executionId; }
     public String getNotes() { return notes; }
     public void setNotes(String notes) { this.notes = notes; }
 }
 
-/**
- * 确认服务请求
- */
 class ConfirmRequest {
     private Long executionId;
-    
     public Long getExecutionId() { return executionId; }
     public void setExecutionId(Long executionId) { this.executionId = executionId; }
 }
 
-/**
- * 查询执行记录过滤条件
- */
 class MyExecutionFilter {
     private Long familyId;
-    
     public Long getFamilyId() { return familyId; }
     public void setFamilyId(Long familyId) { this.familyId = familyId; }
 }
 
-/**
- * 执行结果数据转换
- */
+class DetailRequest {
+    private Long executionId;
+    public Long getExecutionId() { return executionId; }
+    public void setExecutionId(Long executionId) { this.executionId = executionId; }
+}
+
+class GuideTasksRequest {
+    private Long plannerId;
+    public Long getPlannerId() { return plannerId; }
+    public void setPlannerId(Long plannerId) { this.plannerId = plannerId; }
+}
+
+class OrderRequest {
+    private Long orderId;
+    public Long getOrderId() { return orderId; }
+    public void setOrderId(Long orderId) { this.orderId = orderId; }
+}
+
 class ServiceRatingDTO {
     private Long id;
     private Long executionId;
@@ -194,7 +156,6 @@ class ServiceRatingDTO {
         this.createdAt = rating.getCreatedAt().toString();
     }
 
-    // Getters and Setters
     public Long getId() { return id; }
     public void setId(Long id) { this.id = id; }
     public Long getExecutionId() { return executionId; }
@@ -215,4 +176,4 @@ class ServiceRatingDTO {
     public void setPlannerComment(String plannerComment) { this.plannerComment = plannerComment; }
     public String getCreatedAt() { return createdAt; }
     public void setCreatedAt(String createdAt) { this.createdAt = createdAt; }
-}
+}

+ 12 - 31
cfc-backend/src/main/java/com/etotem/cfc/controller/family/FamilyInviteController.java

@@ -19,12 +19,12 @@ import io.swagger.v3.oas.annotations.tags.Tag;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.RequestAttribute;
 import org.springframework.web.bind.annotation.RequestBody;
 import org.springframework.web.bind.annotation.RequestMapping;
 import org.springframework.web.bind.annotation.RestController;
 
 import javax.annotation.Resource;
-import javax.servlet.http.HttpServletRequest;
 import java.util.Date;
 import java.util.HashMap;
 import java.util.Map;
@@ -57,8 +57,7 @@ public class FamilyInviteController {
      */
     @Operation(summary = "生成家庭邀请二维码")
     @PostMapping("/qrcode")
-    public Result<Map<String, Object>> generateQrCode(HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<Map<String, Object>> generateQrCode(@RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("请先登录");
         }
@@ -100,9 +99,8 @@ public class FamilyInviteController {
      */
     @Operation(summary = "通过邀请码加入家庭")
     @PostMapping("/accept-by-code")
-    public Result<String> acceptByCode(HttpServletRequest request,
-                                       @RequestBody Map<String, String> body) {
-        Long userId = getUserId(request);
+    public Result<String> acceptByCode(@RequestBody Map<String, String> body,
+        @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("请先登录");
         }
@@ -148,8 +146,7 @@ public class FamilyInviteController {
      */
     @Operation(summary = "生成家庭邀请")
     @PostMapping("/generate")
-    public Result<InviteGenerateDTO> generateInvite(HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<InviteGenerateDTO> generateInvite(@RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("请先登录");
         }
@@ -203,9 +200,8 @@ public class FamilyInviteController {
      */
     @Operation(summary = "接受家庭邀请")
     @PostMapping("/accept")
-    public Result<String> acceptInvite(HttpServletRequest request,
-                                       @RequestBody InviteAcceptDTO dto) {
-        Long userId = getUserId(request);
+    public Result<String> acceptInvite(@RequestBody InviteAcceptDTO dto,
+        @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("请先登录");
         }
@@ -223,8 +219,7 @@ public class FamilyInviteController {
      */
     @Operation(summary = "查询家庭状态")
     @PostMapping("/check-family")
-    public Result<FamilyStatusDTO> checkFamilyStatus(HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<FamilyStatusDTO> checkFamilyStatus(@RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("请先登录");
         }
@@ -242,9 +237,8 @@ public class FamilyInviteController {
      */
     @Operation(summary = "吊销邀请链接")
     @PostMapping("/revoke")
-    public Result<String> revokeInvite(HttpServletRequest request,
-                                       @RequestBody InviteRevokeDTO dto) {
-        Long userId = getUserId(request);
+    public Result<String> revokeInvite(@RequestBody InviteRevokeDTO dto,
+        @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("请先登录");
         }
@@ -262,9 +256,8 @@ public class FamilyInviteController {
      */
     @Operation(summary = "转让家庭管理员")
     @PostMapping("/transfer-admin")
-    public Result<String> transferAdmin(HttpServletRequest request,
-                                        @RequestBody TransferAdminDTO dto) {
-        Long userId = getUserId(request);
+    public Result<String> transferAdmin(@RequestBody TransferAdminDTO dto,
+        @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("请先登录");
         }
@@ -282,18 +275,6 @@ public class FamilyInviteController {
         }
     }
 
-    private Long getUserId(HttpServletRequest request) {
-        Object userIdObj = request.getAttribute("userId");
-        if (userIdObj != null) {
-            return (Long) userIdObj;
-        }
-        String userIdHeader = request.getHeader("X-User-Id");
-        if (userIdHeader != null) {
-            return Long.parseLong(userIdHeader);
-        }
-        return null;
-    }
-
     private String generateInviteCode() {
         String uuid = java.util.UUID.randomUUID().toString().replace("-", "").toUpperCase();
         return uuid.substring(0, 8);

+ 110 - 130
cfc-backend/src/main/java/com/etotem/cfc/controller/family/FamilyMembersController.java

@@ -11,7 +11,6 @@ import io.swagger.v3.oas.annotations.tags.Tag;
 import org.springframework.web.bind.annotation.*;
 
 import javax.annotation.Resource;
-import javax.servlet.http.HttpServletRequest;
 import java.util.List;
 import java.util.Map;
 
@@ -23,141 +22,122 @@ public class FamilyMembersController {
     @Resource
     private FamilyMemberService familyMemberService;
 
-    private Long getUserId(HttpServletRequest request) {
-        Object userIdObj = request.getAttribute("userId");
-        if (userIdObj != null) {
-            return (Long) userIdObj;
-        }
-        String userIdHeader = request.getHeader("X-User-Id");
-        if (userIdHeader != null) {
-            return Long.parseLong(userIdHeader);
-        }
-        return null;
-    }
-
-    @Operation(summary = "添加家庭成员")
-    @PostMapping("/add")
-    public Result<FamilyMemberVO> addMember(HttpServletRequest request,
-                                            @RequestBody AddFamilyMemberDTO dto) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
-        try {
-            FamilyMemberVO vo = familyMemberService.addMember(userId, dto);
-            return Result.success(vo);
-        } catch (IllegalArgumentException e) {
-            return Result.error(e.getMessage());
-        } catch (RuntimeException e) {
-            return Result.error(e.getMessage());
-        }
-    }
+@Operation(summary = "添加家庭成员")
+@PostMapping("/add")
+public Result<FamilyMemberVO> addMember(@RequestBody AddFamilyMemberDTO dto,
+ @RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
+ try {
+   FamilyMemberVO vo = familyMemberService.addMember(userId, dto);
+   return Result.success(vo);
+ } catch (IllegalArgumentException e) {
+   return Result.error(e.getMessage());
+ } catch (RuntimeException e) {
+   return Result.error(e.getMessage());
+ }
+}
 
-    @Operation(summary = "获取家庭成员列表")
-    @PostMapping("/list")
-    public Result<List<FamilyMemberVO>> listMembers(HttpServletRequest request) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
-        List<FamilyMemberVO> members = familyMemberService.listMembers(userId);
-        return Result.success(members);
-    }
+@Operation(summary = "获取家庭成员列表")
+@PostMapping("/list")
+public Result<List<FamilyMemberVO>> listMembers(@RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
+ List<FamilyMemberVO> members = familyMemberService.listMembers(userId);
+ return Result.success(members);
+}
 
-    @Operation(summary = "切换到家庭成员视图")
-    @PostMapping("/switch")
-    public Result<SwitchMemberVO> switchToMember(HttpServletRequest request,
-                                                  @RequestBody Map<String, Long> body) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
-        Long memberId = body.get("memberId");
-        if (memberId == null) {
-            return Result.error("缺少成员ID");
-        }
-        try {
-            SwitchMemberVO vo = familyMemberService.switchToMember(userId, memberId);
-            return Result.success(vo);
-        } catch (RuntimeException e) {
-            return Result.error(e.getMessage());
-        }
-    }
+@Operation(summary = "切换到家庭成员视图")
+@PostMapping("/switch")
+public Result<SwitchMemberVO> switchToMember(@RequestBody Map<String, Long> body,
+ @RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
+ Long memberId = body.get("memberId");
+ if (memberId == null) {
+   return Result.error("缺少成员ID");
+ }
+ try {
+   SwitchMemberVO vo = familyMemberService.switchToMember(userId, memberId);
+   return Result.success(vo);
+ } catch (RuntimeException e) {
+   return Result.error(e.getMessage());
+ }
+}
 
-    @Operation(summary = "踢出家庭成员")
-    @PostMapping("/kick")
-    public Result<String> kickMember(HttpServletRequest request,
-                                     @RequestBody Map<String, Long> body) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
-        Long memberId = body.get("memberId");
-        if (memberId == null) {
-            return Result.error("缺少成员ID");
-        }
-        try {
-            familyMemberService.kickMember(userId, memberId);
-            return Result.success("踢出成功");
-        } catch (RuntimeException e) {
-            return Result.error(e.getMessage());
-        }
-    }
+@Operation(summary = "踢出家庭成员")
+@PostMapping("/kick")
+public Result<String> kickMember(@RequestBody Map<String, Long> body,
+ @RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
+ Long memberId = body.get("memberId");
+ if (memberId == null) {
+   return Result.error("缺少成员ID");
+ }
+ try {
+   familyMemberService.kickMember(userId, memberId);
+   return Result.success("踢出成功");
+ } catch (RuntimeException e) {
+   return Result.error(e.getMessage());
+ }
+}
 
-    @Operation(summary = "更新成员信息")
-    @PostMapping("/update")
-    public Result<FamilyMemberVO> updateMember(HttpServletRequest request,
-                                               @RequestBody Map<String, Object> body) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
-        Long memberId = body.get("memberId") != null
-                ? Long.valueOf(body.get("memberId").toString()) : null;
-        if (memberId == null) {
-            return Result.error("缺少成员ID");
-        }
+@Operation(summary = "更新成员信息")
+@PostMapping("/update")
+public Result<FamilyMemberVO> updateMember(@RequestBody Map<String, Object> body,
+ @RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
+ Long memberId = body.get("memberId") != null
+ ? Long.valueOf(body.get("memberId").toString()) : null;
+ if (memberId == null) {
+   return Result.error("缺少成员ID");
+ }
 
-        AddFamilyMemberDTO dto = new AddFamilyMemberDTO();
-        if (body.get("nickname") != null) dto.setNickname(body.get("nickname").toString());
-        if (body.get("phone") != null) dto.setPhone(body.get("phone").toString());
-        if (body.get("avatar") != null) dto.setAvatar(body.get("avatar").toString());
-        if (body.get("gender") != null) dto.setGender(body.get("gender").toString());
-        if (body.get("birthday") != null) dto.setBirthday(body.get("birthday").toString());
+ AddFamilyMemberDTO dto = new AddFamilyMemberDTO();
+ if (body.get("nickname") != null) dto.setNickname(body.get("nickname").toString());
+ if (body.get("phone") != null) dto.setPhone(body.get("phone").toString());
+ if (body.get("avatar") != null) dto.setAvatar(body.get("avatar").toString());
+ if (body.get("gender") != null) dto.setGender(body.get("gender").toString());
+ if (body.get("birthday") != null) dto.setBirthday(body.get("birthday").toString());
 
-        try {
-            FamilyMemberVO vo = familyMemberService.updateMember(userId, memberId, dto);
-            return Result.success(vo);
-        } catch (RuntimeException e) {
-            return Result.error(e.getMessage());
-        }
-    }
+ try {
+   FamilyMemberVO vo = familyMemberService.updateMember(userId, memberId, dto);
+   return Result.success(vo);
+ } catch (RuntimeException e) {
+   return Result.error(e.getMessage());
+ }
+}
 
-    @Operation(summary = "检查成员是否可编辑")
-    @PostMapping("/editable")
-    public Result<Boolean> checkEditable(HttpServletRequest request,
-                                          @RequestBody Map<String, Long> body) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
-        Long memberId = body.get("memberId");
-        if (memberId == null) {
-            return Result.error("缺少成员ID");
-        }
-        boolean editable = familyMemberService.isEditable(memberId);
-        return Result.success(editable);
-    }
+@Operation(summary = "检查成员是否可编辑")
+@PostMapping("/editable")
+public Result<Boolean> checkEditable(@RequestBody Map<String, Long> body,
+ @RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
+ Long memberId = body.get("memberId");
+ if (memberId == null) {
+   return Result.error("缺少成员ID");
+ }
+ boolean editable = familyMemberService.isEditable(memberId);
+ return Result.success(editable);
+}
 
-    @Operation(summary = "查询成员变更日志")
-    @PostMapping("/logs")
-    public Result<List<FamilyMemberLog>> logs(HttpServletRequest request,
-                                              @RequestBody Map<String, Long> body) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
-        Long memberId = body != null ? body.get("memberId") : null;
-        return familyMemberService.getMemberLogs(userId, memberId);
-    }
+@Operation(summary = "查询成员变更日志")
+@PostMapping("/logs")
+public Result<List<FamilyMemberLog>> logs(@RequestBody Map<String, Long> body,
+ @RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
+ Long memberId = body != null ? body.get("memberId") : null;
+ return familyMemberService.getMemberLogs(userId, memberId);
+}
 }

+ 29 - 57
cfc-backend/src/main/java/com/etotem/cfc/controller/family/FamilyUserController.java

@@ -13,6 +13,7 @@ import com.etotem.cfc.service.UserService;
 import io.swagger.v3.oas.annotations.Operation;
 import io.swagger.v3.oas.annotations.tags.Tag;
 import javax.annotation.Resource;
+import org.springframework.web.bind.annotation.RequestAttribute;
 import org.springframework.web.bind.annotation.*;
 
 import java.util.Date;
@@ -37,42 +38,25 @@ public class FamilyUserController {
     @Resource
     private FamilyMemberMapper familyMemberMapper;
 
-    private Long getUserId(javax.servlet.http.HttpServletRequest request) {
-        // 从请求属性中获取用户ID(由拦截器设置)
-        Object userIdObj = request.getAttribute("userId");
-        if (userIdObj != null) {
-            return (Long) userIdObj;
-        }
-        // 兼容从请求头获取
-        String userIdHeader = request.getHeader("X-User-Id");
-        if (userIdHeader != null) {
-            return Long.parseLong(userIdHeader);
-        }
-        return null;
-    }
-
     @Operation(summary = "获取用户信息")
     @PostMapping("/info")
-    public Result<User> getUserInfo(javax.servlet.http.HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<User> getUserInfo(@RequestAttribute("userId") Long userId) {
         User user = userService.getUserInfo(userId);
         return Result.success(user);
     }
 
     @Operation(summary = "更新用户信息")
     @PostMapping("/update")
-    public Result<Boolean> updateUserInfo(javax.servlet.http.HttpServletRequest request,
-                                          @RequestBody UpdateUserDTO dto) {
-        Long userId = getUserId(request);
+    public Result<Boolean> updateUserInfo(@RequestAttribute("userId") Long userId,
+        @RequestBody UpdateUserDTO dto) {
         boolean success = userService.updateUserInfo(userId, dto);
         return Result.success(success);
     }
 
     @Operation(summary = "加入家庭(通过邀请码)")
     @PostMapping("/join-family")
-    public Result<Boolean> joinFamily(javax.servlet.http.HttpServletRequest request,
-                                      @RequestBody Map<String, String> body) {
-        Long userId = getUserId(request);
+    public Result<Boolean> joinFamily(@RequestAttribute("userId") Long userId,
+        @RequestBody Map<String, String> body) {
         String inviteCode = body.get("inviteCode");
         boolean success = userService.joinFamily(userId, inviteCode);
         return Result.success(success);
@@ -80,9 +64,8 @@ public class FamilyUserController {
 
     @Operation(summary = "创建新家庭")
     @PostMapping("/create-family")
-    public Result<Long> createFamily(javax.servlet.http.HttpServletRequest request,
-                                     @RequestBody Map<String, String> body) {
-        Long userId = getUserId(request);
+    public Result<Long> createFamily(@RequestAttribute("userId") Long userId,
+        @RequestBody Map<String, String> body) {
         String familyName = body.getOrDefault("name", "我的家庭");
         Long familyId = userService.createFamilyForUser(userId, familyName);
         return Result.success(familyId);
@@ -90,16 +73,15 @@ public class FamilyUserController {
 
     @Operation(summary = "切换家长/孩子模式(已废弃,使用 /api/family/member/switch)")
     @PostMapping("/switch-mode")
-    public Result<String> switchMode(javax.servlet.http.HttpServletRequest request,
-                                     @RequestBody Map<String, String> body) {
+    public Result<String> switchMode(@RequestAttribute("userId") Long userId,
+        @RequestBody Map<String, String> body) {
         return Result.error(410, "该接口已废弃,请使用 /api/family/member/switch");
     }
 
     @Operation(summary = "切换用户角色 (支持 parent/child/teacher)")
     @PostMapping("/switch-role")
-    public Result<String> switchRole(javax.servlet.http.HttpServletRequest request,
-                                      @RequestBody Map<String, String> body) {
-        Long userId = getUserId(request);
+    public Result<String> switchRole(@RequestAttribute("userId") Long userId,
+        @RequestBody Map<String, String> body) {
         String role = body.get("role");
         String result = userService.switchRole(userId, role);
         if (result == null) {
@@ -110,32 +92,29 @@ public class FamilyUserController {
 
     @Operation(summary = "获取用户所有角色列表")
     @PostMapping("/roles")
-    public Result<List<String>> getUserRoles(javax.servlet.http.HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<List<String>> getUserRoles(@RequestAttribute("userId") Long userId) {
         List<String> roles = userService.getUserRoles(userId);
         return Result.success(roles);
     }
 
     @Operation(summary = "家长切换到指定孩子身份(已废弃,使用 /api/family/member/switch)")
     @PostMapping("/switch-to-child")
-    public Result<Long> switchToFamilyMember(javax.servlet.http.HttpServletRequest request,
-                                       @RequestBody Map<String, Long> body) {
+    public Result<Long> switchToFamilyMember(@RequestAttribute("userId") Long userId,
+        @RequestBody Map<String, Long> body) {
         return Result.error(410, "该接口已废弃,请使用 /api/family/member/switch");
     }
 
     @Operation(summary = "孩子切换回家长身份")
     @PostMapping("/switch-back-to-parent")
-    public Result<Boolean> switchBackToParent(javax.servlet.http.HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<Boolean> switchBackToParent(@RequestAttribute("userId") Long userId) {
         boolean result = userService.switchBackToParent(userId);
         return Result.success(result);
     }
 
     @Operation(summary = "带密码校验切换回家长视角")
     @PostMapping("/switch-back-verify")
-    public Result<Boolean> switchBackVerify(javax.servlet.http.HttpServletRequest request,
-                                            @RequestBody Map<String, String> body) {
-        Long userId = getUserId(request);
+    public Result<Boolean> switchBackVerify(@RequestAttribute("userId") Long userId,
+        @RequestBody Map<String, String> body) {
         if (userId == null) {
             return Result.error("请先登录");
         }
@@ -152,26 +131,23 @@ public class FamilyUserController {
 
     @Operation(summary = "创建孩子")
     @PostMapping("/children")
-    public Result<FamilyMemberInfoDTO> createFamilyMember(javax.servlet.http.HttpServletRequest request,
-                                            @RequestBody CreateFamilyMemberDTO dto) {
-        Long userId = getUserId(request);
+    public Result<FamilyMemberInfoDTO> createFamilyMember(@RequestAttribute("userId") Long userId,
+        @RequestBody CreateFamilyMemberDTO dto) {
         FamilyMemberInfoDTO child = userService.createFamilyMember(userId, dto);
         return Result.success(child);
     }
 
     @Operation(summary = "获取孩子列表")
     @PostMapping("/children/list")
-    public Result<List<FamilyMemberInfoDTO>> getFamilyMemberren(javax.servlet.http.HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<List<FamilyMemberInfoDTO>> getFamilyMemberren(@RequestAttribute("userId") Long userId) {
         List<FamilyMemberInfoDTO> children = userService.getFamilyMemberren(userId);
         return Result.success(children);
     }
 
     @Operation(summary = "更新孩子信息")
     @PostMapping("/children/update")
-    public Result<Boolean> updateFamilyMember(javax.servlet.http.HttpServletRequest request,
-                                       @RequestBody UpdateFamilyMemberDTO dto) {
-        Long userId = getUserId(request);
+    public Result<Boolean> updateFamilyMember(@RequestAttribute("userId") Long userId,
+        @RequestBody UpdateFamilyMemberDTO dto) {
         Long childId = dto.getFamilyMemberId();
         boolean success = userService.updateFamilyMember(userId, childId, dto);
         return Result.success(success);
@@ -179,8 +155,7 @@ public class FamilyUserController {
 
     @Operation(summary = "获取家庭成员列表")
     @PostMapping("/family-members")
-    public Result<Map<String, Object>> getFamilyMembers(javax.servlet.http.HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<Map<String, Object>> getFamilyMembers(@RequestAttribute("userId") Long userId) {
         User user = userMapper.selectById(userId);
 
         if (user == null) {
@@ -224,17 +199,15 @@ public class FamilyUserController {
 
     @Operation(summary = "获取对家庭成员可见的成员列表")
     @PostMapping("/members/visible")
-    public Result<List<FamilyMemberVO>> getVisibleMembers(javax.servlet.http.HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<List<FamilyMemberVO>> getVisibleMembers(@RequestAttribute("userId") Long userId) {
         List<FamilyMemberVO> members = userService.getVisibleMembers(userId);
         return Result.success(members);
     }
 
     @Operation(summary = "更新成员可见性")
     @PostMapping("/members/update-visibility")
-    public Result<Boolean> updateVisibility(javax.servlet.http.HttpServletRequest request,
-                                            @RequestBody Map<String, Object> body) {
-        Long userId = getUserId(request);
+    public Result<Boolean> updateVisibility(@RequestAttribute("userId") Long userId,
+        @RequestBody Map<String, Object> body) {
         Long memberId = Long.valueOf(body.get("memberId").toString());
         String memberType = (String) body.get("memberType");
         Integer showToFamily = Integer.valueOf(body.get("showToFamily").toString());
@@ -244,9 +217,8 @@ public class FamilyUserController {
 
     @Operation(summary = "踢出家庭成员(仅管理员可操作)")
     @PostMapping("/kick")
-    public Result<Boolean> kickMember(javax.servlet.http.HttpServletRequest request,
-                                      @RequestBody Map<String, Long> body) {
-        Long userId = getUserId(request);
+    public Result<Boolean> kickMember(@RequestAttribute("userId") Long userId,
+        @RequestBody Map<String, Long> body) {
         Long targetUserId = body.get("targetUserId");
         if (targetUserId == null) {
             return Result.error("缺少目标用户ID");

+ 23 - 38
cfc-backend/src/main/java/com/etotem/cfc/controller/family/InteractionLogController.java

@@ -10,7 +10,6 @@ import io.swagger.v3.oas.annotations.tags.Tag;
 import org.springframework.web.bind.annotation.*;
 
 import javax.annotation.Resource;
-import javax.servlet.http.HttpServletRequest;
 import java.util.Map;
 
 @Tag(name = "互动记录管理", description = "家庭成员互动记录 CRUD")
@@ -21,44 +20,30 @@ public class InteractionLogController {
     @Resource
     private InteractionLogService interactionLogService;
 
-    private Long getUserId(HttpServletRequest request) {
-        Object userIdObj = request.getAttribute("userId");
-        if (userIdObj != null) {
-            return (Long) userIdObj;
-        }
-        String userIdHeader = request.getHeader("X-User-Id");
-        if (userIdHeader != null) {
-            return Long.parseLong(userIdHeader);
-        }
-        return null;
-    }
-
-    @Operation(summary = "添加互动记录")
-    @PostMapping("/add")
-    public Result<InteractionLogVO> addInteraction(HttpServletRequest request,
-                                                     @RequestBody AddInteractionDTO dto) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
-        try {
-            InteractionLogVO vo = interactionLogService.addInteraction(dto);
-            return Result.success(vo);
-        } catch (IllegalArgumentException e) {
-            return Result.error(e.getMessage());
-        } catch (RuntimeException e) {
-            return Result.error(e.getMessage());
-        }
-    }
+@Operation(summary = "添加互动记录")
+@PostMapping("/add")
+public Result<InteractionLogVO> addInteraction(@RequestBody AddInteractionDTO dto,
+ @RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
+ try {
+   InteractionLogVO vo = interactionLogService.addInteraction(dto);
+   return Result.success(vo);
+ } catch (IllegalArgumentException e) {
+   return Result.error(e.getMessage());
+ } catch (RuntimeException e) {
+   return Result.error(e.getMessage());
+ }
+}
 
-    @Operation(summary = "查询互动记录列表")
-    @PostMapping("/list")
-    public Result<Page<InteractionLogVO>> listInteractions(HttpServletRequest request,
-                                                            @RequestBody Map<String, Object> body) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
+@Operation(summary = "查询互动记录列表")
+@PostMapping("/list")
+public Result<Page<InteractionLogVO>> listInteractions(@RequestBody Map<String, Object> body,
+ @RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
         Long familyId = body.get("familyId") != null
                 ? Long.valueOf(body.get("familyId").toString()) : null;
         Long fromMemberId = body.get("fromMemberId") != null

+ 40 - 57
cfc-backend/src/main/java/com/etotem/cfc/controller/family/RelationshipQualityController.java

@@ -12,7 +12,6 @@ import io.swagger.v3.oas.annotations.tags.Tag;
 import org.springframework.web.bind.annotation.*;
 
 import javax.annotation.Resource;
-import javax.servlet.http.HttpServletRequest;
 import java.util.Collections;
 import java.util.List;
 import java.util.Map;
@@ -28,55 +27,41 @@ public class RelationshipQualityController {
     @Resource
     private UserMapper userMapper;
 
-    private Long getUserId(HttpServletRequest request) {
-        Object userIdObj = request.getAttribute("userId");
-        if (userIdObj != null) {
-            return (Long) userIdObj;
-        }
-        String userIdHeader = request.getHeader("X-User-Id");
-        if (userIdHeader != null) {
-            return Long.parseLong(userIdHeader);
-        }
-        return null;
-    }
+private Long getFamilyIdFromRequest(Long userId, Map<String, Object> body) {
+ // 优先从请求体获取
+ if (body != null && body.get("familyId") != null) {
+   try {
+     return Long.valueOf(body.get("familyId").toString());
+   } catch (NumberFormatException e) {
+     // familyId不是有效数字(如前端传了{}),fallthrough到JWT用户推导
+   }
+ }
+ // 从JWT用户推导
+ if (userId == null) {
+   return null;
+ }
+ User user = userMapper.selectById(userId);
+ if (user == null) {
+   return null;
+ }
+ return user.getFamilyId();
+}
 
-    private Long getFamilyIdFromRequest(HttpServletRequest request, Map<String, Object> body) {
-        // 优先从请求体获取
-        if (body != null && body.get("familyId") != null) {
-            try {
-                return Long.valueOf(body.get("familyId").toString());
-            } catch (NumberFormatException e) {
-                // familyId不是有效数字(如前端传了{}),fallthrough到JWT用户推导
-            }
-        }
-        // 从JWT用户推导
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return null;
-        }
-        User user = userMapper.selectById(userId);
-        if (user == null) {
-            return null;
-        }
-        return user.getFamilyId();
-    }
-
-    @Operation(summary = "获取家庭成员关系质量评分")
-    @PostMapping("/scores")
-    public Result<List<RelationshipScoreVO>> getScores(HttpServletRequest request,
-                                                        @RequestBody Map<String, Object> body) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
-        Long familyId = body.get("familyId") != null
-                ? Long.valueOf(body.get("familyId").toString()) : null;
-        if (familyId == null) {
-            return Result.error("familyId不能为空");
-        }
-        List<RelationshipScoreVO> scores = relationshipQualityService.getScores(familyId);
-        return Result.success(scores);
-    }
+@Operation(summary = "获取家庭成员关系质量评分")
+@PostMapping("/scores")
+public Result<List<RelationshipScoreVO>> getScores(@RequestBody Map<String, Object> body,
+@RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
+ Long familyId = body.get("familyId") != null
+ ? Long.valueOf(body.get("familyId").toString()) : null;
+ if (familyId == null) {
+   return Result.error("familyId不能为空");
+ }
+ List<RelationshipScoreVO> scores = relationshipQualityService.getScores(familyId);
+ return Result.success(scores);
+}
 
     @Operation(summary = "计算并保存成员关系质量评分")
     @PostMapping("/calculate")
@@ -96,13 +81,12 @@ public class RelationshipQualityController {
 
     @Operation(summary = "获取健康预警列表")
     @PostMapping("/health-alerts")
-    public Result<List<HealthAlertVO>> getHealthAlerts(HttpServletRequest request,
-                                                       @RequestBody Map<String, Object> body) {
-        Long userId = getUserId(request);
+    public Result<List<HealthAlertVO>> getHealthAlerts(@RequestBody Map<String, Object> body,
+                                                       @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("请先登录");
         }
-        Long familyId = getFamilyIdFromRequest(request, body);
+        Long familyId = getFamilyIdFromRequest(userId, body);
         if (familyId == null) {
             return Result.success(Collections.emptyList());
         }
@@ -112,13 +96,12 @@ public class RelationshipQualityController {
 
     @Operation(summary = "获取即将到来的里程碑")
     @PostMapping("/milestones")
-    public Result<List<MilestoneVO>> getMilestones(HttpServletRequest request,
-                                                   @RequestBody Map<String, Object> body) {
-        Long userId = getUserId(request);
+    public Result<List<MilestoneVO>> getMilestones(@RequestBody Map<String, Object> body,
+                                                   @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("请先登录");
         }
-        Long familyId = getFamilyIdFromRequest(request, body);
+        Long familyId = getFamilyIdFromRequest(userId, body);
         if (familyId == null) {
             return Result.success(Collections.emptyList());
         }

+ 62 - 79
cfc-backend/src/main/java/com/etotem/cfc/controller/family/RelationshipQuestionnaireController.java

@@ -11,7 +11,6 @@ import io.swagger.v3.oas.annotations.tags.Tag;
 import org.springframework.web.bind.annotation.*;
 
 import javax.annotation.Resource;
-import javax.servlet.http.HttpServletRequest;
 import java.util.List;
 import java.util.Map;
 
@@ -23,85 +22,69 @@ public class RelationshipQuestionnaireController {
     @Resource
     private RelationshipQuestionnaireService questionnaireService;
 
-    private Long getUserId(HttpServletRequest request) {
-        Object userIdObj = request.getAttribute("userId");
-        if (userIdObj != null) {
-            return (Long) userIdObj;
-        }
-        String userIdHeader = request.getHeader("X-User-Id");
-        if (userIdHeader != null) {
-            return Long.parseLong(userIdHeader);
-        }
-        return null;
-    }
+@Operation(summary = "AI 生成关系问卷")
+@PostMapping("/generate")
+public Result<QuestionnaireSnapshotVO> generateQuestionnaire(@RequestBody GenerateQuestionnaireDTO dto,
+ @RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
+ dto.setRespondentId(userId);
+ try {
+   QuestionnaireSnapshotVO vo = questionnaireService.generateQuestionnaire(dto);
+   return Result.success(vo);
+ } catch (IllegalArgumentException e) {
+   return Result.error(e.getMessage());
+ } catch (RuntimeException e) {
+   return Result.error(e.getMessage());
+ }
+}
 
-    @Operation(summary = "AI 生成关系问卷")
-    @PostMapping("/generate")
-    public Result<QuestionnaireSnapshotVO> generateQuestionnaire(HttpServletRequest request,
-                                                                    @RequestBody GenerateQuestionnaireDTO dto) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
-        dto.setRespondentId(userId);
-        try {
-            QuestionnaireSnapshotVO vo = questionnaireService.generateQuestionnaire(dto);
-            return Result.success(vo);
-        } catch (IllegalArgumentException e) {
-            return Result.error(e.getMessage());
-        } catch (RuntimeException e) {
-            return Result.error(e.getMessage());
-        }
-    }
+@Operation(summary = "提交问卷答案")
+@PostMapping("/submit")
+public Result<RelationshipQuestionnaireResponse> submitQuestionnaire(@RequestBody SubmitQuestionnaireDTO dto,
+ @RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
+ dto.setRespondentId(userId);
+ try {
+   RelationshipQuestionnaireResponse resp = questionnaireService.submitQuestionnaire(dto);
+   return Result.success(resp);
+ } catch (IllegalArgumentException e) {
+   return Result.error(e.getMessage());
+ } catch (RuntimeException e) {
+   return Result.error(e.getMessage());
+ }
+}
 
-    @Operation(summary = "提交问卷答案")
-    @PostMapping("/submit")
-    public Result<RelationshipQuestionnaireResponse> submitQuestionnaire(HttpServletRequest request,
-                                                                           @RequestBody SubmitQuestionnaireDTO dto) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
-        dto.setRespondentId(userId);
-        try {
-            RelationshipQuestionnaireResponse resp = questionnaireService.submitQuestionnaire(dto);
-            return Result.success(resp);
-        } catch (IllegalArgumentException e) {
-            return Result.error(e.getMessage());
-        } catch (RuntimeException e) {
-            return Result.error(e.getMessage());
-        }
-    }
+@Operation(summary = "获取最新问卷快照")
+@PostMapping("/snapshot/{memberId}")
+public Result<QuestionnaireSnapshotVO> getSnapshot(@PathVariable Long memberId,
+ @RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
+ try {
+   QuestionnaireSnapshotVO vo = questionnaireService.getSnapshot(memberId);
+   return Result.success(vo);
+ } catch (IllegalArgumentException e) {
+   return Result.error(e.getMessage());
+ }
+}
 
-    @Operation(summary = "获取最新问卷快照")
-    @PostMapping("/snapshot/{memberId}")
-    public Result<QuestionnaireSnapshotVO> getSnapshot(HttpServletRequest request,
-                                                        @PathVariable Long memberId) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
-        try {
-            QuestionnaireSnapshotVO vo = questionnaireService.getSnapshot(memberId);
-            return Result.success(vo);
-        } catch (IllegalArgumentException e) {
-            return Result.error(e.getMessage());
-        }
-    }
-
-    @Operation(summary = "获取问卷历史记录")
-    @PostMapping("/history/{memberId}")
-    public Result<List<RelationshipQuestionnaireResponse>> getHistory(HttpServletRequest request,
-                                                                        @PathVariable Long memberId) {
-        Long userId = getUserId(request);
-        if (userId == null) {
-            return Result.error("请先登录");
-        }
-        try {
-            List<RelationshipQuestionnaireResponse> history = questionnaireService.getHistory(memberId);
-            return Result.success(history);
-        } catch (IllegalArgumentException e) {
-            return Result.error(e.getMessage());
-        }
-    }
+@Operation(summary = "获取问卷历史记录")
+@PostMapping("/history/{memberId}")
+public Result<List<RelationshipQuestionnaireResponse>> getHistory(@PathVariable Long memberId,
+ @RequestAttribute("userId") Long userId) {
+ if (userId == null) {
+   return Result.error("请先登录");
+ }
+ try {
+   List<RelationshipQuestionnaireResponse> history = questionnaireService.getHistory(memberId);
+   return Result.success(history);
+ } catch (IllegalArgumentException e) {
+   return Result.error(e.getMessage());
+ }
+}
 }

+ 11 - 30
cfc-backend/src/main/java/com/etotem/cfc/controller/guide/GuideController.java

@@ -13,7 +13,6 @@ import com.etotem.cfc.service.InviteCardService;
 import org.springframework.web.bind.annotation.*;
 
 import javax.annotation.Resource;
-import javax.servlet.http.HttpServletRequest;
 
 import java.util.List;
 import java.util.Map;
@@ -45,9 +44,8 @@ public class GuideController {
     }
 
     @PostMapping("/apply/new")
-    public Result<Boolean> applyNew(HttpServletRequest request,
-                                    @RequestBody Map<String, Object> params) {
-        Long userId = getUserId(request);
+    public Result<Boolean> applyNew(@RequestBody Map<String, Object> params,
+        @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("未登录");
         }
@@ -58,9 +56,8 @@ public class GuideController {
     }
 
     @PostMapping("/apply/upgrade")
-    public Result<Boolean> applyUpgrade(HttpServletRequest request,
-                                        @RequestBody Map<String, Object> params) {
-        Long userId = getUserId(request);
+    public Result<Boolean> applyUpgrade(@RequestBody Map<String, Object> params,
+        @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("未登录");
         }
@@ -71,8 +68,7 @@ public class GuideController {
     }
 
     @PostMapping("/my")
-    public Result<Guide> getMyGuide(HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<Guide> getMyGuide(@RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("未登录");
         }
@@ -80,8 +76,7 @@ public class GuideController {
     }
 
     @PostMapping("/applications/my")
-    public Result<List<GuideApplication>> getMyApplications(HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<List<GuideApplication>> getMyApplications(@RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("未登录");
         }
@@ -92,8 +87,7 @@ public class GuideController {
     }
 
     @PostMapping("/my/packages")
-    public Result<List<GuidePackage>> getMyPackages(HttpServletRequest request) {
-        Long userId = getUserId(request);
+    public Result<List<GuidePackage>> getMyPackages(@RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("未登录");
         }
@@ -114,9 +108,8 @@ public class GuideController {
     }
 
     @PostMapping("/parent-invite/generate")
-    public Result<Map<String, Object>> generateParentInvite(HttpServletRequest request,
-                                                             @RequestBody Map<String, Object> params) {
-        Long userId = getUserId(request);
+    public Result<Map<String, Object>> generateParentInvite(@RequestBody Map<String, Object> params,
+        @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("未登录");
         }
@@ -135,9 +128,8 @@ public class GuideController {
     }
 
     @PostMapping("/parent-invite/accept")
-    public Result<Map<String, Object>> acceptParentInvite(HttpServletRequest request,
-                                                           @RequestBody Map<String, Object> params) {
-        Long userId = getUserId(request);
+    public Result<Map<String, Object>> acceptParentInvite(@RequestBody Map<String, Object> params,
+        @RequestAttribute("userId") Long userId) {
         if (userId == null) {
             return Result.error("未登录");
         }
@@ -148,15 +140,4 @@ public class GuideController {
         return inviteCardService.acceptParentInvite(code, userId);
     }
 
-    private Long getUserId(HttpServletRequest request) {
-        Object userIdObj = request.getAttribute("userId");
-        if (userIdObj != null) {
-            return (Long) userIdObj;
-        }
-        String userIdHeader = request.getHeader("X-User-Id");
-        if (userIdHeader != null) {
-            return Long.parseLong(userIdHeader);
-        }
-        return null;
-    }
 }