您现在的位置是:网站首页> 内容页

如何快速上手SQL映射文件的编写

  • 88pt88手机客户端
  • 2019-02-21
  • 387人已阅读
简介在讲之前先说说它的好处:Mybatis真正强大之处就是在于SQL映射语句,也是他的魅力所在。相对于它强大的功能,SQL映射文件的配置却非常简单。简单的对比一下SQL映射配置和JDBC代

在讲之前先说说它的好处:Mybatis真正强大之处就是在于SQL映射语句,也是他的魅力所在。相对于它强大的功能,SQL映射文件的配置却非常简单。简单的对比一下SQL映射配置和JDBC代码,发现使用SQL映射文件配置可减少50%以上的代码量。并且MyBatis专注于SQL,对于开发人员来说,也可极大限度地进行SQL调优,以保证性能。

关于SQL映射文件的几个顶级元素配置:

顶级元素配置mapper:映射文件的根元素节点,只有一个属性namespace(命名空间),作用如下:

用于区分不同的mapper,全局唯一绑定DAO接口,即面向接口编程。当namespace绑定某一接口之后,可以不用写该接口的实现类, MyBatis会通过接口的完全限定名查找到对应的mapper配置来执行SQL语句,因此namespace的命名必须要跟接口同名

cache:配置给定命名空间的缓存cache-ref:从其他命名空间引用缓存配置resultMap:用来描述数据库结果集和对象的对应关系sql:可以重用的SQL块,也可以被其他语句引用insert:映射插入语句update:映射更新语句delete:映射删除语句select:映射查询语句

使用select完成单条件查询编写Mapper映射文件

<!--根据用户名查询用户列表(模糊查询)--><select id="getUserListByUserName" resultType="User" parameterType="string"> SELECT * FROM USER WHERE userName LIKE concat("%"#{userName}"%")</select>

各属性介绍:id:命名空间中唯一的标识符,可以被用来引用这条语句parameterType:表示查询语句传入参数的类型的完全限定名或别名。resultType:查询语句返回结果类型的完全限定名或别名别名表

别名映射的类型别名映射类型
stringStringdoubleDouble
byteBytefloatFloat
loangLongbooleanBoolean
shortShortdateDate
intIntegermapMap
integerIntegerhashmapHashMap
arrayListArrayListlistList

使用select实现多条件查询

使用对象入参编写映射文件

<select id="getUserListByUser" resultType="User" parameterType="User"> SELECT * FROM USER WHERE userName LIKE concat("%"#{userName}"%") and userRole=#{userRole}</select>

编写接口

List<User> getUserListByUser(User user)

编写测试

SqlSession sqlSession=nullList<User> userList=new ArrayList<User>() try{ sqlSession=MyBatisUtil.createSqlSession() User user=new User() user.setUserName("赵") user.setUserRole(3) userList=sqlSession.getMapper(UserMapper.class).getUserListByUser(user)}catch (Exception ex){ ex.printStackTrace()}finally { MyBatisUtil.closeSqlSession(sqlSession)}for (User user: userList) { System.out.println(user.getUserName()+""+user.getUserRole())}

使用Map入参编写接口

List<User> getUserListByMap(Map<StringString> userMap)

编写UserMapper.xml文件

<select id="getUserListByMap" resultType="User" parameterType="Map"> SELECT * FROM USER WHERE userName LIKE concat("%"#{userName}"%") and userRole=#{userRole}</select>

编写测试

SqlSession sqlSession=nullList<User> userList=new ArrayList<User>() try{ sqlSession=MyBatisUtil.createSqlSession() Map<StringString> userMap=new HashMap<StringString>() userMap.put("userName""赵") userMap.put("userRole""3") userList=sqlSession.getMapper(UserMapper.class).getUserListByMap(userMap)}catch (Exception ex){ ex.printStackTrace()}finally { MyBatisUtil.closeSqlSession(sqlSession)}for (User user: userList) { System.out.println(user.getUserName()+""+user.getUserRole())}

使用resultMap完成查询结果的展现

先在User类中加入userRoleName属性:private String userRoleName,及其相应的getter和setter方

编写UserMapper.xml文件,修改其中的getUserList方法

<select id="getUserList" resultMap="userList" parameterType="User"> SELECT u.*r.roleName FROM USER uRole r WHERE u.userName LIKE concat("%"#{userName}"%") AND u.userRole=#{userRole} AND u.userRole=r.id</select> 添加id为userList的resultMap元素节点 <resultMap id="userList" type="User"> <result property="id" column="id"/> <result property="userCode" column="userCode"/> <result property="userName" column="userName"/> <result property="phone" column="phone"/> <result property="birthday" column="birthday"/> <result property="gender" column="gender"/> <result property="userRole" column="userRole"/> <result property="userRoleName" column="roleName"/></resultMap>

测试

SqlSession sqlSession=nullList<User> userList=new ArrayList<User>() try{ sqlSession=MyBatisUtil.createSqlSession() User user=new User() user.setUserName("赵") user.setUserRole(3) userList=sqlSession.getMapper(UserMapper.class).getUserList(user) }catch (Exception ex){ ex.printStackTrace()}finally { MyBatisUtil.closeSqlSession(sqlSession)}for (User user: userList) { System.out.println(user.getUserName()+""+user.getUserRole()+""+user.getUserRoleName())}

resultMap元素的属性值和子节点:id属性:唯一标识,此id值用于select元素resultMap属性的引用type属性:表示该resultMap的映射结果类型result子节点:用于标识一些简答的属性,其中column属性表示从数据库中查询的字段名,property则表示查询出来的字段对应的赋值给实体对象的哪个属性resultType和resultMap的异同点及场景

1.resultType直接表示返回类型,包括基本数据类型和复杂数据类型2.resultMap则是对外部resultMap定义的引用,对应外部resultMap的id3.MyBatis的每个查询映射的返回类型都是resultMap当我们提供的返回类型是resultType,会自动赋值给指定属性4.resultMap自动映射界别默认映射级别为PARTIAL,在resultMap没有做映射关联时也能自动匹配。关闭方法:

<settings> <!--设置resultMap的自动映射级别为NONE(禁止自动匹配)--> <setting name="autoMappingBehavior" value="NONE"/> </settings>

实现增删改的操作

1使用insert完成增加操作在接口中添加add()方法int add(User user)在映射文件中编写插入语句

<insert id="add" parameterType="User"> INSERT INTO USER (userCodeuserNameuserPasswordgenderbirthday phoneaddressuserRolecreatedBycreationDate) VALUES (#{userCode}#{userName}#{userPassword}#{gender}#{birthday} #{phone}#{address}#{userRole}#{createdBy}#{creationDate})</insert>

编写测试代码

SqlSession sqlSession=null try{ sqlSession=MyBatisUtil.createSqlSession() User user=new User() user.setUserCode("testtt") user.setUserName("测试") user.setUserPassword("fajklfd") user.setGender(1) Date birthday=new SimpleDateFormat("yyyy-MM-dd").parse("1990-1-1") user.setBirthday(birthday) user.setPhone("1228392324") user.setAddress("北京") user.setUserRole(3) user.setCreatedBy(1) user.setCreationDate(new Date()) int count=sqlSession.getMapper(UserMapper.class).add(user) System.out.println("数量:"+count) sqlSession.commit()}catch (Exception ex){ ex.printStackTrace() sqlSession.rollback()}finally { MyBatisUtil.closeSqlSession(sqlSession)}

使用update完成修改

在接口中添加modify()方法int modify(User user)在映射文件中编写修改语句

<update id="modify" parameterType="User"> UPDATE USER SET userCode=#{userCode}userName=#{userName}userPassword=# {userPassword} gender=#{gender}phone=#{phone}address=#{address}userRole=#{userRole}modifyBy=# {modifyBy} modifyDate=#{modifyDate}birthday=#{birthday} WHERE id=#{id}</update>

编写测试代码

SqlSession sqlSession=null try{ sqlSession=MyBatisUtil.createSqlSession() User user=new User() user.setId(15) user.setUserCode("testtt") user.setUserName("测试修改") user.setUserPassword("fajklfd") user.setGender(1) Date birthday=new SimpleDateFormat("yyyy-MM-dd").parse("1990-1-1") user.setBirthday(birthday) user.setPhone("1228392324") user.setAddress("北京") user.setUserRole(3) user.setCreateBy(1) user.setCreationDate(new Date()) int count=sqlSession.getMapper(UserMapper.class).modify(user) //int i=2/0//测试事务回滚 System.out.println("数量:"+count) sqlSession.commit()}catch (Exception ex){ ex.printStackTrace() sqlSession.rollback()}finally { MyBatisUtil.closeSqlSession(sqlSession)}

使用@Param注解实现多参数入参

如果参数只有两个,封装成对象并不合适,多参数入参可读性高。在参数前增加@Param注解

int updatePwd(@Param("id")Integer id@Param("userPassword")String pwd)

编写修改语句

<update id="updatePwd"> UPDATE USER SET userPassword=#{userPassword} WHERE id=#{id}</update>

编写测试

SqlSession sqlSession=null try{ sqlSession=MyBatisUtil.createSqlSession() int id=15 String pwd="abc1223" int count=sqlSession.getMapper(UserMapper.class).updatePwd(idpwd) //int i=2/0//测试事务回滚 System.out.println("数量:"+count) sqlSession.commit()}catch (Exception ex){ ex.printStackTrace() sqlSession.rollback()}finally { MyBatisUtil.closeSqlSession(sqlSession)}

使用delete完成删除操作

编写接口方法

int deleteUserById(@Param("id")Integer delId)

在映射文件中编写删除语句

<delete id="deleteUserById"> DELETE FROM USER WHERE id=#{id}</delete>

编写测试

SqlSession sqlSession=nulltry{ sqlSession=MyBatisUtil.createSqlSession() int id=15 int count=sqlSession.getMapper(UserMapper.class).deleteUserById(id) System.out.println("数量:"+count) sqlSession.commit()}catch (Exception ex){ ex.printStackTrace() sqlSession.rollback()}finally { MyBatisUtil.closeSqlSession(sqlSession)}

使用resultMap实现高级结果映射(表表关联)

使用resultMap实现高级结果映射(表表关联)

Role类public class Role { private Integer id private String roleCode private String roleName private Integer createdBy private Date creationDate private Integer modifyBy private Date modifyDate //省略getter和setter}

修改pojo User类

public class User { private Integer id //id private String userCode //用户编码 private String userName //用户名称 private String userPassword //用户密码 private Integer gender //性别 private Date birthday //出生日期 private String phone //电话 private String address //地址 private Integer userRole //用户角色 private Integer createdBy //创建者 private Date creationDate //创建时间 private Integer modifyBy //更新者 private Date modifyDate //更新时间 //private String userRoleName //用户角色名称 private Role role //省略getter&setter方法}在UserMapper接口中添加方法List<User> getUserListByRoleId(@Param("userRole")Integer roleId)

修改UserMapper.xml 增加getUserListByRoleIdxml <resultMap id="userRoleResult" type="User"> <id property="id" column="id"/> <result property="userCode" column="userCode"/> <result property="userName" column="userName"/> <result property="userRole" column="userRole"/> <association property="role" javaType="Role"> <id property="id" column="r_id"/> <result property="roleCode" column="roleCode"/> <result property="roleName" column="roleName"/> </association> </resultMap> <select id="getUserListByRoleId" parameterType="Integer" resultMap="userRoleResult"> SELECT u.*r.id AS r_idr.roleCoder.roleName FROM user urole r WHERE u.userRole=#{userRole} and u.userRole=r.id </select>使用外部resultMap复用配置

<resultMap id="roleResult" type="Role"> <id property="id" column="r_id"/> <result property="roleCode" column="roleCode"/> <result property="roleName" column="roleName"/></resultMap><resultMap id="userRoleResult" type="User"> <id property="id" column="id"/> <result property="userCode" column="userCode"/> <result property="userName" column="userName"/> <result property="userRole" column="userRole"/> <association property="role" javaType="Role" resultMap="roleResult"/></resultMap>

collection 一对多关联创建pojo Addres.java

public class Address { private Integer id private String contact private String addressDesc private String postCode private String tel private Integer createdBy private Date creationDate private Integer modifyBy private Date modifyDate private Integer userId //省略getter和setter}

修改User类增加地址列表属性

List<Address>addressList

编写接口中的方法

List<User> getAddressListByUserId(@Param("id")Integer userId)

编写映射文件

<resultMap id="addressResult" type="Address"> <id column="a_id" property="id"/> <result property="postCode" column="postCode"/> <result property="tel" column="tel"/> <result property="contact" column="contact"/> <result property="addressDesc" column="addressDesc"/></resultMap><resultMap id="userAddressResult" type="User"> <id property="id" column="id"/> <result property="userCode" column="userCode"/> <result property="userName" column="userName"/> <collection property="addressList" ofType="Address" resultMap="addressResult"/></resultMap>

编写测试

SqlSession sqlSession=null try{ sqlSession=MyBatisUtil.createSqlSession() List<User> userList=sqlSession.getMapper(UserMapper.class).getAddressListByUserId(1) for (User user: userList) { System.out.println(user.getUserName()) List<Address> addresses=user.getAddressList() for (Address address: addresses) { System.out.println("--- "+address.getContact()) } }}catch (Exception ex){ ex.printStackTrace()}finally { MyBatisUtil.closeSqlSession(sqlSession)}

resultMap自动映射级别和MyBatis缓存

autoMappingBehavior的三个级别NONE:禁止自动匹配PARTIAL:(默认)自动匹配所有属性,有内部嵌套(assocition,collection)除外FULL:自动匹配所有

文章评论

Top