diff --git a/build.gradle b/build.gradle index 1266a52..f307ee0 100644 --- a/build.gradle +++ b/build.gradle @@ -28,6 +28,8 @@ repositories { } dependencies { + implementation 'org.springframework.boot:spring-boot-starter' + implementation 'org.springframework.boot:spring-boot-starter-web' implementation 'org.springframework.boot:spring-boot-starter-data-jdbc' implementation 'org.springframework.boot:spring-boot-starter-security' implementation 'org.springframework.boot:spring-boot-starter-thymeleaf' @@ -49,8 +51,12 @@ dependencies { testImplementation 'org.mybatis.spring.boot:mybatis-spring-boot-starter-test:3.0.4' testImplementation 'org.springframework.security:spring-security-test' testRuntimeOnly 'org.junit.platform:junit-platform-launcher' + implementation 'com.huaban:jieba-analysis:1.0.2' + implementation 'org.aspectj:aspectjweaver:1.9.19' + implementation 'org.springframework:spring-aop:6.1.0' + implementation 'javax.servlet:javax.servlet-api:4.0.1' } tasks.named('test') { useJUnitPlatform() -} +} \ No newline at end of file diff --git a/src/main/java/com/example/copykamanotes/NotesApplication.java b/src/main/java/com/example/copykamanotes/NotesApplication.java index 446aff1..1b544e7 100644 --- a/src/main/java/com/example/copykamanotes/NotesApplication.java +++ b/src/main/java/com/example/copykamanotes/NotesApplication.java @@ -2,8 +2,10 @@ package com.example.copykamanotes; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; +import org.springframework.scheduling.annotation.EnableScheduling; @SpringBootApplication(scanBasePackages = "com.example.copykamanotes") +@EnableScheduling public class NotesApplication { public static void main(String[] args) { diff --git a/src/main/java/com/example/copykamanotes/aspect/NeedLoginAspect.java b/src/main/java/com/example/copykamanotes/aspect/NeedLoginAspect.java new file mode 100644 index 0000000..4ce089a --- /dev/null +++ b/src/main/java/com/example/copykamanotes/aspect/NeedLoginAspect.java @@ -0,0 +1,31 @@ +package com.example.copykamanotes.aspect; + +import com.example.copykamanotes.annotation.NeedLogin; +import com.example.copykamanotes.scope.RequestScopeData; +import com.example.copykamanotes.utils.ApiResponseUtils; +import org.aspectj.lang.ProceedingJoinPoint; +import org.aspectj.lang.annotation.Around; +import org.aspectj.lang.annotation.Aspect; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Component; + +@Aspect +@Component +public class NeedLoginAspect { + + @Autowired + private RequestScopeData requestScopeData; + + @Around("@annotation(needLogin)") + public Object around(ProceedingJoinPoint joinPoint, NeedLogin needLogin) throws Throwable { + + if (!requestScopeData.isLogin()) { + return ApiResponseUtils.error("请先登录"); + } + + if (requestScopeData.getUserId() == null ) { + return ApiResponseUtils.error("用户不存在"); + } + return joinPoint.proceed(); + } +} diff --git a/src/main/java/com/example/copykamanotes/config/SecurityConfig.java b/src/main/java/com/example/copykamanotes/config/SecurityConfig.java index 13e8650..dcca82a 100644 --- a/src/main/java/com/example/copykamanotes/config/SecurityConfig.java +++ b/src/main/java/com/example/copykamanotes/config/SecurityConfig.java @@ -5,6 +5,7 @@ import org.springframework.context.annotation.Configuration; import org.springframework.http.HttpMethod; import org.springframework.security.config.annotation.web.builders.HttpSecurity; import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; +import org.springframework.security.config.annotation.web.configurers.AbstractHttpConfigurer; import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder; import org.springframework.security.crypto.password.PasswordEncoder; import org.springframework.security.web.SecurityFilterChain; @@ -23,7 +24,7 @@ public class SecurityConfig { .requestMatchers("/api/**").permitAll() // 允许 /api/** 路径下的所有请求 .anyRequest().authenticated() // 其他请求需要认证 ) - .csrf(csrf -> csrf.disable()); // 根据需要禁用 CSRF + .csrf(AbstractHttpConfigurer::disable); // 根据需要禁用 CSRF return http.build(); } diff --git a/src/main/java/com/example/copykamanotes/config/WebConfig.java b/src/main/java/com/example/copykamanotes/config/WebConfig.java index a3f2ba9..13f34cc 100644 --- a/src/main/java/com/example/copykamanotes/config/WebConfig.java +++ b/src/main/java/com/example/copykamanotes/config/WebConfig.java @@ -1,9 +1,14 @@ package com.example.copykamanotes.config; +import com.example.copykamanotes.filter.TraceIdFilter; import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.boot.web.servlet.FilterRegistrationBean; +import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.web.servlet.config.annotation.CorsRegistry; import org.springframework.web.servlet.config.annotation.InterceptorRegistry; +import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; import com.example.copykamanotes.interceptor.TokenInterceptor; @@ -13,6 +18,14 @@ public class WebConfig implements WebMvcConfigurer { @Autowired private TokenInterceptor tokenInterceptor; + @Value("${upload.path:D:/kamaNotes/upload") + private String uploadPath; + + @Override + public void addResourceHandlers(ResourceHandlerRegistry registry) { + registry.addResourceHandler("/images/**") + .addResourceLocations("file:" + uploadPath + "/"); + } /** * 添加拦截器, 拦截所有请求,除了登录和注册 @@ -35,4 +48,11 @@ public class WebConfig implements WebMvcConfigurer { .maxAge(3600); } + @Bean + public FilterRegistrationBean traceIdFilter() { + FilterRegistrationBean registrationBean = new FilterRegistrationBean<>(); + registrationBean.setFilter(new TraceIdFilter()); + registrationBean.addUrlPatterns("/*"); + return registrationBean; + } } diff --git a/src/main/java/com/example/copykamanotes/filter/TraceIdFilter.java b/src/main/java/com/example/copykamanotes/filter/TraceIdFilter.java new file mode 100644 index 0000000..8795002 --- /dev/null +++ b/src/main/java/com/example/copykamanotes/filter/TraceIdFilter.java @@ -0,0 +1,34 @@ +package com.example.copykamanotes.filter; + +import org.slf4j.MDC; + +import jakarta.servlet.Filter; +import jakarta.servlet.FilterChain; +import jakarta.servlet.FilterConfig; +import jakarta.servlet.ServletException; +import jakarta.servlet.ServletRequest; +import jakarta.servlet.ServletResponse; +import java.io.IOException; + +public class TraceIdFilter implements Filter { + private static final String TRACE_ID_KEY = "trace_id"; + + @Override + public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { + try { + chain.doFilter(request, response); + } finally { + MDC.remove(TRACE_ID_KEY); + } + } + + @Override + public void init(FilterConfig filterConfig) throws ServletException { + Filter.super.init(filterConfig); + } + + @Override + public void destroy() { + Filter.super.destroy(); + } +} diff --git a/src/main/java/com/example/copykamanotes/service/impl/NoteServiceImpl.java b/src/main/java/com/example/copykamanotes/service/impl/NoteServiceImpl.java index 39c7ff7..77f759f 100644 --- a/src/main/java/com/example/copykamanotes/service/impl/NoteServiceImpl.java +++ b/src/main/java/com/example/copykamanotes/service/impl/NoteServiceImpl.java @@ -16,9 +16,9 @@ import com.example.copykamanotes.service.NoteLikeService; import com.example.copykamanotes.service.NoteService; import com.example.copykamanotes.service.QuestionService; import com.example.copykamanotes.service.UserService; -import com.example.copykamanotes.utils.ApiResponseUtil; -import com.example.copykamanotes.utils.MarkdownUtil; -import com.example.copykamanotes.utils.PaginationUtil; +import com.example.copykamanotes.utils.ApiResponseUtils; +import com.example.copykamanotes.utils.MarkdownUtils; +import com.example.copykamanotes.utils.PaginationUtils; import org.springframework.beans.BeanUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; @@ -48,7 +48,7 @@ public class NoteServiceImpl implements NoteService { @Override public ApiResponse> getNotes(NoteQueryParams noteQueryParams) { - int offset = PaginationUtil.calculateOffset(noteQueryParams.getPage(), noteQueryParams.getPageSize()); + int offset = PaginationUtils.calculateOffset(noteQueryParams.getPage(), noteQueryParams.getPageSize()); int total = noteMapper.countNotes(noteQueryParams); @@ -105,9 +105,9 @@ public class NoteServiceImpl implements NoteService { userActionsVO.setIsCollected(true); } - if (MarkdownUtil.needCollapsed(note.getContent())) { + if (MarkdownUtils.needCollapsed(note.getContent())) { noteVO.setNeedCollapsed(true); - noteVO.setDisplayContent(MarkdownUtil.extractIntroduction(note.getContent())); + noteVO.setDisplayContent(MarkdownUtils.extractIntroduction(note.getContent())); } else { noteVO.setNeedCollapsed(false); } @@ -116,9 +116,9 @@ public class NoteServiceImpl implements NoteService { return noteVO; }).toList(); - return ApiResponseUtil.success("获取笔记列表成功", noteVOs, pagination); + return ApiResponseUtils.success("获取笔记列表成功", noteVOs, pagination); } catch (Exception e) { - return ApiResponseUtil.error("获取笔记列表失败"); + return ApiResponseUtils.error("获取笔记列表失败"); } } diff --git a/src/main/java/com/example/copykamanotes/service/impl/UploadServiceImpl.java b/src/main/java/com/example/copykamanotes/service/impl/UploadServiceImpl.java index 95d927a..a19e113 100644 --- a/src/main/java/com/example/copykamanotes/service/impl/UploadServiceImpl.java +++ b/src/main/java/com/example/copykamanotes/service/impl/UploadServiceImpl.java @@ -4,7 +4,7 @@ import com.example.copykamanotes.model.base.ApiResponse; import com.example.copykamanotes.model.vo.upload.ImageVO; import com.example.copykamanotes.service.FileService; import com.example.copykamanotes.service.UploadService; -import com.example.copykamanotes.utils.ApiResponseUtil; +import com.example.copykamanotes.utils.ApiResponseUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import org.springframework.web.multipart.MultipartFile; @@ -20,6 +20,6 @@ public class UploadServiceImpl implements UploadService { String url = fileService.uploadImage(file); ImageVO imageVO = new ImageVO(); imageVO.setUrl(url); - return ApiResponseUtil.success("上传成功", imageVO); + return ApiResponseUtils.success("上传成功", imageVO); } } diff --git a/src/main/java/com/example/copykamanotes/service/impl/UserServiceImpl.java b/src/main/java/com/example/copykamanotes/service/impl/UserServiceImpl.java index f2da4a7..affba6a 100644 --- a/src/main/java/com/example/copykamanotes/service/impl/UserServiceImpl.java +++ b/src/main/java/com/example/copykamanotes/service/impl/UserServiceImpl.java @@ -17,10 +17,9 @@ import com.example.copykamanotes.scope.RequestScopeData; import com.example.copykamanotes.service.EmailService; import com.example.copykamanotes.service.FileService; import com.example.copykamanotes.service.UserService; -import com.example.copykamanotes.utils.ApiResponseUtil; +import com.example.copykamanotes.utils.ApiResponseUtils; import com.example.copykamanotes.utils.JwtUtil; -import com.example.copykamanotes.utils.PaginationUtil; -import com.google.protobuf.Api; +import com.example.copykamanotes.utils.PaginationUtils; import lombok.extern.log4j.Log4j2; import org.springframework.beans.BeanUtils; import org.springframework.beans.factory.annotation.Autowired; @@ -62,14 +61,14 @@ public class UserServiceImpl implements UserService { public ApiResponse register(RegisterRequest registerRequest) { User existingUser = userMapper.findByAccount(registerRequest.getAccount()); if (existingUser != null) { - return ApiResponseUtil.error("账号重复"); + return ApiResponseUtils.error("账号重复"); } if (registerRequest.getEmail() != null && !registerRequest.getEmail().isEmpty()) { // 验证邮箱是否重复 existingUser = userMapper.findByEmail(registerRequest.getEmail()); if (existingUser != null) { - return ApiResponseUtil.error("邮箱重复"); + return ApiResponseUtils.error("邮箱重复"); } // if (registerRequest.getVerifyCode() == null || registerRequest.getVerifyCode().isEmpty()) { @@ -95,10 +94,10 @@ public class UserServiceImpl implements UserService { BeanUtils.copyProperties(user, registerVO); userMapper.updateLastLoginAt(user.getUserId()); - return ApiResponseUtil.success("注册成功", registerVO, token); + return ApiResponseUtils.success("注册成功", registerVO, token); } catch (Exception e) { log.error("注册失败", e); - return ApiResponseUtil.error("注册失败,请稍后再试"); + return ApiResponseUtils.error("注册失败,请稍后再试"); } } @@ -111,15 +110,15 @@ public class UserServiceImpl implements UserService { } else if (loginRequest.getEmail() != null && !loginRequest.getEmail().isEmpty()) { user = userMapper.findByEmail(loginRequest.getEmail()); } else { - return ApiResponseUtil.error("账号或邮箱不能为空"); + return ApiResponseUtils.error("账号或邮箱不能为空"); } if (user == null) { - return ApiResponseUtil.error("账号或邮箱不存在"); + return ApiResponseUtils.error("账号或邮箱不存在"); } if (!passwordEncoder.matches(loginRequest.getPassword(), user.getPassword())) { - return ApiResponseUtil.error("密码错误"); + return ApiResponseUtils.error("密码错误"); } String token = jwtUtil.generateToken(user.getUserId()); @@ -129,7 +128,7 @@ public class UserServiceImpl implements UserService { userMapper.updateLastLoginAt(user.getUserId()); - return ApiResponseUtil.success("登录成功", loginUserVO, token); + return ApiResponseUtils.success("登录成功", loginUserVO, token); } @Override @@ -137,26 +136,26 @@ public class UserServiceImpl implements UserService { Long userId = requestScopeData.getUserId(); if (userId == null) { - return ApiResponseUtil.error("未登录"); + return ApiResponseUtils.error("未登录"); } try { User user = userMapper.findById(userId); if (user == null) { - return ApiResponseUtil.error("用户不存在"); + return ApiResponseUtils.error("用户不存在"); } String newToken = jwtUtil.generateToken(userId); if (newToken == null) { - return ApiResponseUtil.error("token生成失败"); + return ApiResponseUtils.error("token生成失败"); } LoginUserVO loginUserVO = new LoginUserVO(); BeanUtils.copyProperties(user, loginUserVO); - return ApiResponseUtil.success("获取用户信息成功", loginUserVO, newToken); + return ApiResponseUtils.success("获取用户信息成功", loginUserVO, newToken); } catch (Exception e) { log.error("获取用户信息失败", e); - return ApiResponseUtil.error("获取用户信息失败"); + return ApiResponseUtils.error("获取用户信息失败"); } } @@ -165,12 +164,12 @@ public class UserServiceImpl implements UserService { User user = userMapper.findById(userId); if (user == null) { - return ApiResponseUtil.error("用户不存在"); + return ApiResponseUtils.error("用户不存在"); } UserVO userVO = new UserVO(); BeanUtils.copyProperties(user, userVO); - return ApiResponseUtil.success("获取用户信息成功", userVO); + return ApiResponseUtils.success("获取用户信息成功", userVO); } @Override @@ -180,7 +179,7 @@ public class UserServiceImpl implements UserService { Long userId = requestScopeData.getUserId(); if (userId == null) { - return ApiResponseUtil.error("未登录"); + return ApiResponseUtils.error("未登录"); } User user = new User(); @@ -189,10 +188,10 @@ public class UserServiceImpl implements UserService { try { userMapper.update(user); - return ApiResponseUtil.success("更新用户信息成功"); + return ApiResponseUtils.success("更新用户信息成功"); } catch (Exception e) { log.error("更新用户信息失败", e); - return ApiResponseUtil.error("更新用户信息失败"); + return ApiResponseUtils.error("更新用户信息失败"); } } @@ -210,15 +209,15 @@ public class UserServiceImpl implements UserService { // 分页数据 int total = userMapper.countByQueryParam(userQueryParam); - int offset = PaginationUtil.calculateOffset(userQueryParam.getPage(), userQueryParam.getPageSize()); + int offset = PaginationUtils.calculateOffset(userQueryParam.getPage(), userQueryParam.getPageSize()); Pagination pagination = new Pagination(userQueryParam.getPage(), userQueryParam.getPageSize(), total); try { List users = userMapper.findByQueryParam(userQueryParam, userQueryParam.getPageSize(), offset); - return ApiResponseUtil.success("获取用户列表成功", users, pagination); + return ApiResponseUtils.success("获取用户列表成功", users, pagination); } catch (Exception e) { - return ApiResponseUtil.error(e.getMessage()); + return ApiResponseUtils.error(e.getMessage()); } } @@ -228,10 +227,10 @@ public class UserServiceImpl implements UserService { String url = fileService.uploadImage(file); AvatarVO avatarVO = new AvatarVO(); avatarVO.setAvatarUrl(url); - return ApiResponseUtil.success("上传成功", avatarVO); + return ApiResponseUtils.success("上传成功", avatarVO); } catch (Exception e) { log.error("上传失败", e); - return ApiResponseUtil.error("上传失败"); + return ApiResponseUtils.error("上传失败"); } } @@ -240,27 +239,27 @@ public class UserServiceImpl implements UserService { Long userId = requestScopeData.getUserId(); if (userId == null) { - return ApiResponseUtil.error("未登录"); + return ApiResponseUtils.error("未登录"); } User user = null; user = userMapper.findById(userId); if (user == null || !passwordEncoder.matches(oldPassword, user.getPassword())) { - return ApiResponseUtil.error("旧密码错误"); + return ApiResponseUtils.error("旧密码错误"); } if (Objects.equals(oldPassword, newPassword)) { - return ApiResponseUtil.error("新密码不能与旧密码相同"); + return ApiResponseUtils.error("新密码不能与旧密码相同"); } user.setPassword(passwordEncoder.encode(newPassword)); try { userMapper.updatePassword(user.getUserId(), user.getPassword()); - return ApiResponseUtil.success("更新密码成功"); + return ApiResponseUtils.success("更新密码成功"); } catch (Exception e) { log.error("更新密码失败", e); - return ApiResponseUtil.error("更新密码失败"); + return ApiResponseUtils.error("更新密码失败"); } } } diff --git a/src/main/java/com/example/copykamanotes/utils/ApiResponseUtil.java b/src/main/java/com/example/copykamanotes/utils/ApiResponseUtils.java similarity index 97% rename from src/main/java/com/example/copykamanotes/utils/ApiResponseUtil.java rename to src/main/java/com/example/copykamanotes/utils/ApiResponseUtils.java index b88ec53..7f4576f 100644 --- a/src/main/java/com/example/copykamanotes/utils/ApiResponseUtil.java +++ b/src/main/java/com/example/copykamanotes/utils/ApiResponseUtils.java @@ -7,7 +7,7 @@ import com.example.copykamanotes.model.base.PaginationApiResponse; import com.example.copykamanotes.model.base.TokenApiResponse; import org.springframework.http.HttpStatus; -public class ApiResponseUtil { +public class ApiResponseUtils { /** * 构建成功的响应 diff --git a/src/main/java/com/example/copykamanotes/utils/JwtUtil.java b/src/main/java/com/example/copykamanotes/utils/JwtUtil.java index 8c7d3af..8811e46 100644 --- a/src/main/java/com/example/copykamanotes/utils/JwtUtil.java +++ b/src/main/java/com/example/copykamanotes/utils/JwtUtil.java @@ -44,8 +44,9 @@ public class JwtUtil { */ public Long getUserIdFromToken(String token) { try { - Claims claims = Jwts.parser() - .setSigningKey(SECRET_KEY) + Claims claims = Jwts + .parserBuilder() + .setSigningKey(SECRET_KEY).build() .parseClaimsJws(token) .getBody(); return Long.valueOf(claims.get("userId").toString()); @@ -60,7 +61,8 @@ public class JwtUtil { */ public boolean validateToken(String token) { try { - Jwts.parser().setSigningKey(secret).parseClaimsJws(token); + Jwts.parserBuilder().setSigningKey(SECRET_KEY).build().parseClaimsJws(token); +// Jwts.parser().setSigningKey(secret).parseClaimsJws(token); return true; } catch (Exception e) { return false; diff --git a/src/main/java/com/example/copykamanotes/utils/MarkdownAST.java b/src/main/java/com/example/copykamanotes/utils/MarkdownAST.java index 83e52b7..3c9a8c1 100644 --- a/src/main/java/com/example/copykamanotes/utils/MarkdownAST.java +++ b/src/main/java/com/example/copykamanotes/utils/MarkdownAST.java @@ -15,20 +15,24 @@ public class MarkdownAST { private final Document markdownAST; private final String markdownText; - public MarkdownAST( String markdownText) { + // 构造函数:初始化并解析 Markdown文本 + public MarkdownAST(String markdownText) { this.markdownText = markdownText; Parser parser = Parser.builder().build(); + // 解析 Markdown 文本 this.markdownAST = parser.parse(markdownText); } public String extractIntroduction(int maxChars) { StringBuilder introText = new StringBuilder(); - + // 遍历 AST 节点,提取文本内容 for (Node node : markdownAST.getChildren()) { if (node instanceof Heading || node instanceof Paragraph) { + // 获取节点的文本内容 String renderedText = getNoteText(node); + // 计算剩余字符数,并截取文本 int remainingChars = maxChars - introText.length(); introText.append(renderedText, 0, Math.min(remainingChars, renderedText.length())); @@ -41,26 +45,30 @@ public class MarkdownAST { return introText.toString().trim() + "..."; } + // 检查Markdown文本中是否包含图片 public List extractImages() { - List images = new ArrayList<>(); + List imageUrls = new ArrayList<>(); for (Node node : markdownAST.getChildren()) { if (node instanceof Image imageNode) { - images.add(((Image) node).getUrl().toString()); + imageUrls.add(imageNode.getUrl().toString()); } } - return images; + return imageUrls; } + // 检查Markdown文本是否需要折叠 public boolean shouldCollapse(int maxChars) { return hasImages() || markdownText.length() > maxChars; } + // 获取折叠后的Markdown文本 public String getCollapseMarkdown() { String introText = extractIntroduction(150); return introText + "..."; } + // 获取节点的文本内容 private String getNoteText(Node node) { StringBuilder text = new StringBuilder(); @@ -74,6 +82,7 @@ public class MarkdownAST { return text.toString(); } + // 检查Markdown文本中是否包含图片 private boolean hasImages() { return !extractImages().isEmpty(); } diff --git a/src/main/java/com/example/copykamanotes/utils/MarkdownUtil.java b/src/main/java/com/example/copykamanotes/utils/MarkdownUtil.java index b854242..b9c7c22 100644 --- a/src/main/java/com/example/copykamanotes/utils/MarkdownUtil.java +++ b/src/main/java/com/example/copykamanotes/utils/MarkdownUtil.java @@ -1,6 +1,7 @@ package com.example.copykamanotes.utils; public class MarkdownUtil { + public static boolean needCollapsed(String markdown) { MarkdownAST ast = new MarkdownAST(markdown); return ast.shouldCollapse(250); diff --git a/src/main/java/com/example/copykamanotes/utils/MarkdownUtils.java b/src/main/java/com/example/copykamanotes/utils/MarkdownUtils.java new file mode 100644 index 0000000..f884aa7 --- /dev/null +++ b/src/main/java/com/example/copykamanotes/utils/MarkdownUtils.java @@ -0,0 +1,13 @@ +package com.example.copykamanotes.utils; + +public class MarkdownUtils { + public static boolean needCollapsed(String markdown) { + MarkdownAST ast = new MarkdownAST(markdown); + return ast.shouldCollapse(250); + } + + public static String extractIntroduction(String markdown) { + MarkdownAST ast = new MarkdownAST(markdown); + return ast.extractIntroduction(250); + } +} diff --git a/src/main/java/com/example/copykamanotes/utils/PaginationUtil.java b/src/main/java/com/example/copykamanotes/utils/PaginationUtils.java similarity index 95% rename from src/main/java/com/example/copykamanotes/utils/PaginationUtil.java rename to src/main/java/com/example/copykamanotes/utils/PaginationUtils.java index 4256432..e50e12c 100644 --- a/src/main/java/com/example/copykamanotes/utils/PaginationUtil.java +++ b/src/main/java/com/example/copykamanotes/utils/PaginationUtils.java @@ -1,6 +1,6 @@ package com.example.copykamanotes.utils; -public class PaginationUtil { +public class PaginationUtils { /** * 计算分页参数 * diff --git a/src/main/java/com/example/copykamanotes/utils/SearchUtils.java b/src/main/java/com/example/copykamanotes/utils/SearchUtils.java new file mode 100644 index 0000000..6c82271 --- /dev/null +++ b/src/main/java/com/example/copykamanotes/utils/SearchUtils.java @@ -0,0 +1,37 @@ +package com.example.copykamanotes.utils; + +import com.huaban.analysis.jieba.JiebaSegmenter; +import org.springframework.util.StringUtils; + +import java.util.List; + +public class SearchUtils { + private static final JiebaSegmenter segmenter = new JiebaSegmenter(); + + /** + * 预处理搜索关键词 + * @param keyword + * @return + */ + public static String preprocessKeyword(String keyword) { + if (!StringUtils.hasText(keyword)) { + return ""; + } + + keyword = keyword.replaceAll("[\\p{P}\\p{S}]", " "); + + List words = segmenter.sentenceProcess(keyword); + + return String.join(" ", words); + } + + /** + * 计算分页的偏移量 + * @param page + * @param pageSize + * @return + */ + public static int calculateOffset(int page, int pageSize) { + return Math.max(0, (page - 1) * pageSize); + } +} diff --git a/src/main/java/com/example/copykamanotes/utils/SecurityUtil.java b/src/main/java/com/example/copykamanotes/utils/SecurityUtils.java similarity index 97% rename from src/main/java/com/example/copykamanotes/utils/SecurityUtil.java rename to src/main/java/com/example/copykamanotes/utils/SecurityUtils.java index de31195..f42fd1c 100644 --- a/src/main/java/com/example/copykamanotes/utils/SecurityUtil.java +++ b/src/main/java/com/example/copykamanotes/utils/SecurityUtils.java @@ -4,7 +4,7 @@ import com.example.copykamanotes.model.entity.User; import org.springframework.security.core.Authentication; import org.springframework.security.core.context.SecurityContextHolder; -public class SecurityUtil { +public class SecurityUtils { /** * 获取当前登录用户的ID *