一、了解myBatis的作用域和生命周期
[错误的使用会导致非常严重的并发问题]
(1)SqlSessionFactoryBuilder
[ 作用:仅仅是用来创建SqlSessionFactory,作用域:方法作用域(局部变量) ]
(2)SqlSessionFactory(类似连接池)
[ 生命周期:一旦被创建就应该在应用的运行期间一直存在,作用域:应用作用域变量(使 用单例
模式/静态单例模式) ]
(3)SqlSession(类似连接对象)
[ 特点:非线程安全,不能共享,作用域:请求或方法作用域(局部变量) ]
二、抽取MyBatis工具类[用来创建Sqlsession]
✿ 在理解myBatis的作用域和生命周期基础上,抽取MyBatis工具类:
public class MyBatisUtil { //创建一个sqlSessionFactory对象【应用对象(静态单例模式)】 private static SqlSessionFactory factory = null; static { try { InputStream in = Resources.getResourceAsStream("mybatis-config.xml"); factory = new SqlSessionFactoryBuilder().build(in); } catch (IOException e) { e.printStackTrace(); } } //返回sqlSession对象 public static SqlSession getSession() { return factory.openSession(); } }
- 通过factory.openSession() 默认是不提交事务的方式,当修改了对象的属性之后,发现数据库的表的记录的列值没有改变----因为默认是不提交事务,需要
手动提交事务
:
//手动提交事务 session.commit();
三、mybatis执行增删改查操作:
1、mybatis的映射文件[UserMapper.xml] 编写增删改查sql
【 把sql存放到insert|update|delete|select 元素中去】
<mapper namespace="com.shan.hello.UserMapper"> <!-- 保存操作 --> <insert id="insert"> insert into t_user (name, salary) values (#{name}, #{salary}); </insert> <!-- 保存操作,并设置返回自动生成的主键【useGeneratedKeys、keyProperty】 useGeneratedKeys:是否需要返回自动生成的主键 keyProperty:把自动生成的主键设置到对象的哪个属性(OID) --> <insert id="keyInsert" useGeneratedKeys="true" keyProperty="id"> insert into t_user (name, salary) values (#{name}, #{salary}); </insert> <!-- 删除操作 --> <delete id="delete"> delete from t_user where id = #{id}; </delete> <!-- 更改操作 --> <update id="update"> update t_user set name = #{name}, salary = #{salary} where id = #{aid}; </update> <!-- 查询操作 --> <select id="get" parameterType="java.lang.Long" resultType="com.shan.hello.User"> select * from t_user where id = #{id} </select> <select id="getList" parameterType="java.lang.Long" resultType="com.shan.hello.User"> select * from t_user; </select> </mapper>
2、测试mybatis的增删改查:
/* 测试查询 */ @Test public void testGetList3() { //jdk7try-finally结构的另外一种写法,将关闭资源的finally部分内容放大try后边的括号内容 try(SqlSession session = MyBatisUtil.getSession();){ //4、进行数据库操作(CRUD) User user = session.selectOne("com.shan.hello.UserMapper.get", 2L); } } /* 测试更改 */ @Test public void testUpdate() { User user = new User(); user.setId(4L); user.setName("好贱"); user.setSalary(new BigDecimal(100)); //jdk7try-finally结构的另外一种写法,将关闭资源的finally部分内容放大try后边的括号内容 try(SqlSession session = MyBatisUtil.getSession();){ //4、进行数据库操作(CRUD) int rows = session.update("com.shan.hello.UserMapper.update", user); session.commit(); } } /* 测试删除 */ @Test public void testDelete() { //jdk7try-finally结构的另外一种写法,将关闭资源的finally部分内容放大try后边的括号内容 try(SqlSession session = MyBatisUtil.getSession();){ //4、进行数据库操作(CRUD) int rows = session.delete("com.shan.hello.UserMapper.delete", 4L); session.commit(); } } /* 测试保存 */ @Test public void testInsert() { User user = new User(); user.setName("就是贱"); user.setSalary(new BigDecimal(1)); //jdk7try-finally结构的另外一种写法,将关闭资源的finally部分内容放大try后边的括号内容 try(SqlSession session = MyBatisUtil.getSession();){ //4、进行数据库操作(CRUD) int rows = session.insert("com.shan.hello.UserMapper.insert", user); session.commit(); System.out.println(user); } } /* 测试保存(获取自动生成的主键) */ @Test public void testKeyInsert() { User user = new User(); user.setName("贱"); user.setSalary(new BigDecimal(1)); //jdk7try-finally结构的另外一种写法,将关闭资源的finally部分内容放大try后边的括号内容 try(SqlSession session = MyBatisUtil.getSession();){ //4、进行数据库操作(CRUD) int rows = session.insert("com.shan.hello.UserMapper.keyInsert", user); session.commit(); System.out.println(user); } }
✿ 获取主键的作用
---注册时,一次性填写过多信息,不友好,分成两次填写呗【获取主键,将其传递给第二个填写注册信息界面】