您好,登錄后才能下訂單哦!
這篇文章主要介紹了Mybatis-Plus進階分頁,樂觀鎖插件,通用枚舉和多數據源實例分析的相關知識,內容詳細易懂,操作簡單快捷,具有一定借鑒價值,相信大家閱讀完這篇Mybatis-Plus進階分頁,樂觀鎖插件,通用枚舉和多數據源實例分析文章都會有所收獲,下面我們一起來看看吧。
??MP中自帶了分頁插件的功能,只需要在配置類中進行簡單的配置即可使用分頁的相關功能。分頁插件常常與前端的分頁顯示功能相關,為了在前端美觀的顯示查詢到的數據,通常會使用分頁插件,將所有的數據分成許多頁一頁一頁的進行顯示,不同頁的切換使用按鈕來完成 MP的插件配置類
@Configuration public class MybatisPlusConfiguration { @Bean public MybatisPlusInterceptor mybatisPlusInterceptor() { // 創建一個MybatisPlus的插件攔截器 MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor(); // 創建分頁的插件對象并設置數據庫類型 PaginationInnerInterceptor paginationInnerInterceptor = new PaginationInnerInterceptor(DbType.MYSQL); // 設置請求的頁面大于最大頁后操作, true調回到首頁,false 繼續請求 默認false paginationInnerInterceptor.setOverflow(true); // 設置分頁的單頁最多條數,默認 500 條,-1 不受限制 paginationInnerInterceptor.setMaxLimit(500L); // 將這個分頁插件添加到攔截器中并返回 interceptor.addInnerInterceptor(paginationInnerInterceptor); return interceptor; } }
自定義方法并調用分頁 mapper定義方法
@Mapper @Repository public interface UserMapper extends BaseMapper<User> { /** * 通過年齡查詢用戶信息并分頁返回 * @param page 傳入一個page對象 * @param age 年齡 * @return 返回一個page對象 */ Page<User> selectPageVo(@Param("page") Page<User> page, @Param("age") Integer age); }
映射文件編寫SQL語句
<mapper namespace="com.xiaochen.mapper.UserMapper"> <select id="selectPageVo" resultType="com.xiaochen.domain.User"> select id,name,age,email from user where age > #{age} </select> </mapper>
測試方法調用自定義方法
@Autowired UserMapper mapper; @Test public void testpage() { // 創建一個page對象,設置當前頁是第1頁,每頁包含3條記錄 Page<User> page = new Page<>(2, 3); // mapper調用selectPage方法之后將結果返回給上面的page對象 // 第二個參數null的話就是查詢所有的記錄,如果有查詢條件的話就傳一個wrapper對象 mapper.selectPageVo(page, 20); // 當前頁的數據 System.out.println(page.getRecords()); // 當前是第幾頁 System.out.println(page.getCurrent()); // 總頁數 System.out.println(page.getPages()); // 每頁的記錄數 System.out.println(page.getSize()); // 總記錄數 System.out.println(page.getTotal()); // 是否有下一頁 System.out.println(page.hasNext()); // 是否有上一頁 System.out.println(page.hasPrevious()); }
??要想使用樂觀鎖插件,首先要知道什么是樂觀鎖以及樂觀鎖出現的原因。現實生活中,一個管理系統往往不僅僅只有一個管理員,以修改商品價格為例,如果有兩個管理員小李和小王商品的原價為100,老板先是讓小李將商品的價格上調50,一段時間后讓小王將商品的價格下調20,由于小李有事耽擱,兩個人同時登錄管理系統獲取到商品的價格對其分別進行修改操作。如果小李最后完成操作的話商品最終為150元,如果小王最后完成操作的話商品最終為80元,這樣的話就會造成最終的價格不是老板想要的130。 要想使用代碼實現上述案例的話,使用線程來實現的話更加真實(可以模擬兩人處理先后的不確定性),但是為了簡化操作,設定最后完成操作的是小王,也即是說最后商品的價格為80
@Test public void happyLockTest() { // 小李查詢商品的價格 Product productLi = mapper.selectById(1); // 小王查詢到商品的價格 Product productWang = mapper.selectById(1); // +50 productLi.setPrice(productLi.getPrice() + 50); mapper.updateById(productLi); // -20 productWang.setPrice(productWang.getPrice() - 20); mapper.updateById(productWang); // 查詢最終的商品價格 System.out.println("最終價格為:" + mapper.selectById(1).getPrice()); }
// 控制臺最終打印 -> 最終價格為:80
??有問題就有解決問題的方法,出現這個問題的原因就是兩個管理員同時獲取到了商品的信息并對他進行了修改,如果可以使用鎖限制同一時間只能有一個管理員對數據進行修改操作的話,就可以避免這個問題了,這就是悲觀鎖。
??不對啊,不是說要講樂觀鎖的嘛怎么講到了悲觀鎖了?悲觀鎖將整張表鎖住了,阻止其他人對表進行修改操作,這樣的話對效率有很大的折損。于是樂觀鎖應運而生,樂觀鎖允許任何人任何時候對表中數據進行修改,只不過數據表中要添加一個字段表示數據的當前版本號,數據每經過一次更新版本號就相應加一,數據每次更新的時候都會帶上版本號字段作為更新的條件。這樣的話就可以避免之前的問題了,兩人同時獲取到的版本都是0,小李修改之后就會將版本字段值加一也就是1,這時小王修改的時候就會查不到表中版本號為0的數據而無法修改。
??這樣的話就會避免修改沖突,但是還是無法得到想要的結果,于是可以對兩人的修改結果進行判斷,如果更新操作的返回結果不是0的話就說明更新成功,否則就再次獲取數據表中的信息(這次就是為了獲得最新的版本號)再次進行更新操作
??使用MP中的樂觀鎖插件,首先需要在配置類中將樂觀鎖插件添加到攔截器中,然后再在實體類中的版本號字段上使用@Version標志,然后就是和平常一樣的操作數據庫即可,執行更新操作的時候會自動將當前查詢到的版本號當做條件拼接到SQL語句中
// 將樂觀鎖插件添加到攔截器中 interceptor.addInnerInterceptor(new OptimisticLockerInnerInterceptor()); // 實體類標注版本號 @Version private Integer version; // 測試方法,測試兩個人最后的修改結果 @Test public void happyLockTest() { // 小李查詢商品的價格 Product productLi = mapper.selectById(1); // 小王查詢到商品的價格 Product productWang = mapper.selectById(1); // +50 int result = 0; do { // 更新失敗,重新查詢并修改 productLi = mapper.selectById(1); productLi.setPrice(productLi.getPrice() + 50); result = mapper.updateById(productLi); } while (result == 0); // -20 do { // 更新失敗,重新查詢并修改 productWang = mapper.selectById(1); productWang.setPrice(productWang.getPrice() - 20); result = mapper.updateById(productWang); } while (result == 0); // 查詢最終的商品價格 System.out.println("最終價格為:" + mapper.selectById(1).getPrice()); }
// 控制臺最終打印 -> 最終價格為:130
??對于表中擁有固定幾個值的一些字段,可以使用枚舉類將比較簡單的數字或字符存入到數據庫表中,然后將這個簡單的數字或字符對應著其具體的字符串表示,比如性別0代表女1代表男。這樣就會減輕數據庫的存儲壓力,提高用戶的使用體驗。 使用MP的通用枚舉必須先創建一個枚舉類,向外提供屬性的getter方法和全參構造器,并使用@EnumValue注解將標識的屬性值在數據庫中存儲
@Getter @AllArgsConstructor public enum SexEnum { FEMALE(0, "女"), MALE(1, "男"); // 將注解標識的屬性值存儲到數據庫中 @EnumValue private Integer sex; private String sexName; }
??然后實體類中修改字段對應屬性的類型為枚舉類型,然后重寫toString方法,方便查詢結果顯示為數據表中數字或字符對應的具體的字符串表示
// 修改字段對應屬性的類型為枚舉類型 private SexEnum sex; // 重寫toString方法 @Override public String toString() { return "User{" + "id=" + id + ", name='" + name + '\'' + ", sex=" + sex.getSexName() + ", age=" + age + ", email='" + email + '\'' + ", isDeleted=" + isDeleted + '}'; }
??最后在配置文件中設置通用枚舉的包,也就是相當于讓你寫的枚舉類生效
mybatis-plus: # 設置通用枚舉的包 type-enums-package: com.xiaochen.enums
測試
@Test public void enumTest() { User user = new User(); user.setName("張三"); user.setAge(23); user.setSex(SexEnum.FEMALE); mapper.insert(user); User user1 = mapper.selectById(6); System.out.println(user1); }
測試結果
??多數據源就是在一個程序中同時配置多個數據庫作為數據源進行操作,適用于多種場景:純粹多庫、 讀寫分離、 一主多從、 混合模式等。目前我們就來模擬一個純粹多庫的一個場景,配置兩個數據庫的兩張表,通過一個測試用例分別獲取兩張表的數據,如果獲取到說明多庫模擬成功
第一步: 導入依賴
<!--mybatis-的場景啟動器--> <dependency> <groupId>com.baomidou</groupId> <artifactId>mybatis-plus-boot-starter</artifactId> <version>3.5.1</version> </dependency>
第二步: 配置文件配置多數據源
spring:
# 配置數據源信息
datasource:
dynamic:
# 設置默認的數據源或者數據源組,當設置的數據源都找不到時使用默認數據源,默認值即為master
primary: master
# 嚴格匹配數據源,默認false.true未匹配到指定數據源時拋異常,false匹配不到指定數據源時使用默認數據源
strict: false
datasource:
# 主數據源
master:
driver-class-name: com.mysql.jdbc.Driver
url: jdbc:mysql://localhost:3306/mybatis_plus
username: root
password: 123456
# 從數據源
slave_1:
driver-class-name: com.mysql.jdbc.Driver
url: jdbc:mysql://localhost:3306/test
username: root
password: 123456
第三步: 照常使用方法測試在兩個數據庫查詢兩張表,唯一不同的就是在service的實現類上使用@DS注解,標注service實現類的所有方法都是對指定數據源進行操作的
測試類及結果
關于“Mybatis-Plus進階分頁,樂觀鎖插件,通用枚舉和多數據源實例分析”這篇文章的內容就介紹到這里,感謝各位的閱讀!相信大家對“Mybatis-Plus進階分頁,樂觀鎖插件,通用枚舉和多數據源實例分析”知識都有一定的了解,大家如果還想學習更多知識,歡迎關注億速云行業資訊頻道。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。