您的位置:首页 > 其它

MyBatis基础(二)—持久层开发的两种方法

2016-06-14 18:42 155 查看
SqlSession作用范围

持久层开发的两种方法
原始的DAO开发方式

mapper自动代理的开发方式
mapper开发规范

mapper开发的主要mapperxml和mapper接口

补充SqlMapConfig中几个配置
typeAliases

mappers配置

输入输出映射
parameterType

resultType

resultMap

动态SQL
SQL片段

if和where

foreach

完整代码

SqlSession作用范围

SqlSessionFactoryBuilder

SqlSessionFactoryBuilder是以工具类方式来使用,需要创建sqlSessionFactory就new一个SqlSessionFactoryBuilder。

sqlSessionFactory

正常开发时,以单例方式管理sqlSessionFactory,整个系统运行过程中sqlSessionFactory只有一个实例,将来和spring整合后由spring以单例方式管理sqlSessionFactory。

SqlSession

sqlSession是一个面向用户(程序员)的接口,程序员调用sqlSession的接口方法进行操作数据库。

由于sqlSession是线程不安全,(查看MyBatis的源码,Executor的实现类中currentSql、currentStatement等为成员变量),所以sqlSession最佳应用范围在方法体内,在方法体内定义局部变量使用sqlSession。

持久层开发的两种方法

原始的DAO开发方式

DAO接口和实现

UserDao

public interface UserDao {
public User findUserById(int id) throws Exception;

public List<User> findUserByUsername(String username) throws Exception;

public void insertUser(User user) throws Exception;

}


UserDaoImpl

public class UserDaoImpl implements UserDao {
private SqlSessionFactory sqlSessionFactory;

public UserDaoImpl(SqlSessionFactory sqlSessionFactory) {
this.sqlSessionFactory = sqlSessionFactory;
}

@Override
public User findUserById(int id) throws Exception {
// 创建SqlSession
SqlSession sqlSession = sqlSessionFactory.openSession();

User user = sqlSession.selectOne("test.findUserById", id);

sqlSession.close();
return user;
}

@Override
public List<User> findUserByUsername(String username) throws Exception {
SqlSession sqlSession = sqlSessionFactory.openSession();
List<User> list = sqlSession.selectList("test.findUserByName", username);
sqlSession.close();
return list;
}

@Override
public void insertUser(User user) throws Exception {
SqlSession sqlSession = sqlSessionFactory.openSession();
sqlSession.insert("test.insertUser", user);
sqlSession.commit();
sqlSession.close();
}
}


测试类

public class UserDaoImplTest {
private SqlSessionFactory sqlSessionFactory;

@Before
public void init() throws IOException {
String resource = "SqlMapConfig.xml";

//MyBatis提供了Resources读取配置文件
InputStream inputStream = Resources.getResourceAsStream(resource);

sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
}

@Test
public void testFindUserById() throws Exception {
UserDao userDao = new UserDaoImpl(sqlSessionFactory);

User user = userDao.findUserById(1);
System.out.println(user);
}
}


User.xml同上一篇博文

mapper自动代理的开发方式

mapper开发规范

mapper.xml中namespace指定为mapper接口的全限定名

此步骤目的:通过mapper.xml和mapper.java进行关联。

mapper.xml中statement的id就是mapper.java中方法名

mapper.xml中statement的parameterType和mapper.java中方法输入参数类型一致

mapper.xml中statement的resultType和mapper.java中方法返回值类型一致.

mapper开发的主要mapper.xml和mapper接口

mapper映射文件的命名方式建议:类名+Mapper.xml

mapper接口(相当于DAO接口)的命名方式建议:类名+Mapper

UserMapper

public interface UserMapper {
public User findUserById(int id) throws Exception;

public List<User> findUserByName(String username) throws Exception;
}


UserMapper.xml

<mapper namespace="cn.itcast.mybatis.mapper.UserMapper">
<select id="findUserById" parameterType="int" resultType="cn.itcast.mybatis.po.User">
SELECT * FROM USER WHERE id= #{id}
</select>

<select id="findUserByName" parameterType="java.lang.String" resultType="cn.itcast.mybatis.po.User">
select * from user where username like '%${value}%'
</select>

<insert id="insertUser" parameterType="cn.itcast.mybatis.po.User">
<selectKey keyProperty="id" order="AFTER" resultType="int">
select LAST_INSERT_ID()
</selectKey>

INSERT INTO USER(username,birthday,sex,address) VALUES(#{username},#{birthday},#{sex},#{address})
</insert>

<delete id="deleteUser" parameterType="int">
delete from user where id=#{id}
</delete>

<update id="updateUser" parameterType="cn.itcast.mybatis.po.User">
update user set username=#{username},birthday=#{birthday},sex=#{sex},address=#{address} where id=#{id}
</update>
</mapper>


测试类:

public class UserMapperTest {
private SqlSessionFactory sqlSessionFactory;

@Before
public void init() throws IOException {
String resource = "SqlMapConfig.xml";

InputStream inputStream = Resources.getResourceAsStream(resource);

sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);

}

@Test
public void testFindUserById() throws Exception {
SqlSession sqlSession = sqlSessionFactory.openSession();

// 创建代理对象
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);

User user = userMapper.findUserById(1);

System.out.println(user);
}

@Test
public void testFindUserByUsername() throws Exception {
SqlSession sqlSession = sqlSessionFactory.openSession();
// 创建代理对象
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);

List<User> list = userMapper.findUserByName("小明");

System.out.println(list);
}

@Test
public void testInsertUser() throws Exception {
SqlSession sqlSession = sqlSessionFactory.openSession();
// 创建代理对象
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);

User user = new User();
user.setUsername("李奎");
userMapper.insertUser(user);

sqlSession.commit();
sqlSession.close();
}
}


补充SqlMapConfig中几个配置

typeAliases

单个别名定义:

alias:别名,type:别名映射的类型

<typeAliases>
<typeAlias type="cn.itcast.mybatis.po.User" alias="user"/>
</typeAliases>


批量别名定义

指定包路径,自动扫描包下边的pojo,定义别名,别名默认为类名(首字母小写或大写)

<typeAliases>
<package name="cn.itcast.mybatis.po"/>
</typeAliases>


mappers配置

resource引用

<mappers>
<mapper resource="sqlmap/User.xml" />
</mappers>


class引用mapper接口

class:配置mapper接口全限定名

要求:需要mapper.xml和mapper.java同名并且在一个目录中

<mappers>
<mapper class="cn.itcast.mybatis.mapper.UserMapper"/>
</mappers>


批量mapper配置

通过package进行自动扫描包下边的mapper接口,

要求:需要mapper.xml和mapper.java同名并且在一个目录 中

<mappers>
<package name="cn.itcast.mybatis.mapper"/>
</mappers>


输入输出映射

parameterType

parameterType传递POJO包装对象,可以定义POJO包装类型扩展mapper接口输入参数的内容。

(使用场景:自定义查询等)

resultType

指定输出结果的类型(简单类型、POJO、HashMap…),将SQL查询结果映射为Java对象 。

**注意:**SQL查询的列名要和resultType指定POJO的属性名相同,指定相同属性方可映射成功,如果SQL查询的列名和resultType指定POJO的属性名全部不相同,list中无法创建POJO对象的。

resultMap

将SQL查询结果映射为java对象。

如果SQL查询列名和最终要映射的POJO的属性名不一致,使用resultMap将列名和POJO的属性名做一个对应关系 (列名和属性名映射配置)

定义resultMap

id:mapper.xml中的唯一标识

type:最终要映射的pojo类型

列名和属性名映射配置

id:要映射结果集的唯 一标识 ,称为主键

result:就是普通列的映射配置

column:结果集的列名

property:type指定的哪个属性中

<resultMap id="userListResultMap" type="user" >
<id column="id_" property="id"/>
<result column="username_" property="username"/>
<result column="birthday_" property="birthday"/>
</resultMap>


动态SQL

SQL片段

通过sql片段可以将通用的sql语句抽取出来,单独定义,在其它的statement中可以引用sql片段。

通用的sql语句,常用:where条件、查询列。

SQL片段定义

<sql id="query_user_where">
</sql>


SQL片段引用

<include refid="query_user_where"></include>


if和where

<sql id="query_user_where">
<if test="userCustom!=null">
<if test="userCustom.username!=null and userCustom.username!=''">
and username like '%${userCustom.username}%'
</if>
<if test="userCustom.sex!=null and userCustom.sex!=''">
and sex = #{userCustom.sex}
</if>
</if>
</sql>


foreach

在statement通过foreach遍历parameterType中的集合类型。

collection:集合的属性

open:开始循环拼接的串

close:结束循环拼接的串

item:每次循环取到的对象

separator:每两次循环中间拼接的串

<sql id="query_user_where">
<if test="userCustom!=null">
<foreach collection="ids" open=" AND id IN ( " close=")" item="id" separator=",">
#{id}
</foreach>
</if>
</sql>


完整代码

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: