Mybatis—代理开发和核心配置文件深入
代理開發方式介紹
采用 Mybatis 的代理開發方式實現 DAO 層的開發,這種方式是我們后面進入企業的主流。
Mapper 接口開發方法只需要程序員編寫Mapper 接口(相當于Dao 接口),由Mybatis 框架根據接口定義創建接口的動態代理對象,代理對象的方法體同上邊Dao接口實現類方法。
Mapper 接口開發需要遵循以下規范:
1) Mapper.xml文件中的namespace與mapper接口的全限定名相同
2) Mapper接口方法名和Mapper.xml中定義的每個statement的id相同
3) Mapper接口方法的輸入參數類型和mapper.xml中定義的每個sql的parameterType的類型相同
4) Mapper接口方法的輸出參數類型和mapper.xml中定義的每個sql的resultType的類型相同
public interface userMapper {public List<User> findAll(); } @Testpublic void tset4() {InputStream resourceAsStream = null;try {resourceAsStream = Resources.getResourceAsStream("SqlMapConfig.xml");} catch (IOException ioException) {ioException.printStackTrace();}SqlSessionFactory sqlSessionFactory=new SqlSessionFactoryBuilder().build(resourceAsStream);SqlSession sqlSession = sqlSessionFactory.openSession(true);userMapper userMapper=sqlSession.getMapper(com.controller.userMapper.class);List<User> aLl = userMapper.findAll();System.out.println(aLl);} <?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="com.controller.userMapper"><select id="findAll" resultType="user">select * from user</select></mapper>動態 SQL 之<if>
我們根據實體類的不同取值,使用不同的 SQL語句來進行查詢。比如在 id如果不為空時可以根據id查詢,如果username 不同空時還要加入用戶名作為條件。這種情況在我們的多條件組合查詢中經常會碰到。
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="com.controller.userMapper"><select id="findAll" resultType="user">select * from user</select><select id="findById" resultType="user" parameterType="user">select * from user<where><if test="id!=0">and id=#{id}</if><if test="username!=null">and username=#{username}</if></where></select> </mapper> public interface userMapper {public List<User> findAll();public User findById(User user); }動態 SQL 之<foreach>
循環執行sql的拼接操作,例如:SELECT * FROM USER WHERE id IN (1,2,5)。
foreach標簽的屬性含義如下:
標簽用于遍歷集合,它的屬性:
?collection:代表要遍歷的集合元素,注意編寫時不要寫#{}
?open:代表語句的開始部分
?close:代表結束部分
?item:代表遍歷集合的每個元素,生成的變量名
?sperator:代表分隔符
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="com.controller.userMapper"><sql id="selectUser" >select * from User</sql><select id="findAll" resultType="user">select * from user</select><select id="findById" resultType="user" parameterType="user"><include refid="selectUser"></include><where><if test="id!=0">and id=#{id}</if><if test="username!=null">and username=#{username}</if></where></select><select id="findByIds" parameterType="list" resultType="user"><include refid="selectUser"></include><where><foreach collection="list" open="id in (" close=")" item="id" separator=",">#{id}</foreach></where></select> </mapper> public interface userMapper {public List<User> findAll();public User findById(User user);public List<User> findByIds(List<Integer> list); } @Testpublic void tset4() {InputStream resourceAsStream = null;try {resourceAsStream = Resources.getResourceAsStream("SqlMapConfig.xml");} catch (IOException ioException) {ioException.printStackTrace();}SqlSessionFactory sqlSessionFactory=new SqlSessionFactoryBuilder().build(resourceAsStream);SqlSession sqlSession = sqlSessionFactory.openSession(true);userMapper userMapper=sqlSession.getMapper(com.controller.userMapper.class);User user = new User();user.setId(1);User user1 = new User();user1.setId(2);List<Integer> list=new ArrayList<>();list.add(1);list.add(2);System.out.println(userMapper.findByIds(list));}2.2 SQL片段抽取
Sql 中可將重復的 sql 提取出來,使用時用 include 引用即可,最終達到 sql 重用的目的
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="com.controller.userMapper"><sql id="selectUser" >select * from User</sql><select id="findAll" resultType="user">select * from user</select><select id="findById" resultType="user" parameterType="user"><include refid="selectUser"></include><where><if test="id!=0">and id=#{id}</if><if test="username!=null">and username=#{username}</if></where></select><select id="findByIds" parameterType="list" resultType="user"><include refid="selectUser"></include><where><foreach collection="list" open="id in (" close=")" item="id" separator=",">#{id}</foreach></where></select> </mapper>MyBatis核心配置文件深入
typeHandlers標簽
無論是 MyBatis 在預處理語句(PreparedStatement)中設置一個參數時,還是從結果集中取出一個值時, 都會用類型處理器將獲取的值以合適的方式轉換成 Java 類型。下表描述了一些默認的類型處理器(截取部分)。
你可以重寫類型處理器或創建你自己的類型處理器來處理不支持的或非標準的類型。具體做法為:實現 org.apache.ibatis.type.TypeHandler 接口, 或繼承一個很便利的類 org.apache.ibatis.type.BaseTypeHandler, 然后可以選擇性地將它映射到一個JDBC類型。例如需求:一個Java中的Date數據類型,我想將之存到數據庫的時候存成一個1970年至今的毫秒數,取出來時轉換成java的Date,即java的Date與數據庫的varchar毫秒值之間轉換。
開發步驟:
①定義轉換類繼承類BaseTypeHandler
②覆蓋4個未實現的方法,其中setNonNullParameter為java程序設置數據到數據庫的回調方法,getNullableResult為查詢時 mysql的字符串類型轉換成 java的Type類型的方法
public class MyDateTypeHandler extends BaseTypeHandler<Date> {@Overridepublic void setNonNullParameter(PreparedStatement preparedStatement, int i, Date date, JdbcType jdbcType) throws SQLException {preparedStatement.setString(i,date.getTime()+"");}@Overridepublic Date getNullableResult(ResultSet resultSet, String s) throws SQLException {return new Date(resultSet.getLong(s));}@Overridepublic Date getNullableResult(ResultSet resultSet, int i) throws SQLException {return new Date(resultSet.getLong(i));}@Overridepublic Date getNullableResult(CallableStatement callableStatement, int i) throws SQLException {return callableStatement.getDate(i);} }③在MyBatis核心配置文件中進行注冊
<typeHandlers><typeHandler handler="com.MyDateTypeHandler"/> </typeHandlers>測試轉換是否正確
@Testpublic void tset4() {InputStream resourceAsStream = null;try {resourceAsStream = Resources.getResourceAsStream("SqlMapConfig.xml");} catch (IOException ioException) {ioException.printStackTrace();}SqlSessionFactory sqlSessionFactory=new SqlSessionFactoryBuilder().build(resourceAsStream);SqlSession sqlSession = sqlSessionFactory.openSession(true);userMapper userMapper=sqlSession.getMapper(com.controller.userMapper.class);User user = new User();user.setUsername("xx");user.setPassword("123");user.setBirthday(new Date());userMapper.add(user);}plugins標簽
MyBatis可以使用第三方的插件來對功能進行擴展,分頁助手PageHelper是將分頁的復雜操作進行封裝,使用簡單的方式即可獲得分頁的相關數據
開發步驟:
①導入通用PageHelper的坐標
<dependency><groupId>com.github.pagehelper</groupId><artifactId>pagehelper</artifactId><version>3.7.5</version></dependency><dependency><groupId>com.github.jsqlparser</groupId><artifactId>jsqlparser</artifactId><version>0.9.1</version></dependency>②在mybatis核心配置文件中配置PageHelper插件
<plugins><plugin interceptor="com.github.pagehelper.PageHelper"><property name="dialect" value="mysql"/></plugin> </plugins>③測試分頁數據獲取
@Testpublic void tset4() {InputStream resourceAsStream = null;try {resourceAsStream = Resources.getResourceAsStream("SqlMapConfig.xml");} catch (IOException ioException) {ioException.printStackTrace();}SqlSessionFactory sqlSessionFactory=new SqlSessionFactoryBuilder().build(resourceAsStream);SqlSession sqlSession = sqlSessionFactory.openSession(true);userMapper userMapper=sqlSession.getMapper(com.controller.userMapper.class);PageHelper.startPage(2,2);List<User> all = userMapper.findAll();for (User user : all) {System.out.println(user);}PageInfo<User> pageInfo = new PageInfo<User>(all);System.out.println("總條數:"+pageInfo.getTotal());System.out.println("總頁數:"+pageInfo.getPages());System.out.println("當前頁:"+pageInfo.getPageNum());System.out.println("每頁顯示長度:"+pageInfo.getPageSize());System.out.println("是否第一頁:"+pageInfo.isIsFirstPage());System.out.println("是否最后一頁:"+pageInfo.isIsLastPage());}總結
以上是生活随笔為你收集整理的Mybatis—代理开发和核心配置文件深入的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: leetcode 485. 最大连续1的
- 下一篇: leetcode 561. 数组拆分 I