mybatis基於傳統dao的開發方式
第一步:開發接口
public interface UserDao {
public User getUserById(int id) throws Exception;
public void insertUser(User user) throws Exception;
}
第二步:設置實現類
public class UserDaoImpl implements UserDao {
private SqlSessionFactory sqlSessionFactory;
public UserDaoImpl(SqlSessionFactory sqlSessionFactory) {
this.sqlSessionFactory = sqlSessionFactory;
}
public UserDaoImpl() {
super();
}
@Override
public User getUserById(int id) throws Exception {
//獲取sqlSession,需要使用sqlSessionFactory
SqlSession session = sqlSessionFactory.openSession();
try {
User user = session.selectOne("selectUserById", id);
return user;
} finally{
session.close();
}
}
@Override
public void insertUser(User user) throws Exception {
//獲取sqlSession,需要使用sqlSessionFactory
SqlSession session = sqlSessionFactory.openSession();
try {
session.insert("insertUser", user);
session.commit();
} finally{
session.close();
}
}
}
第三步:設置對應的mapper文件
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="mybatis.mapper.UserMapper">
<!-- 根據id獲取用戶信息 -->
<select id="selectUserById" parameterType="int" resultType="user">
select * from user where id = #{id}
</select>
<!-- 向數據庫插入一條數據 -->
<insert id="insertUser" parameterType="user">
<selectKey keyProperty="id" resultType="int" order="AFTER">
select last_insert_id();
</selectKey>
insert into user(username,birthday,sex,address)
values(#{username},#{birthday},#{sex},#{address})
</insert>
</mapper>
加載mapper文件
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE configuration
PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
<!-- 加載外部配置文件 -->
<properties resource="db.properties">
</properties>
<!-- 這個environments定義了我們的數據庫的連接操作 -->
<environments default="development">
<environment id="development">
<transactionManager type="JDBC"/>
<dataSource type="POOLED">
<property name="driver" value="${driver}"/>
<property name="url" value="${url}"/>
<property name="username" value="${username}"/>
<property name="password" value="${password}"/>
</dataSource>
</environment>
</environments>
<!-- 通過mappers來指定加載我們對應的mapper文件 -->
<mappers>
<mapper resource="UserMapper.xml"/>
</mappers>
</configuration>
第五步:編寫測試案例
public class UserDaoTest {
private SqlSessionFactory getSqlSessionFactory() throws IOException {
String resource = "mybatis-config.xml";
InputStream inputStream = Resources.getResourceAsStream(resource);
SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
return sqlSessionFactory;
}
@Test
public void testGetUserById() throws Exception {
SqlSessionFactory sqlSessionFactory = getSqlSessionFactory();
UserDao userDao = new UserDaoImpl(sqlSessionFactory);
User user = userDao.getUserById(1);
System.out.println(user);
}
@Test
public void testInsertUser() throws Exception {
SqlSessionFactory sqlSessionFactory = getSqlSessionFactory();
UserDao userDao = new UserDaoImpl(sqlSessionFactory);
User user = new User();
user.setUsername("安茱莉");
user.setSex("0");
user.setAddress("好萊塢38號");
userDao.insertUser(user);
}
}
存在的問題
- Dao方法體存在重複代碼:通過SqlSessionFactory創建SqlSession,調用SqlSession的數據庫操作方法
- 調用sqlSession的數據庫操作方法需要指定statement的id,這裏存在硬編碼,不得於開發維護。
通過接口代理的方式來開發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 {
// 根據id查找用戶
public User findUserById(int id) throws Exception;
// 插入用戶信息
public void insertUser(User user) throws Exception;
}
第二步:定義mapper文件
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="mybatis.mapper.UserMapper">
<!-- 根據id獲取用戶信息 -->
<select id="findUserById" parameterType="int" resultType="user">
select * from user where id = #{id}
</select>
<!-- 向數據庫插入一條數據 -->
<insert id="insertUser" parameterType="user">
insert into user(username,birthday,sex,address)
values(#{username},#{birthday},#{sex},#{address})
</insert>
</mapper>
第三步:加載mapper文件
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE configuration
PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
<!-- 別名的配置 -->
<typeAliases>
<!-- 不區分大小寫的 -->
<!-- <typeAlias type="domain.User" alias="user"/> -->
<!-- 掃描這個包下面的所有類,起別名,也是不區分大小寫的 ,名字是類名不帶包,推薦這種方式-->
<package name="domain"/>
</typeAliases>
<!-- 加載外部配置文件 -->
<properties resource="db.properties">
</properties>
<!-- 這個environments定義了我們的數據庫的連接操作 -->
<environments default="development">
<environment id="development">
<transactionManager type="JDBC"/>
<dataSource type="POOLED">
<property name="driver" value="${driver}"/>
<property name="url" value="${url}"/>
<property name="username" value="${username}"/>
<property name="password" value="${password}"/>
</dataSource>
</environment>
</environments>
<!-- 通過mappers來指定加載我們對應的mapper文件 -->
<!-- 此種方法要求mapper接口名稱和mapper映射文件名稱相同,且放在同一個目錄中。 -->
<mappers>
<mapper resource="mapper.xml"/>
<!-- <mapper class="mybatis.mapper.UserMapper"/> -->
<!-- 加載包下所有mapper接口,要求接口名稱和mapper映射文件名稱相同,且放在同一個目錄中。 -->
<package name="mybatis.mapper"/>
</mappers>
</configuration>
第四步:開發測試代碼
public class UserMapperTest {
/**
* 通過接口代理開發dao層的測試
* 調用getUserById方法,傳遞id參數
* 輸出user對象到控制檯
*/
@Test
public void findUserByIdTest() throws Exception{
SqlSessionFactory sqlSessionFactory = getSqlSessionFactory();
SqlSession sqlSession = sqlSessionFactory.openSession(true);
//mybatis會產生一個代理對象
UserMapper mapper = sqlSession.getMapper(UserMapper.class);
User user = mapper.getUserById(2);
System.out.println(user);
sqlSession.close();
}
...
/**
* 抽取方法,保證項目中SQLSessionFactory的單例
*/
private SqlSessionFactory getSqlSessionFactory() throws IOException {
InputStream inputStream = Resources.getResourceAsStream("sqlMapConfig.xml");
SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
return sqlSessionFactory;
}
}
補充:mybatis默認支持的別名:
別名 | 映射的類型 |
---|---|
_byte | byte |
_long | long |
_short | short |
_int | int |
_integer | int |
_double | double |
_float | float |
_boolean | boolean |
string | String |
byte | Byte |
long | Long |
short | Short |
int | Integer |
integer | Integer |
double | Double |
float | Float |
boolean | Boolean |
date | Date |
decimal | BigDecimal |
bigdecimal | BigDecimal |
map | Map |