java框架之mybatis(SQL映射文件)
Posted Lazy的笔记
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了java框架之mybatis(SQL映射文件)相关的知识,希望对你有一定的参考价值。
MyBatis真正的强大在于映射语句,专注于SQL,功能强大,SQL映射的配置却是相当简单
SQL映射文件的几个顶级元素(按照定义的顺序)
mapper-namespace
cache-配置给定命名空间的缓存
cache-ref - 从其他命名空间引用缓存配置
resultMap -用来描述数据库结构集和对象的对应关系
sql -可以重用的SQL块,也可以被其他语句引用
insert - 映射插入语句
update -映射更新语句
delete -映射删除语句
select -映射查询语句
mapper元素
namespace:命名空间
namespace和子元素的id联合保证唯一,区别不同的mapper
绑定DAO接口
namespace的命名必须跟某个接口同名
接口中的方法与映射文件中的SQL语句id——对应
<mapper namespace="cn.smbms.dao.user.UserMapper">
<!-- 查询用户表记录数 -->
<select id="count" resultType="int">
select count(1) as count from smbms_user
</select>
<!-- 查询用户列表 -->
<select id="getUserList" resultType="cn.smbms.pojo.User">
select * from smbms_user
</select>
</mapper>
namespace="cn.smbms.dao.user.UserMapper"一定要给DAO类保持一致,id与接口方法同名
resultType="cn.smbms.pojo.User"这是类的类型,id="getUserList"是方法名
UserMapper类
package cn.smbms.dao.user;
import java.util.List;
import cn.smbms.pojo.User;
public interface UserMapper {
public List<User> getUserList();
}
select语句有很多属性可以详细配置每一个语句
id
命名空间中唯一的标识符
接口中的方法与映射文件中的SQL语句id一一对应
parameterType
传入SQL语句的参数类型的完全限定名或别名
基础数据类型
int、String 、Date等
只能传入一个,通过#{参数名}即可获取传入值
复杂数据类型
java实体类、Map等
通过#{属性名}或#{Map的key}即可获取传入的值
(支持基础数据类型和复杂数据类型,不区分大小写可以是String和string)
resultType
SQL语句返回值类型的完整类名或别名
<!-- 根据用户名称查询用户列表(模糊查询) -->
<select id="getUserListByUserName" parameterType="string" resultType="User">
select * from smbms_user where userName like CONCAT ('%',#{userName},'%')
</select>
参数传递:#{参数名}/parameterType="string" 参数类型
注:数据库字段名与JavaBean的属性名一致
使用resultMap
连表查询
第一种方式
1、修改User的属性,增加userRoleName属性【在数据库的smbms_user中没有这一行属性】
2、修改查询sql语句,连表查询
<select id="getUserList2" resultType="User" parameterType="user">
select u.*,r.roleName as userRoleName from smbms_user
u,smbms_role r where userName like CONCAT ('%',#{userName},'%')
and userRole=#{userRole} and u.userRole=r.id
</select> -->
第二种方式:
修改User的属性,增加userRoleName属性
使用resultMap自定义查询结果
<!-- 使用resultMap自定义查询结果 -->
<resultMap type="user" id="userList">
<result property="id" column="id"/>
<result property="userCode" column="userCode"/>
<result property="userName" column="userName"/>
<result property="userRoleName" column="roleName" />
</resultMap>
<select id="getUserList2" resultMap="userList" parameterType="user">
select u.*,r.roleName from smbms_user u,smbms_role r
where userName like CONCAT ('%',#{userName},'%')
and userRole=#{userRole} and u.userRole=r.id
</select>
<result property="userRoleName" column="roleName" />不在同一表的属性,在smbms_role表中的中文描述角色,而在用户表中是用userRole描述是用数字描述的,通过u.userRole=r.id条件,roleName的值赋予userRoleName;roleName,并显示查询结果
<result property="userName" column="userName"/>是在同一个表中查询的,
property表示查询处理的属性对应的值赋给实体对象的哪个属性,column从数据库查询的列名。
resultType:直接表示返回类型
基础数据类型
复杂数据类型
resultMap:对外部resultMap的引用
应用场景
数据库字段信息与对象属性不一致
复杂的联合查询,自由控制映射结果
二者不能同时存在,本质上都是Map数据结构
resultMap自动映射匹配前提:字段名与属性名一致
resultMap的自动映射级别(autoMappingBehavior)
PARTIAL(默认):自动匹配所有属性
在mybatis-config.xml配置
<settings>
<setting name="autoMappingBehavior" value="NONE"/>
</settings>
使用MyBatis来实现增加、修改,删除
<!-- 插入数据 -->
<insert id="add" parameterType="User">
insert into smbms_user (userCode,userName,userPassword,
gender,birthday,phone,address,
userRole,createBy,creationDate)
values(#{userCode},#{userName},
#{userPassword},#{gender},
#{birthday},#{phone},#{address},
#{userRole},#{createBy},#{creationDate})
</insert>
<!-- 更新数据 -->
<update id="modify" parameterType="User">
update smbms_user set userCode=#{userCode}
,userName=#{userName} where id=#{id}
</update>
传入参数(多个):用户id和新密码
使用注解@param来传入多个参数
映射SQL中的参数:#{注解名称}
public int updatePwd(@Param("id")Integer id,@Param("userPassword")String userPassword);//接口类的参数设置@Param("id"),其中id是注解名称
<!-- 修改密码 -->
<update id="updatePwd" parameterType="User">
update smbms_user set
userPassword=#{userPassword} where id=#{id}
</update>
注:四个以上的参数封装成对象入参。
<!-- 删除记录 -->
<delete id="deleteUserById" parameterType="Integer">
delete from smbms_user where id=#{id}
</delete>
DAO层接口方法常见的返回类型
java对象、Map、List等复杂数据类型
Int(增、删、改)更新操作时影响的数据行数
resultMap属性
id:resultMap的唯一标识
type:java实体类
resultMap子元素
id 一般对应数据库该行的主键id,设置此项可提高MyBatis性能
result 映射到JavaBean的某个简单类型属性
association 映射到javaBean的某个复杂类型属性,比如javaBean类
collection 映射到JavaBean的某个复杂类型属性,比如集合
association
复杂的类型关联,一对一
内部嵌套 映射一个嵌套JavaBean属性
属性
property:映射数据列的实体对象的属性
javaType:完整Java类名或者别名
resultMap:引用外部resultMap
子元素
id
result
property:映射数据库列的实体对象的属性
column:数据库列名或者别名
<!-- resultMap多表查询应用 -->
<resultMap type="User" id="userRoleResult">
<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" />//嵌套类型的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_id,r.roleCode,r.roleName
from smbms_user u,smbms_role r
where u.userRole=#{userRole} and u.userRole=r.id
</select>
<association property="role" javaType="Role">
Role是用户角色实体类,在User实体类被用作属性类型,role是属性名称
相当于将类Role以属性性质嵌套在类User中,通过调用get方法获得Role类,进而获取它里面的属性。
注:一般实体类的属性名称跟数据库表中的列名称一致。
<!-- resultMap多表查询应用 -->
<resultMap type="Role" id="roleResult">
<id property="id" column="r_id" />
<result property="roleCode" column="roleCode" />
<result property="roleName" column="roleName" />
</resultMap>
<resultMap type="User" id="userRoleResult">
<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>
<select id="getUserListByRoleId" parameterType="Integer" resultMap="userRoleResult">
select u.*,r.id as r_id,r.roleCode,r.roleName
from smbms_user u,smbms_role r
where u.userRole=#{userRole} and u.userRole=r.id
</select>
collection
复杂类型集合,一对多
内部嵌套 映射一个嵌套结果集到一个列表
属性
property:映射数据库列的实体对象的属性
ofType:完整Java类名或者别名(集合包括的类型)
resultMap:引用外部resultMap
子元素
id
result
property:映射数据库列的实体对象的属性
column:数据库列名或者别名
<!-- collection应用 -->
<resultMap type="User" id="userAddressResult">
<id property="id" column="id"/>
<result property="userCode" column="userCode" />
<result property="userName" column="userName" />
<collection property="addressList" ofType="Address">
<id property="id" column="a_id"/>
<result property="contact" column="contact" />
<result property="addressDesc" column="addressDesc" />
</collection>
</resultMap>
<select id="getAddressListByUserId" parameterType="Integer"
resultMap="userAddressResult" >
select u.*,a.id as a_id,a.contact,a.addressDesc
from smbms_user u,smbms_address a
where u.id=a.userId and u.id=#{id}
</select>
MyBatis缓存
一级缓存(在session作用域范围内)
二级缓存(全局缓存application)
二级缓存的配置
在mybatis-config.xml文件中设置
<settings>
<setting name="cacheEnabled" value="true" />
</settings>
在MapperXML文件中设置缓存,默认情况下:未开启
<cache eviction="FIFO" flushInterval=60000"
size="512" readOnly="true" />
在Mapper XML文件中配置支持cache后,若需要对个别查询进行调整,可以单独设置cache
<select id="selectAll" resultType="Emp" useCache="true">
实际用的很少
以上是关于java框架之mybatis(SQL映射文件)的主要内容,如果未能解决你的问题,请参考以下文章
mybatis xml数据层框架应用--Mybatis关系映射之一对一关系映射