经验首页 前端设计 程序设计 Java相关 移动开发 数据库/运维 软件/图像 大数据/云计算 其他经验
当前位置:技术经验 » Java相关 » Spring » 查看文章
springboot用户数据修改的详细实现
来源:jb51  时间:2022/4/7 8:47:53  对本文有异议

修改密码

1 用户-修改密码-持久层

1.1 规划需要执行的SQL语句

用户修改密码时需要执行的SQL语句大致是:

  1. UPDATE t_user SET password=?, modified_user=?, modified_time=? WHERE uid=?

在执行修改密码之前,还应检查用户数据是否存在、并检查用户数据是否被标记为“已删除”、并检查原密码是否正确,这些检查都可以通过查询用户数据来辅助完成:

  1. SELECT * FROM t_user WHERE uid=?

1.2 接口与抽象方法

在UserMapper接口添加updatePasswordByUid(Integer uid,String password,String modifiedUser,Date modifiedTime)抽象方法。

用注解来简化xml配置时,@Param注解的作用是给参数命名,参数命名后就能根据名字得到参数值,正确的将参数传入sql语句中。@Param("参数名")注解中的参数名需要和sql语句中的#{参数名}的参数名保持一致。

  1. /**
  2. * 根据uid更新用户的密码
  3. * @param uid 用户的id
  4. * @param password 新密码
  5. * @param modifiedUser 最后修改执行人
  6. * @param modifiedTime 最后修改时间
  7. * @return 受影响的行数
  8. */
  9. Integer updatePasswordByUid(
  10. @Param("uid") Integer uid,
  11. @Param("password") String password,
  12. @Param("modifiedUser") String modifiedUser,
  13. @Param("modifiedTime") Date modifiedTime);
  14.  
  15. /**
  16. * 根据用户id查询用户数据
  17. * @param uid 用户id
  18. * @return 匹配的用户数据,如果没有匹配的用户数据,则返回null
  19. */
  20. User findByUid(Integer uid);

1.3 配置SQL映射

1.在UserMapper.xml中配置updatePasswordByUid()、findByUid()抽象方法的映射。

  1. <!-- 根据uid更新用户的密码:
  2. Integer updatePasswordByUid(
  3. @Param("uid") Integer uid,
  4. @Param("password") String password,
  5. @Param("modifiedUser") String modifiedUser,
  6. @Param("modifiedTime") Date modifiedTime) -->
  7. <update id="updatePasswordByUid">
  8. UPDATE
  9. t_user
  10. SET
  11. password = #{password},
  12. modified_user = #{modifiedUser},
  13. modified_time = #{modifiedTime}
  14. WHERE
  15. uid = #{uid}
  16. </update>
  17.  
  18. <!-- 根据用户id查询用户数据:User findByUid(Integer uid) -->
  19. <select id="findByUid" resultMap="UserEntityMap">
  20. SELECT
  21. *
  22. FROM
  23. t_user
  24. WHERE
  25. uid = #{uid}
  26. </select>

2.在UserMapperTests中编写并执行单元测试。

  1. @Test
  2. public void updatePasswordByUid() {
  3. Integer uid = 7;
  4. String password = "123456";
  5. String modifiedUser = "超级管理员";
  6. Date modifiedTime = new Date();
  7. Integer rows = userMapper.updatePasswordByUid(uid, password, modifiedUser, modifiedTime);
  8. System.out.println("rows=" + rows);
  9. }
  10.  
  11. @Test
  12. public void findByUid() {
  13. Integer uid = 7;
  14. User result = userMapper.findByUid(uid);
  15. System.out.println(result);
  16. }

2 用户-修改密码-业务层

2.1 规划异常

1.用户在修改密码前,需要检查用户数据是否存在及是否被标记为“已删除”。如果检查不通过则应抛出UserNotFoundException异常。

2.用户修改密码时,可能会因为输入的原密码错误导致修改失败,则应抛出PasswordNotMatchException异常。

3.在执行修改密码时,如果返回的受影响行数与预期值不同,则应抛出UpdateException异常。

4.创建com.cy.store.service.ex.UpdateException异常类,继承自ServiceException类。

  1. /** 更新数据的异常 */
  2. public class UpdateException extends ServiceException {
  3. // Override Methods...
  4. }

2.2 接口与抽象方法

在IUserService中添加changePassword(Integer uid, String username, String oldPassword, String newPassword)抽象方法。

  1. /**
  2. * 修改密码
  3. * @param uid 当前登录的用户id
  4. * @param username 用户名
  5. * @param oldPassword 原密码
  6. * @param newPassword 新密码
  7. */
  8. public void changePassword(Integer uid, String username, String oldPassword, String newPassword);

2.3 实现抽象方法

1.在UserServiceImpl类中实现changePassword()抽象方法。

  1. public void changePassword(Integer uid, String username, String oldPassword, String newPassword) {
  2. // 调用userMapper的findByUid()方法,根据参数uid查询用户数据
  3. // 检查查询结果是否为null
  4. // 是:抛出UserNotFoundException异常
  5.  
  6. // 检查查询结果中的isDelete是否为1
  7. // 是:抛出UserNotFoundException异常
  8.  
  9. // 从查询结果中取出盐值
  10. // 将参数oldPassword结合盐值加密,得到oldMd5Password
  11. // 判断查询结果中的password与oldMd5Password是否不一致
  12. // 是:抛出PasswordNotMatchException异常
  13.  
  14. // 将参数newPassword结合盐值加密,得到newMd5Password
  15. // 创建当前时间对象
  16. // 调用userMapper的updatePasswordByUid()更新密码,并获取返回值
  17. // 判断以上返回的受影响行数是否不为1
  18. // 是:抛了UpdateException异常
  19. }

2.changePassword()方法的具体代码。

String中的equals与contentEquals方法,都可以用来比较String对象内容是否相同。

  1. @Override
  2. public void changePassword(Integer uid, String username, String oldPassword, String newPassword) {
  3. // 调用userMapper的findByUid()方法,根据参数uid查询用户数据
  4. User result = userMapper.findByUid(uid);
  5. // 检查查询结果是否为null
  6. if (result == null) {
  7. // 是:抛出UserNotFoundException异常
  8. throw new UserNotFoundException("用户数据不存在");
  9. }
  10. // 检查查询结果中的isDelete是否为1
  11. if (result.getIsDelete().equals(1)) {
  12. // 是:抛出UserNotFoundException异常
  13. throw new UserNotFoundException("用户数据不存在");
  14. }
  15. // 从查询结果中取出盐值
  16. String salt = result.getSalt();
  17. // 将参数oldPassword结合盐值加密,得到oldMd5Password
  18. String oldMd5Password = getMd5Password(oldPassword, salt);
  19. // 判断查询结果中的password与oldMd5Password是否不一致
  20. if (!result.getPassword().contentEquals(oldMd5Password)) {
  21. // 是:抛出PasswordNotMatchException异常
  22. throw new PasswordNotMatchException("原密码错误");
  23. }
  24. // 将参数newPassword结合盐值加密,得到newMd5Password
  25. String newMd5Password = getMd5Password(newPassword, salt);
  26. // 创建当前时间对象
  27. Date now = new Date();
  28. // 调用userMapper的updatePasswordByUid()更新密码,并获取返回值
  29. Integer rows = userMapper.updatePasswordByUid(uid, newMd5Password, username, now);
  30. // 判断以上返回的受影响行数是否不为1
  31. if (rows != 1) {
  32. // 是:抛出UpdateException异常
  33. throw new UpdateException("更新用户数据时出现未知错误,请联系系统管理员");
  34. }
  35. }

3.在UserServiceTests中编写并执行单元测试。

  1. @Test
  2. public void changePassword() {
  3. try {
  4. Integer uid = 5;
  5. String username = "lower";
  6. String oldPassword = "123456";
  7. String newPassword = "888888";
  8. userService.changePassword(uid, username, oldPassword, newPassword);
  9. System.out.println("密码修改成功!");
  10. } catch (ServiceException e) {
  11. System.out.println("密码修改失败!" + e.getClass().getSimpleName());
  12. System.out.println(e.getMessage());
  13. }
  14. }

3 用户-修改密码-控制器

3.1 处理异常

在用户修改密码的业务中抛出了新的UpdateException异常,需要在BaseController类中进行处理。

  1. @ExceptionHandler(ServiceException.class)
  2. public JsonResult<Void> handleException(Throwable e) {
  3. JsonResult<Void> result = new JsonResult<Void>(e);
  4. if (e instanceof UsernameDuplicateException) {
  5. result.setState(4000);
  6. } else if (e instanceof UserNotFoundException) {
  7. result.setState(4001);
  8. } else if (e instanceof PasswordNotMatchException) {
  9. result.setState(4002);
  10. } else if (e instanceof InsertException) {
  11. result.setState(5000);
  12. } else if (e instanceof UpdateException) {
  13. result.setState(5001);
  14. }
  15. return result;
  16. }

3.2 设计请求

设计用户提交的请求,并设计响应的方式。

请求路径:/users/change_password
请求参数:String oldPassword, String newPassword, HttpSession session
请求类型:POST
响应结果:JsonResult<Void>

3.3 处理请求

1.在UserController类中添加处理请求的changePassword(String oldPassword, String newPassword, HttpSession session)方法。

  1. @RequestMapping("change_password")
  2. public JsonResult<Void> changePassword(String oldPassword, String newPassword, HttpSession session) {
  3. // 调用session.getAttribute("")获取uid和username
  4. // 调用业务对象执行修改密码
  5. // 返回成功
  6. return null;
  7. }

2.实现UserController控制器中的修改密码方法的代码。

  1. @RequestMapping("change_password")
  2. public JsonResult<Void> changePassword(String oldPassword, String newPassword, HttpSession session) {
  3. // 调用session.getAttribute("")获取uid和username
  4. Integer uid = getUidFromSession(session);
  5. String username = getUsernameFromSession(session);
  6. // 调用业务对象执行修改密码
  7. iUserService.changePassword(uid, username, oldPassword, newPassword);
  8. // 返回成功
  9. return new JsonResult<Void>(OK);
  10. }

3.启动项目先登录,再访问http://localhost:8080/users/change_password?oldPassword=xx&newPassword=xx进行测试。

4 用户-修改密码-前端页面

1.在password.html页面中body标签内部的最后,添加script标签用于编写JavaScript程序。

  1. <script type="text/javascript">
  2. $("#btn-change-password").click(function() {
  3. $.ajax({
  4. url: "/users/change_password",
  5. type: "POST",
  6. data: $("#form-change-password").serialize(),
  7. dataType: "json",
  8. success: function(json) {
  9. if (json.state == 200) {
  10. alert("修改成功!");
  11. } else {
  12. alert("修改失败!" + json.message);
  13. }
  14. }
  15. });
  16. });
  17. </script>

2.启动项目先登录,再访问http://localhost:8080/web/password.html页面并进行修改密码。

问题:如果无法正常将数据传递给后台,重启动系统和IDEA开发工具,登陆后便可修改密码。

3.问题:在操作前端页面时用户进入修改密码页面,长时间停留在当前页面未进行任何操作,将导致登录信息过期。此时点击修改按钮时,仍会向/users/change_password发送请求,会被拦截器重定向到登录页面。由于整个过程是由$.ajax()函数采用异步的方式处理的,所以重定向也是由异步任务完成的,在页面中没有任何表现就会出现“用户登录信息超时后点击按钮没有任何反应”的问题。

解决方案:可以在password.html页面的$.ajax()中补充error属性的配置,该属性的值是一个回调函数。当服务器未正常响应状态码时,例如出现302、400、404、405、500等状态码时,将会调用该函数。

  1. error: function (xhr) {
  2. alert("您的登录信息已经过期,请重新登录!HTTP响应码:" + xhr.status);
  3. location.href = "login.html";
  4. }

个人资料

1 用户-个人资料-持久层

1.1 规划需要执行的SQL语句

1.执行修改用户个人资料的SQL语句大致是:

  1. UPDATE t_user SET phone=?, email=?, gender=?, modified_user=?, modified_time=? WHERE uid=?

2.在执行修改用户资料之前,当用户刚打开修改资料的页面时,就应把当前登录的用户信息显示到页面中。显示用户资料可以通过:

  1. SELECT * FROM t_user WHERE uid=?

说明:

1.该查询功能已经实现,无需再次开发;

2.在执行修改用户资料之前,还应检查用户数据是否存在、是否标记为“已删除”,也可以通过以上查询来实现。

1.2 接口与抽象方法

在UserMapper接口中添加updateInfoByUid(User user)方法。

  1. /**
  2. * 根据uid更新用户资料
  3. * @param user 封装了用户id和新个人资料的对象
  4. * @return 受影响的行数
  5. */
  6. Integer updateInfoByUid(User user);

1.3 配置SQL映射

1.在UserMapper.xml中配置Integer updateInfoByUid(User user)抽象方法的映射。

  1. <!-- 根据uid更新用户个人资料:Integer updateInfoByUid(User user) -->
  2. <update id="updateInfoByUid">
  3. UPDATE
  4. t_user
  5. SET
  6. <if test="phone != null">phone = #{phone},</if>
  7. <if test="email != null">email = #{email},</if>
  8. <if test="gender != null">gender = #{gender},</if>
  9. modified_user = #{modifiedUser},
  10. modified_time = #{modifiedTime}
  11. WHERE
  12. uid = #{uid}
  13. </update>

2.在UserMapperTests中编写并执行单元测试。

  1. @Test
  2. public void updateInfoByUid() {
  3. User user = new User();
  4. user.setUid(20);
  5. user.setPhone("17858802222");
  6. user.setEmail("admin@cy.com");
  7. user.setGender(1);
  8. user.setModifiedUser("系统管理员");
  9. user.setModifiedTime(new Date());
  10. Integer rows = userMapper.updateInfoByUid(user);
  11. System.out.println("rows=" + rows);
  12. }

2 用户-个人资料-业务层

2.1 规划异常

1.关于用户修改个人资料是由两个功能组成的。

  • 打开页面时显示当前登录的用户的信息;

  • 点击修改按钮时更新用户的信息。

2.关于打开页面时显示当前登录的用户的信息,可能会因为用户数据不存在、用户被标记为“已删除”而无法正确的显示页面,则抛出UserNotFoundException异常。

3.关于点击修改按钮时更新用户的信息,在执行修改资料之前仍需再次检查用户数据是否存在、用户是否被标记为“已删除”,则可能抛出UserNotFoundException异常。并且在执行修改资料过程中,还可能抛出UpdateException异常。

2.2 接口与抽象方法

在IUserService接口中添加两个抽象方法,分别对应以上两个功能。

  1. /**
  2. * 获取当前登录的用户的信息
  3. * @param uid 当前登录的用户的id
  4. * @return 当前登录的用户的信息
  5. */
  6. User getByUid(Integer uid);
  7.  
  8. /**
  9. * 修改用户资料
  10. * @param uid 当前登录的用户的id
  11. * @param username 当前登录的用户名
  12. * @param user 用户的新的数据
  13. */
  14. void changeInfo(Integer uid, String username, User user);

2.3 实现抽象方法

1.在UserServiceImpl实现类中实现getByUid(Integer uid)和changeInfo(Integer uid, String username, User user)以上两个抽象方法。

  1. @Override
  2. public User getByUid(Integer uid) {
  3. // 调用userMapper的findByUid()方法,根据参数uid查询用户数据
  4. // 判断查询结果是否为null
  5. // 是:抛出UserNotFoundException异常
  6.  
  7. // 判断查询结果中的isDelete是否为1
  8. // 是:抛出UserNotFoundException异常
  9.  
  10. // 创建新的User对象
  11. // 将以上查询结果中的username/phone/email/gender封装到新User对象中
  12.  
  13. // 返回新的User对象
  14. return null;
  15. }
  16.  
  17. @Override
  18. public void changeInfo(Integer uid, String username, User user) {
  19. // 调用userMapper的findByUid()方法,根据参数uid查询用户数据
  20. // 判断查询结果是否为null
  21. // 是:抛出UserNotFoundException异常
  22.  
  23. // 判断查询结果中的isDelete是否为1
  24. // 是:抛出UserNotFoundException异常
  25.  
  26. // 向参数user中补全数据:uid
  27. // 向参数user中补全数据:modifiedUser(username)
  28. // 向参数user中补全数据:modifiedTime(new Date())
  29. // 调用userMapper的updateInfoByUid(User user)方法执行修改,并获取返回值
  30. // 判断以上返回的受影响行数是否不为1
  31. // 是:抛出UpdateException异常
  32. }

2.getByUid(Integer uid)和changeInfo(Integer uid, String username, User user)方法的具体代码实现。

  1. @Override
  2. public User getByUid(Integer uid) {
  3. // 调用userMapper的findByUid()方法,根据参数uid查询用户数据
  4. User result = userMapper.findByUid(uid);
  5. // 判断查询结果是否为null
  6. if (result == null) {
  7. // 是:抛出UserNotFoundException异常
  8. throw new UserNotFoundException("用户数据不存在");
  9. }
  10. // 判断查询结果中的isDelete是否为1
  11. if (result.getIsDelete().equals(1)) {
  12. // 是:抛出UserNotFoundException异常
  13. throw new UserNotFoundException("用户数据不存在");
  14. }
  15.  
  16. // 创建新的User对象
  17. User user = new User();
  18. // 将以上查询结果中的username/phone/email/gender封装到新User对象中
  19. user.setUsername(result.getUsername());
  20. user.setPhone(result.getPhone());
  21. user.setEmail(result.getEmail());
  22. user.setGender(result.getGender());
  23. // 返回新的User对象
  24. return user;
  25. }
  26.  
  27. @Override
  28. public void changeInfo(Integer uid, String username, User user) {
  29. // 调用userMapper的findByUid()方法,根据参数uid查询用户数据
  30. User result = userMapper.findByUid(uid);
  31. // 判断查询结果是否为null
  32. if (result == null) {
  33. // 是:抛出UserNotFoundException异常
  34. throw new UserNotFoundException("用户数据不存在");
  35. }
  36.  
  37. // 判断查询结果中的isDelete是否为1
  38. if (result.getIsDelete().equals(1)) {
  39. // 是:抛出UserNotFoundException异常
  40. throw new UserNotFoundException("用户数据不存在");
  41. }
  42.  
  43. // 向参数user中补全数据:uid
  44. user.setUid(uid);
  45. // 向参数user中补全数据:modifiedUser(username)
  46. user.setModifiedUser(username);
  47. // 向参数user中补全数据:modifiedTime(new Date())
  48. user.setModifiedTime(new Date());
  49. // 调用userMapper的updateInfoByUid(User user)方法执行修改,并获取返回值
  50. Integer rows = userMapper.updateInfoByUid(user);
  51. // 判断以上返回的受影响行数是否不为1
  52. if (rows != 1) {
  53. // 是:抛出UpdateException异常
  54. throw new UpdateException("更新用户数据时出现未知错误,请联系系统管理员");
  55. }
  56. }

3.在UserServiceTests类中进行单元测试。

  1. @Test
  2. public void getByUid() {
  3. try {
  4. Integer uid = 20;
  5. User user = iUserService.getByUid(uid);
  6. System.out.println(user);
  7. } catch (ServiceException e) {
  8. System.out.println(e.getClass().getSimpleName());
  9. System.out.println(e.getMessage());
  10. }
  11. }
  12.  
  13. @Test
  14. public void changeInfo() {
  15. try {
  16. Integer uid = 20;
  17. String username = "数据管理员";
  18. User user = new User();
  19. user.setPhone("15512328888");
  20. user.setEmail("admin03@cy.cn");
  21. user.setGender(2);
  22. iUserService.changeInfo(uid, username, user);
  23. System.out.println("OK.");
  24. } catch (ServiceException e) {
  25. System.out.println(e.getClass().getSimpleName());
  26. System.out.println(e.getMessage());
  27. }
  28. }

3 用户-个人资料-控制器

3.1 处理异常

说明:无需再次开发。

3.2 设计请求

1.设计用户提交显示当前登录的用户信息的请求,并设计响应的方式。

请求路径:/users/get_by_uid
请求参数:HttpSession session
请求类型:GET
响应结果:JsonResult<User>

2.设计用户提交执行修改用户信息的请求,并设计响应的方式。

请求路径:/users/change_info
请求参数:User user, HttpSession session
请求类型:POST
响应结果:JsonResult<Void>

3.3 处理请求

1.处理获取用户信息请求

1.在UserController类中添加处理请求的getByUid()方法,并导入org.springframework.web.bind.annotation.GetMapping包。

  1. @GetMapping("get_by_uid")
  2. public JsonResult<User> getByUid(HttpSession session) {
  3. // 从HttpSession对象中获取uid
  4. // 调用业务对象执行获取数据
  5. // 响应成功和数据
  6. return null;
  7. }

2.getByUid(HttpSession session)方法中具体代码实现为。

  1. @GetMapping("get_by_uid")
  2. public JsonResult<User> getByUid(HttpSession session) {
  3. // 从HttpSession对象中获取uid
  4. Integer uid = getUidFromSession(session);
  5. // 调用业务对象执行获取数据
  6. User data = userService.getByUid(uid);
  7. // 响应成功和数据
  8. return new JsonResult<User>(OK, data);
  9. }

3.完成后启动项目,打开浏览器先登录,再访问http://localhost:8080/users/get_by_uid请求进行测试。

2.处理修改用户个人信息请求

1.在UserController类中添加处理请求的changeInfo(User user, HttpSession session)方法。

  1. @RequestMapping("change_info")
  2. public JsonResult<Void> changeInfo(User user, HttpSession session) {
  3. // 从HttpSession对象中获取uid和username
  4. // 调用业务对象执行修改用户资料
  5. // 响应成功
  6. return null;
  7. }

2.changeInfo(User user, HttpSession session)方法中具体代码实现为。

  1. @RequestMapping("change_info")
  2. public JsonResult<Void> changeInfo(User user, HttpSession session) {
  3. // 从HttpSession对象中获取uid和username
  4. Integer uid = getUidFromSession(session);
  5. String username = getUsernameFromSession(session);
  6. // 调用业务对象执行修改用户资料
  7. userService.changeInfo(uid, username, user);
  8. // 响应成功
  9. return new JsonResult<Void>(OK);
  10. }

3.完成后启动项目,打开浏览器先登录,再访问http://localhost:8080/users/change_info?phone=17858800000&email=admin07@cy.com&gender=1进行测试。

4 用户-个人资料-前端页面

1.在userdata.html页面中body标签内部的最后,添加script标签用于编写JavaScript程序。

  1. <script type="text/javascript">
  2. $(document).ready(function() {
  3. $.ajax({
  4. url: "/users/get_by_uid",
  5. type: "GET",
  6. dataType: "json",
  7. success: function(json) {
  8. if (json.state == 200) {
  9. console.log("username=" + json.data.username);
  10. console.log("phone=" + json.data.phone);
  11. console.log("email=" + json.data.email);
  12. console.log("gender=" + json.data.gender);
  13.  
  14. $("#username").val(json.data.username);
  15. $("#phone").val(json.data.phone);
  16. $("#email").val(json.data.email);
  17.  
  18. let radio = json.data.gender == 0 ? $("#gender-female") : $("#gender-male");
  19. radio.prop("checked", "checked");
  20. } else {
  21. alert("获取用户信息失败!" + json.message);
  22. }
  23. }
  24. });
  25. });
  26.  
  27. $("#btn-change-info").click(function() {
  28. $.ajax({
  29. url: "/users/change_info",
  30. type: "POST",
  31. data: $("#form-change-info").serialize(),
  32. dataType: "json",
  33. success: function(json) {
  34. if (json.state == 200) {
  35. alert("修改成功!");
  36. location.href = "login.html";
  37. } else {
  38. alert("修改失败!" + json.message);
  39. }
  40. },
  41. error: function(xhr) {
  42. alert("您的登录信息已经过期,请重新登录!HTTP响应码:" + xhr.status);
  43. location.href = "login.html";
  44. }
  45. });
  46. });
  47. </script>

2.完成后启动项目,打开浏览器先登录,再访问http://localhost:8080/web/userdata.html页面并进行用户个人资料的修改测试。

总结

到此这篇关于springboot用户数据修改的文章就介绍到这了,更多相关springboot用户数据修改内容请搜索w3xue以前的文章或继续浏览下面的相关文章希望大家以后多多支持w3xue!

 友情链接:直通硅谷  点职佳  北美留学生论坛

本站QQ群:前端 618073944 | Java 606181507 | Python 626812652 | C/C++ 612253063 | 微信 634508462 | 苹果 692586424 | C#/.net 182808419 | PHP 305140648 | 运维 608723728

W3xue 的所有内容仅供测试,对任何法律问题及风险不承担任何责任。通过使用本站内容随之而来的风险与本站无关。
关于我们  |  意见建议  |  捐助我们  |  报错有奖  |  广告合作、友情链接(目前9元/月)请联系QQ:27243702 沸活量
皖ICP备17017327号-2 皖公网安备34020702000426号