<em>Mac</em>Book项目 2009年学校开始实施<em>Mac</em>Book项目,所有师生配备一本<em>Mac</em>Book,并同步更新了校园无线网络。学校每周进行电脑技术更新,每月发送技术支持资料,极大改变了教学及学习方式。因此2011
2021-06-01 09:32:01
使用者修改密碼時需要執行的SQL語句大致是:
UPDATE t_user SET password=?, modified_user=?, modified_time=? WHERE uid=?
在執行修改密碼之前,還應檢查使用者資料是否存在、並檢查使用者資料是否被標記為“已刪除”、並檢查原密碼是否正確,這些檢查都可以通過查詢使用者資料來輔助完成:
SELECT * FROM t_user WHERE uid=?
在UserMapper介面新增updatePasswordByUid(Integer uid,String password,String modifiedUser,Date modifiedTime)抽象方法。
用註解來簡化xml設定時,@Param註解的作用是給引數命名,引數命名後就能根據名字得到引數值,正確的將引數傳入sql語句中。@Param("引數名")註解中的引數名需要和sql語句中的#{引數名}的引數名保持一致。
/** * 根據uid更新使用者的密碼 * @param uid 使用者的id * @param password 新密碼 * @param modifiedUser 最後修改執行人 * @param modifiedTime 最後修改時間 * @return 受影響的行數 */ Integer updatePasswordByUid( @Param("uid") Integer uid, @Param("password") String password, @Param("modifiedUser") String modifiedUser, @Param("modifiedTime") Date modifiedTime); /** * 根據使用者id查詢使用者資料 * @param uid 使用者id * @return 匹配的使用者資料,如果沒有匹配的使用者資料,則返回null */ User findByUid(Integer uid);
1.在UserMapper.xml中設定updatePasswordByUid()、findByUid()抽象方法的對映。
<!-- 根據uid更新使用者的密碼: Integer updatePasswordByUid( @Param("uid") Integer uid, @Param("password") String password, @Param("modifiedUser") String modifiedUser, @Param("modifiedTime") Date modifiedTime) --> <update id="updatePasswordByUid"> UPDATE t_user SET password = #{password}, modified_user = #{modifiedUser}, modified_time = #{modifiedTime} WHERE uid = #{uid} </update> <!-- 根據使用者id查詢使用者資料:User findByUid(Integer uid) --> <select id="findByUid" resultMap="UserEntityMap"> SELECT * FROM t_user WHERE uid = #{uid} </select>
2.在UserMapperTests中編寫並執行單元測試。
@Test public void updatePasswordByUid() { Integer uid = 7; String password = "123456"; String modifiedUser = "超級管理員"; Date modifiedTime = new Date(); Integer rows = userMapper.updatePasswordByUid(uid, password, modifiedUser, modifiedTime); System.out.println("rows=" + rows); } @Test public void findByUid() { Integer uid = 7; User result = userMapper.findByUid(uid); System.out.println(result); }
1.使用者在修改密碼前,需要檢查使用者資料是否存在及是否被標記為“已刪除”。如果檢查不通過則應丟擲UserNotFoundException異常。
2.使用者修改密碼時,可能會因為輸入的原密碼錯誤導致修改失敗,則應丟擲PasswordNotMatchException異常。
3.在執行修改密碼時,如果返回的受影響行數與預期值不同,則應丟擲UpdateException異常。
4.建立com.cy.store.service.ex.UpdateException異常類,繼承自ServiceException類。
/** 更新資料的異常 */ public class UpdateException extends ServiceException { // Override Methods... }
在IUserService中新增changePassword(Integer uid, String username, String oldPassword, String newPassword)抽象方法。
/** * 修改密碼 * @param uid 當前登入的使用者id * @param username 使用者名稱 * @param oldPassword 原密碼 * @param newPassword 新密碼 */ public void changePassword(Integer uid, String username, String oldPassword, String newPassword);
1.在UserServiceImpl類中實現changePassword()抽象方法。
public void changePassword(Integer uid, String username, String oldPassword, String newPassword) { // 呼叫userMapper的findByUid()方法,根據引數uid查詢使用者資料 // 檢查查詢結果是否為null // 是:丟擲UserNotFoundException異常 // 檢查查詢結果中的isDelete是否為1 // 是:丟擲UserNotFoundException異常 // 從查詢結果中取出鹽值 // 將引數oldPassword結合鹽值加密,得到oldMd5Password // 判斷查詢結果中的password與oldMd5Password是否不一致 // 是:丟擲PasswordNotMatchException異常 // 將引數newPassword結合鹽值加密,得到newMd5Password // 建立當前時間物件 // 呼叫userMapper的updatePasswordByUid()更新密碼,並獲取返回值 // 判斷以上返回的受影響行數是否不為1 // 是:拋了UpdateException異常 }
2.changePassword()方法的具體程式碼。
String中的equals與contentEquals方法,都可以用來比較String物件內容是否相同。
@Override public void changePassword(Integer uid, String username, String oldPassword, String newPassword) { // 呼叫userMapper的findByUid()方法,根據引數uid查詢使用者資料 User result = userMapper.findByUid(uid); // 檢查查詢結果是否為null if (result == null) { // 是:丟擲UserNotFoundException異常 throw new UserNotFoundException("使用者資料不存在"); } // 檢查查詢結果中的isDelete是否為1 if (result.getIsDelete().equals(1)) { // 是:丟擲UserNotFoundException異常 throw new UserNotFoundException("使用者資料不存在"); } // 從查詢結果中取出鹽值 String salt = result.getSalt(); // 將引數oldPassword結合鹽值加密,得到oldMd5Password String oldMd5Password = getMd5Password(oldPassword, salt); // 判斷查詢結果中的password與oldMd5Password是否不一致 if (!result.getPassword().contentEquals(oldMd5Password)) { // 是:丟擲PasswordNotMatchException異常 throw new PasswordNotMatchException("原密碼錯誤"); } // 將引數newPassword結合鹽值加密,得到newMd5Password String newMd5Password = getMd5Password(newPassword, salt); // 建立當前時間物件 Date now = new Date(); // 呼叫userMapper的updatePasswordByUid()更新密碼,並獲取返回值 Integer rows = userMapper.updatePasswordByUid(uid, newMd5Password, username, now); // 判斷以上返回的受影響行數是否不為1 if (rows != 1) { // 是:丟擲UpdateException異常 throw new UpdateException("更新使用者資料時出現未知錯誤,請聯絡系統管理員"); } }
3.在UserServiceTests中編寫並執行單元測試。
@Test public void changePassword() { try { Integer uid = 5; String username = "lower"; String oldPassword = "123456"; String newPassword = "888888"; userService.changePassword(uid, username, oldPassword, newPassword); System.out.println("密碼修改成功!"); } catch (ServiceException e) { System.out.println("密碼修改失敗!" + e.getClass().getSimpleName()); System.out.println(e.getMessage()); } }
在使用者修改密碼的業務中丟擲了新的UpdateException異常,需要在BaseController類中進行處理。
@ExceptionHandler(ServiceException.class) public JsonResult<Void> handleException(Throwable e) { JsonResult<Void> result = new JsonResult<Void>(e); if (e instanceof UsernameDuplicateException) { result.setState(4000); } else if (e instanceof UserNotFoundException) { result.setState(4001); } else if (e instanceof PasswordNotMatchException) { result.setState(4002); } else if (e instanceof InsertException) { result.setState(5000); } else if (e instanceof UpdateException) { result.setState(5001); } return result; }
設計使用者提交的請求,並設計響應的方式。
請求路徑:/users/change_password
請求引數:String oldPassword, String newPassword, HttpSession session
請求型別:POST
響應結果:JsonResult<Void>
1.在UserController類中新增處理請求的changePassword(String oldPassword, String newPassword, HttpSession session)方法。
@RequestMapping("change_password") public JsonResult<Void> changePassword(String oldPassword, String newPassword, HttpSession session) { // 呼叫session.getAttribute("")獲取uid和username // 呼叫業務物件執行修改密碼 // 返回成功 return null; }
2.實現UserController控制器中的修改密碼方法的程式碼。
@RequestMapping("change_password") public JsonResult<Void> changePassword(String oldPassword, String newPassword, HttpSession session) { // 呼叫session.getAttribute("")獲取uid和username Integer uid = getUidFromSession(session); String username = getUsernameFromSession(session); // 呼叫業務物件執行修改密碼 iUserService.changePassword(uid, username, oldPassword, newPassword); // 返回成功 return new JsonResult<Void>(OK); }
3.啟動專案先登入,再存取http://localhost:8080/users/change_password?oldPassword=xx&newPassword=xx進行測試。
1.在password.html頁面中body標籤內部的最後,新增script標籤用於編寫JavaScript程式。
<script type="text/javascript"> $("#btn-change-password").click(function() { $.ajax({ url: "/users/change_password", type: "POST", data: $("#form-change-password").serialize(), dataType: "json", success: function(json) { if (json.state == 200) { alert("修改成功!"); } else { alert("修改失敗!" + json.message); } } }); }); </script>
2.啟動專案先登入,再存取http://localhost:8080/web/password.html頁面並進行修改密碼。
問題:如果無法正常將資料傳遞給後臺,重啟動系統和IDEA開發工具,登陸後便可修改密碼。
3.問題:在操作前端頁面時使用者進入修改密碼頁面,長時間停留在當前頁面未進行任何操作,將導致登入資訊過期。此時點選修改按鈕時,仍會向/users/change_password傳送請求,會被攔截器重定向到登入頁面。由於整個過程是由$.ajax()函數採用非同步的方式處理的,所以重定向也是由非同步任務完成的,在頁面中沒有任何表現就會出現“使用者登入資訊超時後點選按鈕沒有任何反應”的問題。
解決方案:可以在password.html頁面的$.ajax()中補充error屬性的設定,該屬性的值是一個回撥函數。當伺服器未正常響應狀態碼時,例如出現302、400、404、405、500等狀態碼時,將會呼叫該函數。
error: function (xhr) { alert("您的登入資訊已經過期,請重新登入!HTTP響應碼:" + xhr.status); location.href = "login.html"; }
1.執行修改使用者個人資料的SQL語句大致是:
UPDATE t_user SET phone=?, email=?, gender=?, modified_user=?, modified_time=? WHERE uid=?
2.在執行修改使用者資料之前,當用戶剛開啟修改資料的頁面時,就應把當前登入的使用者資訊顯示到頁面中。顯示使用者資料可以通過:
SELECT * FROM t_user WHERE uid=?
說明:
1.該查詢功能已經實現,無需再次開發;
2.在執行修改使用者資料之前,還應檢查使用者資料是否存在、是否標記為“已刪除”,也可以通過以上查詢來實現。
在UserMapper介面中新增updateInfoByUid(User user)方法。
/** * 根據uid更新使用者資料 * @param user 封裝了使用者id和新個人資料的物件 * @return 受影響的行數 */ Integer updateInfoByUid(User user);
1.在UserMapper.xml中設定Integer updateInfoByUid(User user)抽象方法的對映。
<!-- 根據uid更新使用者個人資料:Integer updateInfoByUid(User user) --> <update id="updateInfoByUid"> UPDATE t_user SET <if test="phone != null">phone = #{phone},</if> <if test="email != null">email = #{email},</if> <if test="gender != null">gender = #{gender},</if> modified_user = #{modifiedUser}, modified_time = #{modifiedTime} WHERE uid = #{uid} </update>
2.在UserMapperTests中編寫並執行單元測試。
@Test public void updateInfoByUid() { User user = new User(); user.setUid(20); user.setPhone("17858802222"); user.setEmail("admin@cy.com"); user.setGender(1); user.setModifiedUser("系統管理員"); user.setModifiedTime(new Date()); Integer rows = userMapper.updateInfoByUid(user); System.out.println("rows=" + rows); }
1.關於使用者修改個人資料是由兩個功能組成的。
開啟頁面時顯示當前登入的使用者的資訊;
點選修改按鈕時更新使用者的資訊。
2.關於開啟頁面時顯示當前登入的使用者的資訊,可能會因為使用者資料不存在、使用者被標記為“已刪除”而無法正確的顯示頁面,則丟擲UserNotFoundException異常。
3.關於點選修改按鈕時更新使用者的資訊,在執行修改資料之前仍需再次檢查使用者資料是否存在、使用者是否被標記為“已刪除”,則可能丟擲UserNotFoundException異常。並且在執行修改資料過程中,還可能丟擲UpdateException異常。
在IUserService介面中新增兩個抽象方法,分別對應以上兩個功能。
/** * 獲取當前登入的使用者的資訊 * @param uid 當前登入的使用者的id * @return 當前登入的使用者的資訊 */ User getByUid(Integer uid); /** * 修改使用者資料 * @param uid 當前登入的使用者的id * @param username 當前登入的使用者名稱 * @param user 使用者的新的資料 */ void changeInfo(Integer uid, String username, User user);
1.在UserServiceImpl實現類中實現getByUid(Integer uid)和changeInfo(Integer uid, String username, User user)以上兩個抽象方法。
@Override public User getByUid(Integer uid) { // 呼叫userMapper的findByUid()方法,根據引數uid查詢使用者資料 // 判斷查詢結果是否為null // 是:丟擲UserNotFoundException異常 // 判斷查詢結果中的isDelete是否為1 // 是:丟擲UserNotFoundException異常 // 建立新的User物件 // 將以上查詢結果中的username/phone/email/gender封裝到新User物件中 // 返回新的User物件 return null; } @Override public void changeInfo(Integer uid, String username, User user) { // 呼叫userMapper的findByUid()方法,根據引數uid查詢使用者資料 // 判斷查詢結果是否為null // 是:丟擲UserNotFoundException異常 // 判斷查詢結果中的isDelete是否為1 // 是:丟擲UserNotFoundException異常 // 向引數user中補全資料:uid // 向引數user中補全資料:modifiedUser(username) // 向引數user中補全資料:modifiedTime(new Date()) // 呼叫userMapper的updateInfoByUid(User user)方法執行修改,並獲取返回值 // 判斷以上返回的受影響行數是否不為1 // 是:丟擲UpdateException異常 }
2.getByUid(Integer uid)和changeInfo(Integer uid, String username, User user)方法的具體程式碼實現。
@Override public User getByUid(Integer uid) { // 呼叫userMapper的findByUid()方法,根據引數uid查詢使用者資料 User result = userMapper.findByUid(uid); // 判斷查詢結果是否為null if (result == null) { // 是:丟擲UserNotFoundException異常 throw new UserNotFoundException("使用者資料不存在"); } // 判斷查詢結果中的isDelete是否為1 if (result.getIsDelete().equals(1)) { // 是:丟擲UserNotFoundException異常 throw new UserNotFoundException("使用者資料不存在"); } // 建立新的User物件 User user = new User(); // 將以上查詢結果中的username/phone/email/gender封裝到新User物件中 user.setUsername(result.getUsername()); user.setPhone(result.getPhone()); user.setEmail(result.getEmail()); user.setGender(result.getGender()); // 返回新的User物件 return user; } @Override public void changeInfo(Integer uid, String username, User user) { // 呼叫userMapper的findByUid()方法,根據引數uid查詢使用者資料 User result = userMapper.findByUid(uid); // 判斷查詢結果是否為null if (result == null) { // 是:丟擲UserNotFoundException異常 throw new UserNotFoundException("使用者資料不存在"); } // 判斷查詢結果中的isDelete是否為1 if (result.getIsDelete().equals(1)) { // 是:丟擲UserNotFoundException異常 throw new UserNotFoundException("使用者資料不存在"); } // 向引數user中補全資料:uid user.setUid(uid); // 向引數user中補全資料:modifiedUser(username) user.setModifiedUser(username); // 向引數user中補全資料:modifiedTime(new Date()) user.setModifiedTime(new Date()); // 呼叫userMapper的updateInfoByUid(User user)方法執行修改,並獲取返回值 Integer rows = userMapper.updateInfoByUid(user); // 判斷以上返回的受影響行數是否不為1 if (rows != 1) { // 是:丟擲UpdateException異常 throw new UpdateException("更新使用者資料時出現未知錯誤,請聯絡系統管理員"); } }
3.在UserServiceTests類中進行單元測試。
@Test public void getByUid() { try { Integer uid = 20; User user = iUserService.getByUid(uid); System.out.println(user); } catch (ServiceException e) { System.out.println(e.getClass().getSimpleName()); System.out.println(e.getMessage()); } } @Test public void changeInfo() { try { Integer uid = 20; String username = "資料管理員"; User user = new User(); user.setPhone("15512328888"); user.setEmail("admin03@cy.cn"); user.setGender(2); iUserService.changeInfo(uid, username, user); System.out.println("OK."); } catch (ServiceException e) { System.out.println(e.getClass().getSimpleName()); System.out.println(e.getMessage()); } }
說明:無需再次開發。
1.設計使用者提交顯示當前登入的使用者資訊的請求,並設計響應的方式。
請求路徑:/users/get_by_uid
請求引數:HttpSession session
請求型別:GET
響應結果:JsonResult<User>
2.設計使用者提交執行修改使用者資訊的請求,並設計響應的方式。
請求路徑:/users/change_info
請求引數:User user, HttpSession session
請求型別:POST
響應結果:JsonResult<Void>
1.處理獲取使用者資訊請求
1.在UserController類中新增處理請求的getByUid()方法,並匯入org.springframework.web.bind.annotation.GetMapping包。
@GetMapping("get_by_uid") public JsonResult<User> getByUid(HttpSession session) { // 從HttpSession物件中獲取uid // 呼叫業務物件執行獲取資料 // 響應成功和資料 return null; }
2.getByUid(HttpSession session)方法中具體程式碼實現為。
@GetMapping("get_by_uid") public JsonResult<User> getByUid(HttpSession session) { // 從HttpSession物件中獲取uid Integer uid = getUidFromSession(session); // 呼叫業務物件執行獲取資料 User data = userService.getByUid(uid); // 響應成功和資料 return new JsonResult<User>(OK, data); }
3.完成後啟動專案,開啟瀏覽器先登入,再存取http://localhost:8080/users/get_by_uid請求進行測試。
2.處理修改使用者個人資訊請求
1.在UserController類中新增處理請求的changeInfo(User user, HttpSession session)方法。
@RequestMapping("change_info") public JsonResult<Void> changeInfo(User user, HttpSession session) { // 從HttpSession物件中獲取uid和username // 呼叫業務物件執行修改使用者資料 // 響應成功 return null; }
2.changeInfo(User user, HttpSession session)方法中具體程式碼實現為。
@RequestMapping("change_info") public JsonResult<Void> changeInfo(User user, HttpSession session) { // 從HttpSession物件中獲取uid和username Integer uid = getUidFromSession(session); String username = getUsernameFromSession(session); // 呼叫業務物件執行修改使用者資料 userService.changeInfo(uid, username, user); // 響應成功 return new JsonResult<Void>(OK); }
3.完成後啟動專案,開啟瀏覽器先登入,再存取http://localhost:8080/users/change_info?phone=17858800000&email=admin07@cy.com&gender=1進行測試。
1.在userdata.html頁面中body標籤內部的最後,新增script標籤用於編寫JavaScript程式。
<script type="text/javascript"> $(document).ready(function() { $.ajax({ url: "/users/get_by_uid", type: "GET", dataType: "json", success: function(json) { if (json.state == 200) { console.log("username=" + json.data.username); console.log("phone=" + json.data.phone); console.log("email=" + json.data.email); console.log("gender=" + json.data.gender); $("#username").val(json.data.username); $("#phone").val(json.data.phone); $("#email").val(json.data.email); let radio = json.data.gender == 0 ? $("#gender-female") : $("#gender-male"); radio.prop("checked", "checked"); } else { alert("獲取使用者資訊失敗!" + json.message); } } }); }); $("#btn-change-info").click(function() { $.ajax({ url: "/users/change_info", type: "POST", data: $("#form-change-info").serialize(), dataType: "json", success: function(json) { if (json.state == 200) { alert("修改成功!"); location.href = "login.html"; } else { alert("修改失敗!" + json.message); } }, error: function(xhr) { alert("您的登入資訊已經過期,請重新登入!HTTP響應碼:" + xhr.status); location.href = "login.html"; } }); }); </script>
2.完成後啟動專案,開啟瀏覽器先登入,再存取http://localhost:8080/web/userdata.html頁面並進行使用者個人資料的修改測試。
到此這篇關於springboot使用者資料修改的文章就介紹到這了,更多相關springboot使用者資料修改內容請搜尋it145.com以前的文章或繼續瀏覽下面的相關文章希望大家以後多多支援it145.com!
相關文章
<em>Mac</em>Book项目 2009年学校开始实施<em>Mac</em>Book项目,所有师生配备一本<em>Mac</em>Book,并同步更新了校园无线网络。学校每周进行电脑技术更新,每月发送技术支持资料,极大改变了教学及学习方式。因此2011
2021-06-01 09:32:01
综合看Anker超能充系列的性价比很高,并且与不仅和iPhone12/苹果<em>Mac</em>Book很配,而且适合多设备充电需求的日常使用或差旅场景,不管是安卓还是Switch同样也能用得上它,希望这次分享能给准备购入充电器的小伙伴们有所
2021-06-01 09:31:42
除了L4WUDU与吴亦凡已经多次共事,成为了明面上的厂牌成员,吴亦凡还曾带领20XXCLUB全队参加2020年的一场音乐节,这也是20XXCLUB首次全员合照,王嗣尧Turbo、陈彦希Regi、<em>Mac</em> Ova Seas、林渝植等人全部出场。然而让
2021-06-01 09:31:34
目前应用IPFS的机构:1 谷歌<em>浏览器</em>支持IPFS分布式协议 2 万维网 (历史档案博物馆)数据库 3 火狐<em>浏览器</em>支持 IPFS分布式协议 4 EOS 等数字货币数据存储 5 美国国会图书馆,历史资料永久保存在 IPFS 6 加
2021-06-01 09:31:24
开拓者的车机是兼容苹果和<em>安卓</em>,虽然我不怎么用,但确实兼顾了我家人的很多需求:副驾的门板还配有解锁开关,有的时候老婆开车,下车的时候偶尔会忘记解锁,我在副驾驶可以自己开门:第二排设计很好,不仅配置了一个很大的
2021-06-01 09:30:48
不仅是<em>安卓</em>手机,苹果手机的降价力度也是前所未有了,iPhone12也“跳水价”了,发布价是6799元,如今已经跌至5308元,降价幅度超过1400元,最新定价确认了。iPhone12是苹果首款5G手机,同时也是全球首款5nm芯片的智能机,它
2021-06-01 09:30:45