diff --git a/chaos_api_common/src/main/java/cn/nopj/chaos_api/common/constants/ErrorCode.java b/chaos_api_common/src/main/java/cn/nopj/chaos_api/common/constants/ErrorCode.java index 8596607..4c1efc9 100644 --- a/chaos_api_common/src/main/java/cn/nopj/chaos_api/common/constants/ErrorCode.java +++ b/chaos_api_common/src/main/java/cn/nopj/chaos_api/common/constants/ErrorCode.java @@ -30,6 +30,9 @@ public enum ErrorCode { PHONE_EXISTS(409, "USER-109", "手机号已注册"), PHONE_FORMAT_ERROR(400, "USER-110", "手机号格式无效"), USER_UPDATE_USERNAME_FAILED(400,"USER-111" , "用户名更新失败"), + + USER_UPDATE_NICKNAME_FAILED( 400, "USER-112", "用户昵称更新失败" ), + USER_UPDATE_PROFILE_FAILED(400,"USER-113" , "用户信息更新失败" ), // 用户组 ROLE_REVOKE_FAILED(400,"USER-112" ,"用户组删除失败" ), @@ -58,10 +61,7 @@ public enum ErrorCode { DEVICE_DELETE_FAILED(500, "DEVICE-303", "设备删除失败"), DEVICE_TYPE_DELETE_FAILED(500, "DEVICE-304", "设备类型删除失败"), DEVICE_TYPE_NOT_EMPTY(400, "DEVICE-305", "设备类型不为空"), - DEVICE_DISABLED(403, "DEVICE-306", "设备已禁用"), - - - ; + DEVICE_DISABLED(403, "DEVICE-306", "设备已禁用"); private final int httpStatus; private final String code; // 业务错误码(领域-编号) diff --git a/chaos_api_data/src/main/java/cn/nopj/chaos_api/mapper/UserMapper.java b/chaos_api_data/src/main/java/cn/nopj/chaos_api/mapper/UserMapper.java index 9bec986..0e1ad35 100644 --- a/chaos_api_data/src/main/java/cn/nopj/chaos_api/mapper/UserMapper.java +++ b/chaos_api_data/src/main/java/cn/nopj/chaos_api/mapper/UserMapper.java @@ -70,6 +70,7 @@ public interface UserMapper extends BaseMapper { @Results({ @Result(id = true, property = "id", column = "id"), @Result(property = "username", column = "username"), + @Result(property = "nickname", column = "nickname"), @Result(property = "roles", column = "id", many = @Many(select = "findRolesByUserId")) }) diff --git a/chaos_api_domain/src/main/java/cn/nopj/chaos_api/dto/request/SetUserNicknameRequest.java b/chaos_api_domain/src/main/java/cn/nopj/chaos_api/dto/request/SetUserNicknameRequest.java new file mode 100644 index 0000000..cd4e938 --- /dev/null +++ b/chaos_api_domain/src/main/java/cn/nopj/chaos_api/dto/request/SetUserNicknameRequest.java @@ -0,0 +1,11 @@ +package cn.nopj.chaos_api.dto.request; + +import jakarta.validation.constraints.NotBlank; +import lombok.Data; + +@Data +public class SetUserNicknameRequest { + + @NotBlank(message = "昵称不能为空") + private String nickname; +} diff --git a/chaos_api_domain/src/main/java/cn/nopj/chaos_api/dto/request/UserProfileUpdateRequest.java b/chaos_api_domain/src/main/java/cn/nopj/chaos_api/dto/request/UserProfileUpdateRequest.java new file mode 100644 index 0000000..497c6a9 --- /dev/null +++ b/chaos_api_domain/src/main/java/cn/nopj/chaos_api/dto/request/UserProfileUpdateRequest.java @@ -0,0 +1,9 @@ +package cn.nopj.chaos_api.dto.request; + +import lombok.Data; + +@Data +public class UserProfileUpdateRequest { + private String nickname; + private String password; +} diff --git a/chaos_api_domain/src/main/java/cn/nopj/chaos_api/dto/response/UserinfoResponse.java b/chaos_api_domain/src/main/java/cn/nopj/chaos_api/dto/response/UserProfileResponse.java similarity index 73% rename from chaos_api_domain/src/main/java/cn/nopj/chaos_api/dto/response/UserinfoResponse.java rename to chaos_api_domain/src/main/java/cn/nopj/chaos_api/dto/response/UserProfileResponse.java index 2660584..ea6d41c 100644 --- a/chaos_api_domain/src/main/java/cn/nopj/chaos_api/dto/response/UserinfoResponse.java +++ b/chaos_api_domain/src/main/java/cn/nopj/chaos_api/dto/response/UserProfileResponse.java @@ -5,8 +5,9 @@ import lombok.Data; import java.util.List; @Data -public class UserinfoResponse { +public class UserProfileResponse { private Long id; private String username; + private String nickname; private List roles; } diff --git a/chaos_api_interface/src/main/java/cn/nopj/chaos_api/service/UserInfoService.java b/chaos_api_interface/src/main/java/cn/nopj/chaos_api/service/UserInfoService.java deleted file mode 100644 index bafa368..0000000 --- a/chaos_api_interface/src/main/java/cn/nopj/chaos_api/service/UserInfoService.java +++ /dev/null @@ -1,53 +0,0 @@ -package cn.nopj.chaos_api.service; - -import cn.nopj.chaos_api.dto.response.UserinfoResponse; -import jakarta.validation.constraints.Pattern; - -import java.util.List; - -/** - * 用户信息服务 - * - * @author nopj - */ -public interface UserInfoService { - - /** - * 设置用户密码 - * - * @param id 用户id - * @param password 密码 - */ - void setUserPassword(Long id, String password); - - /** - * 获取所有用户信息 - * - * @return 所有用户信息 - */ - List getAllUsers(); - - /** - * 设置用户密码 - * - * @param userId 用户id - * @param password 密码 - */ - void setUserPassword(@Pattern(regexp = "^[0-9]+$", message = "用户id格式错误") String userId, @Pattern(regexp = "^.{8,16}$", message = "密码长度需为8-16位") String password); - - /** - * 更新用户名 - * - * @param username 用户名 - * @param newUsername 新用户名 - */ - void updateUsername(String username, String newUsername); - - /** - * 根据用户名查询用户信息 - * - * @param username 用户名 - * @return 用户信息 - */ - UserinfoResponse findUserWithRoles(String username); -} diff --git a/chaos_api_interface/src/main/java/cn/nopj/chaos_api/service/UserProfileServcie.java b/chaos_api_interface/src/main/java/cn/nopj/chaos_api/service/UserProfileServcie.java new file mode 100644 index 0000000..46e3602 --- /dev/null +++ b/chaos_api_interface/src/main/java/cn/nopj/chaos_api/service/UserProfileServcie.java @@ -0,0 +1,83 @@ +package cn.nopj.chaos_api.service; + +import cn.nopj.chaos_api.dto.request.UserProfileUpdateRequest; +import cn.nopj.chaos_api.dto.response.UserProfileResponse; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.Pattern; + +import java.util.List; + +/** + * 用户信息服务 + * + * @author nopj + */ +public interface UserProfileServcie { + + /** + * 设置用户密码 + * + * @param id 用户id + * @param password 密码 + */ + void setUserPassword(Long id, String password); + + /** + * 获取所有用户信息 + * + * @return 所有用户信息 + */ + List getAllUsers(); + + /** + * 设置用户密码 + * + * @param userId 用户id + * @param password 密码 + */ + void setUserPassword(@Pattern(regexp = "^[0-9]+$", message = "用户id格式错误") String userId, @Pattern(regexp = "^.{8,16}$", message = "密码长度需为8-16位") String password); + + /** + * 更新用户名 + * + * @param username 用户名 + * @param newUsername 新用户名 + */ + void updateUsername(String username, String newUsername); + + /** + * 根据用户名查询用户信息 + * + * @param username 用户名 + * @return 用户信息 + */ + UserProfileResponse findUserWithRoles(String username); + + /** + * 设置用户昵称 + * + * @param username 用户名 + * @param nickname 昵称 + * @return 处理结果 + */ + UserProfileResponse setUserNickname(@NotBlank(message = "用户账号不能为空") String username, @NotBlank(message = "昵称不能为空") String nickname); + + /** + * 批量设置用户昵称 + * + * @param userId 用户ID + * @param nickname 昵称 + * @return 处理结果 + */ + UserProfileResponse setUserNickname(@NotBlank(message = "用户ID不能为空") Long userId, @NotBlank(message = "昵称不能为空") String nickname); + + + /** + * 更新用户信息 + * + * @param username 用户名 + * @param request 用户信息 + * @return 处理结果 + */ + UserProfileResponse updateUserProfile(String username, UserProfileUpdateRequest request); +} diff --git a/chaos_api_service/src/main/java/cn/nopj/chaos_api/config/AppConfig.java b/chaos_api_service/src/main/java/cn/nopj/chaos_api/config/AppConfig.java deleted file mode 100644 index fbece42..0000000 --- a/chaos_api_service/src/main/java/cn/nopj/chaos_api/config/AppConfig.java +++ /dev/null @@ -1,13 +0,0 @@ -package cn.nopj.chaos_api.config; - -import org.springframework.context.annotation.Bean; -import org.springframework.context.annotation.Configuration; -import org.springframework.web.client.RestTemplate; - -@Configuration -public class AppConfig { - @Bean - public RestTemplate restTemplate() { - return new RestTemplate (); - } -} diff --git a/chaos_api_service/src/main/java/cn/nopj/chaos_api/service/impl/UserInfoServiceImpl.java b/chaos_api_service/src/main/java/cn/nopj/chaos_api/service/impl/UserProfileServcieImpl.java similarity index 52% rename from chaos_api_service/src/main/java/cn/nopj/chaos_api/service/impl/UserInfoServiceImpl.java rename to chaos_api_service/src/main/java/cn/nopj/chaos_api/service/impl/UserProfileServcieImpl.java index ae3c70d..7b04a9d 100644 --- a/chaos_api_service/src/main/java/cn/nopj/chaos_api/service/impl/UserInfoServiceImpl.java +++ b/chaos_api_service/src/main/java/cn/nopj/chaos_api/service/impl/UserProfileServcieImpl.java @@ -3,20 +3,22 @@ package cn.nopj.chaos_api.service.impl; import cn.nopj.chaos_api.common.constants.ErrorCode; import cn.nopj.chaos_api.common.exceotion.BizException; import cn.nopj.chaos_api.domain.entity.User; +import cn.nopj.chaos_api.dto.request.UserProfileUpdateRequest; import cn.nopj.chaos_api.dto.response.RoleResponse; -import cn.nopj.chaos_api.dto.response.UserinfoResponse; +import cn.nopj.chaos_api.dto.response.UserProfileResponse; import cn.nopj.chaos_api.mapper.UserMapper; -import cn.nopj.chaos_api.service.UserInfoService; +import cn.nopj.chaos_api.service.UserProfileServcie; import lombok.extern.slf4j.Slf4j; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.security.crypto.password.PasswordEncoder; import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Transactional; import java.util.List; @Slf4j @Service -public class UserInfoServiceImpl implements UserInfoService { +public class UserProfileServcieImpl implements UserProfileServcie { @Autowired private PasswordEncoder passwordEncoder; @Autowired @@ -38,16 +40,14 @@ public class UserInfoServiceImpl implements UserInfoService { } @Override - public List getAllUsers() { + public List getAllUsers() { List allUserWithRoles = userMapper.findAllUserWithRoles(); if (allUserWithRoles == null){ throw new RuntimeException("获取所有用户信息失败"); } - return allUserWithRoles.stream().map(user -> { - return userConverterUserinfo(user); - }).toList(); + return allUserWithRoles.stream().map(this::userConverterUserinfo).toList(); } @Override @@ -79,7 +79,7 @@ public class UserInfoServiceImpl implements UserInfoService { } @Override - public UserinfoResponse findUserWithRoles(String username) { + public UserProfileResponse findUserWithRoles(String username) { if (username == null || username.isEmpty()){ throw new BizException(ErrorCode.USER_NOT_EXISTS); } @@ -94,16 +94,75 @@ public class UserInfoServiceImpl implements UserInfoService { return userConverterUserinfo(user); } + @Override + public UserProfileResponse setUserNickname(String username, String nickname) { + + User user = userMapper.selectByUsername(username); + if (user == null) { + throw new BizException(ErrorCode.USER_NOT_EXISTS); + } + user.setNickname(nickname); + int i = userMapper.updateById(user); + + log.info("更新用户昵称结果: {}", i); + if (i == 0) { + throw new BizException(ErrorCode.USER_UPDATE_NICKNAME_FAILED); + } + return userConverterUserinfo(user); + } + + @Override + public UserProfileResponse setUserNickname(Long userId, String nickname) { + User user = userMapper.selectById(userId); + if (user == null) { + throw new BizException(ErrorCode.USER_NOT_EXISTS); + } + user.setNickname(nickname); + int i = userMapper.updateById(user); + log.info("更新用户昵称结果: {}", i); + if (i == 0) { + throw new BizException(ErrorCode.USER_UPDATE_NICKNAME_FAILED); + } + return userConverterUserinfo(user); + } + + @Override + @Transactional + public UserProfileResponse updateUserProfile(String username, UserProfileUpdateRequest request) { + + User user = userMapper.findUserWithRolesByUsername(username); + if (user == null) { + throw new BizException(ErrorCode.USER_NOT_EXISTS); + } + + if (request.getNickname() != null){ + user.setNickname(request.getNickname()); + } + if (request.getPassword() != null){ + user.setPassword(passwordEncoder.encode(request.getPassword())); + } + + int i = userMapper.updateById(user); + + log.info("更新用户信息结果: {}", i); + if (i == 0) { + throw new BizException(ErrorCode.USER_UPDATE_PROFILE_FAILED); + } + return userConverterUserinfo(user); + } + + /** * User 转 UserinfoResponse - * @param user - * @return + * @param user 用户 + * @return 用户信息 */ - private UserinfoResponse userConverterUserinfo(User user) { - UserinfoResponse userinfoResponse = new UserinfoResponse(); - userinfoResponse.setId(user.getId()); - userinfoResponse.setUsername(user.getUsername()); - userinfoResponse.setRoles( + private UserProfileResponse userConverterUserinfo(User user) { + UserProfileResponse userProfileResponse = new UserProfileResponse(); + userProfileResponse.setId(user.getId()); + userProfileResponse.setUsername(user.getUsername()); + userProfileResponse.setNickname(user.getNickname()); + userProfileResponse.setRoles( user.getRoles().stream().map(role -> { RoleResponse roleResponse = new RoleResponse(); roleResponse.setId(role.getId()); @@ -111,7 +170,7 @@ public class UserInfoServiceImpl implements UserInfoService { return roleResponse; }).toList() ); - return userinfoResponse; + return userProfileResponse; } diff --git a/chaos_api_web/src/main/java/cn/nopj/chaos_api/config/SecurityConfig.java b/chaos_api_web/src/main/java/cn/nopj/chaos_api/config/SecurityConfig.java index 7b1fbb2..85b6662 100644 --- a/chaos_api_web/src/main/java/cn/nopj/chaos_api/config/SecurityConfig.java +++ b/chaos_api_web/src/main/java/cn/nopj/chaos_api/config/SecurityConfig.java @@ -75,8 +75,7 @@ public class SecurityConfig { CorsConfiguration configuration = new CorsConfiguration(); configuration.setAllowedOrigins(Arrays.asList( - "http://localhost:63342", // 你的前端运行的地址 - "http://localhost:8080", // 其他可能的前端地址 + "http://localhost:5173", // 其他可能的前端地址 "http://127.0.0.1:5500", // 另一个常见的本地开发地址 "null" // 如果是从文件系统直接打开HTML文件,Origin 会是 "null"。仅用于开发! )); diff --git a/chaos_api_web/src/main/java/cn/nopj/chaos_api/controller/UserController.java b/chaos_api_web/src/main/java/cn/nopj/chaos_api/controller/UserController.java index a9bad93..56c76ca 100644 --- a/chaos_api_web/src/main/java/cn/nopj/chaos_api/controller/UserController.java +++ b/chaos_api_web/src/main/java/cn/nopj/chaos_api/controller/UserController.java @@ -1,11 +1,13 @@ package cn.nopj.chaos_api.controller; +import cn.nopj.chaos_api.dto.request.SetUserNicknameRequest; import cn.nopj.chaos_api.dto.request.SetUserPasswordRequest; import cn.nopj.chaos_api.dto.request.UpdateUsernameRequest; -import cn.nopj.chaos_api.dto.response.UserinfoResponse; +import cn.nopj.chaos_api.dto.request.UserProfileUpdateRequest; +import cn.nopj.chaos_api.dto.response.UserProfileResponse; import cn.nopj.chaos_api.model.ApiResult; -import cn.nopj.chaos_api.service.UserInfoService; +import cn.nopj.chaos_api.service.UserProfileServcie; import lombok.extern.slf4j.Slf4j; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.security.access.prepost.PreAuthorize; @@ -23,7 +25,7 @@ import java.util.List; @RequestMapping("/api/user") public class UserController { @Autowired - private UserInfoService userInfoService; + private UserProfileServcie userProfileServcie; /** * 获取所有用户信息 @@ -31,8 +33,8 @@ public class UserController { */ @PreAuthorize("hasAuthority('admin')") @GetMapping("/all") - ApiResult> getAllUsers(){ - return ApiResult.success(userInfoService.getAllUsers()); + ApiResult> getAllUsers(){ + return ApiResult.success(userProfileServcie.getAllUsers()); } /** @@ -43,7 +45,7 @@ public class UserController { @PreAuthorize("hasAuthority('admin')") @PutMapping("/setUserPassword") ApiResult setUserPassword(@RequestBody SetUserPasswordRequest request){ - userInfoService.setUserPassword(request.getUserId(), request.getPassword()); + userProfileServcie.setUserPassword(request.getUserId(), request.getPassword()); return ApiResult.success("用户密码修改成功"); } @@ -54,7 +56,7 @@ public class UserController { */ @PutMapping("/updateUsername") ApiResult updateUsername(@RequestAttribute("currentUsername") String username,@RequestBody UpdateUsernameRequest request){ - userInfoService.updateUsername(username, request.getUsername()); + userProfileServcie.updateUsername(username, request.getUsername()); return ApiResult.success("用户名更新成功"); } @@ -63,8 +65,29 @@ public class UserController { * 获取当前登录用户信息 * @return 用户信息 */ - @GetMapping("/info") - ApiResult getCurrentUserInfo(@RequestAttribute("currentUsername") String username){ - return ApiResult.success(userInfoService.findUserWithRoles(username)); + @GetMapping("/profile") + ApiResult getCurrentUserProfile(@RequestAttribute("currentUsername") String username){ + return ApiResult.success(userProfileServcie.findUserWithRoles(username)); + } + + /** + * 更新用户自身信息 + * @param username 用户名 + * @param request 用户更新信息 + * @return 用户信息 + */ + @PatchMapping("/profile") + ApiResult getUserInfo(@RequestAttribute("currentUsername") String username, @RequestBody UserProfileUpdateRequest request){ + return ApiResult.success(userProfileServcie.updateUserProfile(username,request)); + } + + /** + * 设置用户昵称 + * @param request 用户昵称 + */ + @PreAuthorize("hasAuthority('admin')") + @PutMapping("/{userId}/nickname") + ApiResult setNickname(@PathVariable Long userId, @RequestBody SetUserNicknameRequest request){ + return ApiResult.success(userProfileServcie.setUserNickname(userId,request.getNickname())); } }