TASK:1.日志记录简化 2. stylist参数变更 3.user添加查询用户数据接口

This commit is contained in:
2025-10-28 15:33:00 +08:00
parent dab9e0b396
commit 4601e87c73
14 changed files with 156 additions and 60 deletions

View File

@@ -10,6 +10,7 @@ import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes; import org.springframework.web.context.request.ServletRequestAttributes;
import jakarta.servlet.http.HttpServletRequest; import jakarta.servlet.http.HttpServletRequest;
import java.util.Arrays; import java.util.Arrays;
/** /**
@@ -28,13 +29,15 @@ public class LoggingAspect {
* 定义切点所有Controller方法 * 定义切点所有Controller方法
*/ */
@Pointcut("execution(* com.aida.lanecarford.controller..*(..))") @Pointcut("execution(* com.aida.lanecarford.controller..*(..))")
public void controllerMethods() {} public void controllerMethods() {
}
/** /**
* 定义切点所有Service方法 * 定义切点所有Service方法
*/ */
@Pointcut("execution(* com.aida.lanecarford.service..*(..))") @Pointcut("execution(* com.aida.lanecarford.service..*(..))")
public void serviceMethods() {} public void serviceMethods() {
}
/** /**
* Controller方法执行前记录日志 * Controller方法执行前记录日志
@@ -49,7 +52,8 @@ public class LoggingAspect {
logger.info("请求URL: {}", request.getRequestURL().toString()); logger.info("请求URL: {}", request.getRequestURL().toString());
logger.info("请求方法: {}", request.getMethod()); logger.info("请求方法: {}", request.getMethod());
logger.info("请求IP: {}", getClientIpAddress(request)); logger.info("请求IP: {}", getClientIpAddress(request));
logger.info("调用方法: {}.{}", joinPoint.getSignature().getDeclaringTypeName(), joinPoint.getSignature().getName()); // logger.info("调用方法: {}.{}", joinPoint.getSignature().getDeclaringTypeName(), joinPoint.getSignature().getName());
logger.info("调用方法: {}.{}", joinPoint.getSignature().getDeclaringType().getSimpleName(), joinPoint.getSignature().getName());
logger.info("请求参数: {}", Arrays.toString(joinPoint.getArgs())); logger.info("请求参数: {}", Arrays.toString(joinPoint.getArgs()));
} }
} }
@@ -59,7 +63,7 @@ public class LoggingAspect {
*/ */
@AfterReturning(pointcut = "controllerMethods()", returning = "result") @AfterReturning(pointcut = "controllerMethods()", returning = "result")
public void logControllerAfterReturning(JoinPoint joinPoint, Object result) { public void logControllerAfterReturning(JoinPoint joinPoint, Object result) {
logger.info("方法执行成功: {}.{}", joinPoint.getSignature().getDeclaringTypeName(), joinPoint.getSignature().getName()); logger.info("方法执行成功: {}.{}", joinPoint.getSignature().getDeclaringType().getSimpleName(), joinPoint.getSignature().getName());
logger.info("返回结果: {}", result); logger.info("返回结果: {}", result);
logger.info("=== 请求结束 ==="); logger.info("=== 请求结束 ===");
} }
@@ -69,7 +73,7 @@ public class LoggingAspect {
*/ */
@AfterThrowing(pointcut = "controllerMethods()", throwing = "exception") @AfterThrowing(pointcut = "controllerMethods()", throwing = "exception")
public void logControllerAfterThrowing(JoinPoint joinPoint, Throwable exception) { public void logControllerAfterThrowing(JoinPoint joinPoint, Throwable exception) {
logger.error("方法执行异常: {}.{}", joinPoint.getSignature().getDeclaringTypeName(), joinPoint.getSignature().getName()); logger.error("方法执行异常: {}.{}", joinPoint.getSignature().getDeclaringType().getSimpleName(), joinPoint.getSignature().getName());
logger.error("异常信息: ", exception); logger.error("异常信息: ", exception);
logger.info("=== 请求异常结束 ==="); logger.info("=== 请求异常结束 ===");
} }
@@ -80,8 +84,8 @@ public class LoggingAspect {
@Around("serviceMethods()") @Around("serviceMethods()")
public Object logServiceAround(ProceedingJoinPoint joinPoint) throws Throwable { public Object logServiceAround(ProceedingJoinPoint joinPoint) throws Throwable {
long startTime = System.currentTimeMillis(); long startTime = System.currentTimeMillis();
String methodName = joinPoint.getSignature().getDeclaringTypeName() + "." + joinPoint.getSignature().getName(); // String methodName = joinPoint.getSignature().getDeclaringTypeName() + "." + joinPoint.getSignature().getName();
String methodName = joinPoint.getSignature().getDeclaringType().getSimpleName() + "." + joinPoint.getSignature().getName();
try { try {
logger.debug("Service方法开始执行: {}", methodName); logger.debug("Service方法开始执行: {}", methodName);
Object result = joinPoint.proceed(); Object result = joinPoint.proceed();

View File

@@ -22,7 +22,7 @@ public class PerformanceAspect {
/** /**
* 监控Controller方法性能 * 监控Controller方法性能
*/ */
@Around("execution(* com.aida.lanecarford.controller..*(..))") // @Around("execution(* com.aida.lanecarford.controller..*(..))")
public Object monitorControllerPerformance(ProceedingJoinPoint joinPoint) throws Throwable { public Object monitorControllerPerformance(ProceedingJoinPoint joinPoint) throws Throwable {
return monitorMethodPerformance(joinPoint, "Controller"); return monitorMethodPerformance(joinPoint, "Controller");
} }
@@ -30,7 +30,7 @@ public class PerformanceAspect {
/** /**
* 监控Service方法性能 * 监控Service方法性能
*/ */
@Around("execution(* com.aida.lanecarford.service..*(..))") // @Around("execution(* com.aida.lanecarford.service..*(..))")
public Object monitorServicePerformance(ProceedingJoinPoint joinPoint) throws Throwable { public Object monitorServicePerformance(ProceedingJoinPoint joinPoint) throws Throwable {
return monitorMethodPerformance(joinPoint, "Service"); return monitorMethodPerformance(joinPoint, "Service");
} }
@@ -38,7 +38,7 @@ public class PerformanceAspect {
/** /**
* 监控数据库操作性能 * 监控数据库操作性能
*/ */
@Around("execution(* com.aida.lanecarford.mapper..*(..))") // @Around("execution(* com.aida.lanecarford.mapper..*(..))")
public Object monitorMapperPerformance(ProceedingJoinPoint joinPoint) throws Throwable { public Object monitorMapperPerformance(ProceedingJoinPoint joinPoint) throws Throwable {
return monitorMethodPerformance(joinPoint, "Mapper"); return monitorMethodPerformance(joinPoint, "Mapper");
} }

View File

@@ -1,6 +1,7 @@
package com.aida.lanecarford.common.enums; package com.aida.lanecarford.common.enums;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.AllArgsConstructor; import lombok.AllArgsConstructor;
import lombok.Getter; import lombok.Getter;
@@ -8,13 +9,18 @@ import java.util.stream.Stream;
@Getter @Getter
@AllArgsConstructor @AllArgsConstructor
@Schema(description = "生成状态枚举")
public enum StatusEnum { public enum StatusEnum {
@Schema(description = "等待中")
PENDING(0), PENDING(0),
@Schema(description = "成功")
SUCCEEDED(1), SUCCEEDED(1),
@Schema(description = "失败")
FAILED(2), FAILED(2),
@Schema(description = "运行中")
RUNNING(3); RUNNING(3);
private int code; private int code;
@@ -24,5 +30,4 @@ public enum StatusEnum {
} }
} }

View File

@@ -2,6 +2,7 @@ package com.aida.lanecarford.controller;
import com.aida.lanecarford.common.ApiResponse; import com.aida.lanecarford.common.ApiResponse;
import com.aida.lanecarford.dto.LoginRequest; import com.aida.lanecarford.dto.LoginRequest;
import com.aida.lanecarford.entity.User;
import com.aida.lanecarford.service.LoginService; import com.aida.lanecarford.service.LoginService;
import com.aida.lanecarford.vo.LoginVO; import com.aida.lanecarford.vo.LoginVO;
import io.swagger.v3.oas.annotations.Hidden; import io.swagger.v3.oas.annotations.Hidden;
@@ -86,4 +87,13 @@ public class LoginController {
} }
} }
@Operation(
summary = "获取用户信息",
description = "通过token获取当前用户信息"
)
@GetMapping("/getUserInfo")
public ApiResponse<User> getUserInfo() {
return ApiResponse.success(loginService.getUserInfo());
}
} }

View File

@@ -5,17 +5,15 @@ import lombok.Data;
import jakarta.validation.constraints.Max; import jakarta.validation.constraints.Max;
import jakarta.validation.constraints.Min; import jakarta.validation.constraints.Min;
import java.io.Serializable; import java.io.Serializable;
/** /**
* 请求参数基类 * 请求参数基类
*
* @author AI Assistant
* @since 2024-01-01
*/ */
@Data @Data
@Schema(description = "请求参数基类") @Schema(description = "请求参数基类")
public abstract class BaseRequest implements Serializable { public class BaseRequest implements Serializable {
private static final long serialVersionUID = 1L; private static final long serialVersionUID = 1L;

View File

@@ -3,6 +3,7 @@ package com.aida.lanecarford.dto;
import lombok.Data; import lombok.Data;
import java.util.List; import java.util.List;
import java.util.Map;
@Data @Data
public class OutfitCallbackDTO { public class OutfitCallbackDTO {
@@ -14,5 +15,5 @@ public class OutfitCallbackDTO {
private String path; private String path;
private List<String> items; private List<Map<String, String>> items;
} }

View File

@@ -26,4 +26,6 @@ public interface LoginService extends IService<User> {
void forgotPwd(LoginRequest loginRequest); void forgotPwd(LoginRequest loginRequest);
boolean checkLoginStatus(); boolean checkLoginStatus();
User getUserInfo();
} }

View File

@@ -3,6 +3,7 @@ package com.aida.lanecarford.service.impl;
import com.aida.lanecarford.common.constant.RedisURIConstants; import com.aida.lanecarford.common.constant.RedisURIConstants;
import com.aida.lanecarford.common.enums.AuthenticationOperationTypeEnum; import com.aida.lanecarford.common.enums.AuthenticationOperationTypeEnum;
import com.aida.lanecarford.common.enums.LanguageEnum; import com.aida.lanecarford.common.enums.LanguageEnum;
import com.aida.lanecarford.common.response.ResultEnum;
import com.aida.lanecarford.common.security.JwtUtil; import com.aida.lanecarford.common.security.JwtUtil;
import com.aida.lanecarford.common.security.context.UserContext; import com.aida.lanecarford.common.security.context.UserContext;
import com.aida.lanecarford.dto.LoginRequest; import com.aida.lanecarford.dto.LoginRequest;
@@ -246,11 +247,18 @@ public class LoginServiceImpl extends ServiceImpl<UserMapper, User> implements L
return false; return false;
} }
// 谷歌登录 // todo 谷歌登录
// 获取用户信息
public User getUserInfo() {
AuthPrincipalVO userHolder = UserContext.getUserHolder();
User user = getById(userHolder.getId());
if (Objects.isNull(user)) {
throw new BusinessException("User information cannot be found", ResultEnum.ERROR.getCode());
}
return user;
}
} }

View File

@@ -64,7 +64,7 @@ public class StyleServiceImpl extends ServiceImpl<StyleMapper, Style> implements
outfitRequest.setGender(requestOutfitDTO.getGender()); outfitRequest.setGender(requestOutfitDTO.getGender());
outfitRequestMapper.insert(outfitRequest); outfitRequestMapper.insert(outfitRequest);
String response = SendRequestUtil.sendPost(CommonConstants.REQUEST_OUTFIT, JSON.toJSONString(params)); String response = SendRequestUtil.sendPostWithRetry(CommonConstants.REQUEST_OUTFIT, JSON.toJSONString(params));
JSONObject jsonObject = JSONObject.parseObject(response); // todo 确认这里的status的取值 JSONObject jsonObject = JSONObject.parseObject(response); // todo 确认这里的status的取值
if (Objects.isNull(response) /*|| !jsonObject.getString("status").equals("ok")*/) { if (Objects.isNull(response) /*|| !jsonObject.getString("status").equals("ok")*/) {

View File

@@ -53,6 +53,61 @@ public class SendRequestUtil {
throw new BusinessException("System error (External interface failure)"); throw new BusinessException("System error (External interface failure)");
} }
public static String sendPostWithRetry(String url, String requestBodyStr) {
return sendPost(url, requestBodyStr, 3, 1000); // 默认重试3次间隔1秒
}
public static String sendPost(String url, String requestBodyStr, int maxRetries, long retryInterval) {
int status = 0;
String body = null;
int retryCount = 0;
while (retryCount <= maxRetries) {
try {
log.debug("发送POST请求URL: {}, 重试次数: {}/{}", url, retryCount, maxRetries);
HttpResponse execute = HttpRequest.post(url)
.header("Content-Type", "application/json")
.body(requestBodyStr)
.timeout(180000)
.execute();
status = execute.getStatus();
body = execute.body();
if (status == 200) {
log.debug("请求成功URL: {}, 状态码: {}", url, status);
return body;
} else {
log.warn("请求返回非200状态码URL: {}, 状态码: {}, Body: {}", url, status, body);
}
} catch (Exception e) {
log.warn("请求发生异常URL: {}, 异常信息: {}, 重试次数: {}/{}",
url, e.getMessage(), retryCount, maxRetries);
}
// 判断是否继续重试
if (retryCount < maxRetries) {
retryCount++;
try {
log.debug("等待 {}ms 后重试...", retryInterval);
Thread.sleep(retryInterval);
// 可选:递增重试间隔(指数退避)
retryInterval = (long) (retryInterval * 1.5);
} catch (InterruptedException ie) {
Thread.currentThread().interrupt();
throw new RuntimeException("重试被中断", ie);
}
} else {
break;
}
}
log.error("请求最终失败URL: {}, 最大重试次数: {}, 最后状态码: {}, 最后响应: {}",
url, maxRetries, status, body);
return null;
}
} }

View File

@@ -7,6 +7,7 @@ import lombok.extern.slf4j.Slf4j;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
import java.util.Map;
@Slf4j @Slf4j
public class StringListConverter { public class StringListConverter {
@@ -16,7 +17,7 @@ public class StringListConverter {
/** /**
* 将 List<String> 转换为 JSON 字符串 * 将 List<String> 转换为 JSON 字符串
*/ */
public static String listToJson(List<String> list) { public static String listToJson(List<Map<String, String>> list) {
if (list == null || list.isEmpty()) { if (list == null || list.isEmpty()) {
return "[]"; return "[]";
} }
@@ -31,12 +32,13 @@ public class StringListConverter {
/** /**
* 将 JSON 字符串转换为 List<String> * 将 JSON 字符串转换为 List<String>
*/ */
public static List<String> jsonToList(String json) { public static List<Map<String, String>> jsonToList(String json) {
if (json == null || json.trim().isEmpty()) { if (json == null || json.trim().isEmpty()) {
return new ArrayList<>(); return new ArrayList<>();
} }
try { try {
return objectMapper.readValue(json, new TypeReference<List<String>>() {}); return objectMapper.readValue(json, new TypeReference<>() {
});
} catch (JsonProcessingException e) { } catch (JsonProcessingException e) {
log.error("JSON转List失败: {}", json, e); log.error("JSON转List失败: {}", json, e);
throw new RuntimeException("JSON转List失败", e); throw new RuntimeException("JSON转List失败", e);

View File

@@ -1,18 +1,29 @@
package com.aida.lanecarford.vo; package com.aida.lanecarford.vo;
import com.aida.lanecarford.common.enums.StatusEnum;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data; import lombok.Data;
import lombok.NoArgsConstructor; import lombok.NoArgsConstructor;
@Data @Data
@NoArgsConstructor @NoArgsConstructor
@Schema(description = "AI穿搭推荐结果响应参数")
public class OutfitResultVO { public class OutfitResultVO {
@Schema(description = "记录ID", example = "21")
private Long id; private Long id;
@Schema(description = "请求ID", example = "7c30e8f6-fdc6-4699-9239-ae6a9d3cf948")
private String requestId; private String requestId;
@Schema(description = "图片路径", example = "https://example.com/images/outfit_123.jpg")
private String path; private String path;
@Schema(
description = "处理状态",
implementation = StatusEnum.class,
requiredMode = Schema.RequiredMode.REQUIRED
)
private String status; private String status;
public OutfitResultVO(Long id, String requestId, String status) { public OutfitResultVO(Long id, String requestId, String status) {

View File

@@ -45,7 +45,7 @@ spring:
mybatis-plus: mybatis-plus:
configuration: configuration:
map-underscore-to-camel-case: true map-underscore-to-camel-case: true
log-impl: org.apache.ibatis.logging.stdout.StdOutImpl # log-impl: org.apache.ibatis.logging.stdout.StdOutImpl
global-config: global-config:
db-config: db-config:
logic-delete-field: deleted logic-delete-field: deleted

View File

@@ -1,6 +1,6 @@
-- Lane Carford AI系统基础架构数据库表结构 -- Lane Carford AI系统基础架构数据库表结构
-- 创建数据库 -- 创建数据库
CREATE DATABASE IF NOT EXISTS lanecarford CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci; CREATE DATABASE IF NOT EXISTS lanecrawford CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
USE lanecrawford; USE lanecrawford;
-- 1. 用户表 -- 1. 用户表