mybatis注解开发

mybatis注解开发

1、概述

​ 上述我们已经学习mybatis的SQL映射文件可以使用xml的方式配置,但是我们发现不同的用户模块接口都对应一个映射文件,并且在映射文件中书写sql语句也比较麻烦。所以Mybatis为用户提供了快速的开发方式,因为有时候大量的XML配置文件的编写时非常繁琐的,因此Mybatis也提供了更加简便的基于注解(Annnotation)的配置方式。

注解配置的方式在很多情况下能够取代mybatis的映射文件,提高开发效率。

2、注解实现CRUD

说明:在演示注解开发之前,为了避免和之前的映射文件混淆,所以可以将之前书写的代码放到一个新的工程中,删除映射文件即可。

2.0、CRUD相关注解

【注解】

@Insert:保存  
         Value:sql语句(和xml的配置方式一模一样)
         
@Update:更新 
         Value:sql语句
         
@Delete: 删除
         Value:sql语句
         
@Select: 查询
         Value:sql语句
         
@Options:可选配置(获取主键)
         userGeneratedKeys:开关,值为true表示可以获取主键  相当于select last_insert_id()
         keyProperty     :对象属性
         keyColumn       : 列名

【使用方式】

【第一步】将mybatis全局配置文件mybatis-config.xml中的mapper路径改为包扫描或者class路径;

说明:因为没有了映射文件,所以我们这里采用加载接口方式,需要告知mybatis哪个接口的方法上的注解需要被执行。

在这里插入图片描述

【第二步】编写接口和注解;

【第三步】测试

2.1、新增

目标:使用注解@Insert的方式新增数据

步骤:

第一步:UserMapper接口中新增用户方法上面编写注解;
第二步:测试

实现:

第一步:在UserMapper接口中的saveUser()方法上面添加@Insert注解,并设置该注解的value属性值为具体的SQL语句;

public interface UserMapper {
    //1、新增数据  #{userName} 这里的userName是方法saveUser(User user)参数User类的成员变量
    @Insert("INSERT INTO tb_user VALUES(NULL,#{userName},#{password},#{name},#{age},#{sex})")
    void saveUser(User user);
}

第二步:测试

在UserMapperTest类下面对save方法进行测试:

public class MybatisTest01 {
    private static UserMapper userMapper;
    @BeforeClass
    public static void berofeClass() throws Exception {
        //1、从xml中构建SqlSessionFactory
        String resource = "mybatis-config.xml";
        InputStream inputStream = Resources.getResourceAsStream(resource);
        //这里指定了环境为test
//        SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream,"test");
        //build不方法不指定环境就使用默认的 <environments default="development">
        SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);

        //2、获取SqlSession
        SqlSession sqlSession = sqlSessionFactory.openSession(true);

        //3、获取UserMapper接口的动态代理对象
        userMapper = sqlSession.getMapper(UserMapper.class);
    }

    @Test
    public void saveUser(){
        User user = new User();
        user.setUserName("锁哥");
        user.setAge(18);
        user.setName("黑旋风");
        user.setPassword("1234");
        user.setSex(1);
        userMapper.saveUser(user);
    }
}

小结:

新增数据的注解为:@Insert ,作用等同于映射文件中的<insert>具体使用时,需要给其value属性设置具体的SQL。

2.2、删除

目标:使用注解@Delete删除id值为1的数据

步骤:

第一步:在根据id删除数据的方法上面编写注解@Delete;
第二步:测试

实现:

第一步:在UserMapper接口中的deleteUserById方法上编写@Delete,并设置其value属性值为具体的删除SQL;

    /*
        2.根据id删除用户
     */
    @Delete("delete from user where id=#{id}")
    void deleteUserById(Long id);

第二步:测试

    @Test
    public void deleteUserById(){
        userMapper.deleteUserById(1L);
    }

小结:

删除数据的注解:@Delete,作用等同于映射文件中的<delete>,具体使用时,需要设置其value属性值为具体的删除SQL;

2.3、修改

目标:修改id为1的用户的数据

步骤:

第一步:在根据id修改用户数据方法上面添加注解@Update,然后在其value属性值中编写具体的SQL;
第二步:测试

实现:

第一步:在UserMapper接口的updateUser方法上添加注解:@Update,然后将其value属性值设置成update的SQL;

  /**
     * 3.修改用户数据
     * @param user
     */
    @Update("UPDATE tb_user SET user_name=#{userName}, password=#{password} ,name=#{name} ,age=#{age},sex=#{sex} where id=#{id}")
    void updateUser(User user);

第二步:测试

    @Test
    public void updateUser(){
        User user = new User();
        user.setId(1L);
        user.setUserName("柳岩");
        user.setSex(0);
        user.setPassword("3456");
        user.setName("岩岩");
        user.setAge(20);
        userMapper.updateUser(user);
    }

小结:修改数据的注解:@Update,作用等同于映射文件中的<update>

2.4、查询

目标:使用注解查询所有的用户数据

步骤:

第一步:在接口中查询所有的用户数据的方法上面添加注解:@Select,然后设置其value属性值为具体的SQL查询语句;
第二步:测试

实现:

第一步:在UserMapper接口的queryAllUsers方法上添加注解:@Select,然后设置其value属性值为具体的查询SQL;

  /*
     * 4.查询所有用户数据
     */
    @Select("SELECT * FROM tb_user")
    List<User> queryAllUsers();

第二步:测试

    @Test
    public void queryAllUsers(){
        List<User> list = userMapper.queryAllUsers();
        System.out.println("list = " + list);
    }

小结:

查询数据注解:@Select ,作用等同于映射文件中的<select>标签。

3、返回新增数据的id(自增主键回填)了解

问题:上面注解实现CRUD的测试中,数据新增成功,但是id值没有正常返回.

在这里插入图片描述

目标:使用注解完成数据新增,新增成功后返回数据的主键id值

步骤:

1、在新增数据注解 @Insert下面,添加@Options;
2、在Options注解中,设置useGeneratedKeys值为true,keyProperty为id,keyColumn id;

实现:

第一步:在新增数据注解 @Insert下面,添加@Options,设置useGeneratedKeys值为true,keyProperty为id,keyColumn 为id;

    //1、新增数据  #{userName} 这里的userName是方法saveUser(User user)参数User类的成员变量
    @Insert("INSERT INTO tb_user VALUES(NULL,#{userName},#{password},#{name},#{age},#{sex})")
    @Options(useGeneratedKeys = true,keyColumn = "id",keyProperty = "id")
    void saveUser(User user);

第二步:测试:

在这里插入图片描述

小结:注解@Options

在这里插入图片描述

4、注解实现别名映射

根据之前的学习,如果数据表的列名和pojo实体类的属性名不一致,会导致数据表的数据无法封装到实体类属性值中,对此我们又如下解决方案:

【1】查询的时候给列起别名,别名和实体类的属性名一致

select user_name as userName from tb_user where id =1;

【2】在mybatis的核心配置文件中按照如下配置:

<settings>
    <!--开启驼峰自动映射-->
    <setting name="mapUnderscoreToCamelCase" value="true"/>
</settings>

【3】在映射文件中,我们可以通过在ResultMap中,通过result标签中,给指定的column映射到实体类中指定的属性上。

 <resultMap id="orderAndUserResultRelative" type="Order">
     <result column="user_name" property="userName"/>
 </resultMap>

而在注解中也有相应的解决方案:这里就必须使用注解:@Results

@Results注解相当于之前映射文件中的ResultMap,该注解如下:

public @interface Results {
    Result[] value() default {};
}

我们发现value属于Result数组类型,而Result属于一个注解,注解的属性如下:

public @interface Result {
    //对应数据表的列
    String column() default "";
	//对应pojo类的属性
    String property() default "";
	//javaType:返回的对象类型
    Class<?> javaType() default void.class;
	//one: 一对一配置
    One one() default @One;
	//many: 一对多配置
    Many many() default @Many;
}

目标:使用注解的方式给取别名后的字段,映射到实体类中

步骤:

第一步:将之前核心配置文件中的开启驼峰自动映射设置为false
 <settings>
        <!--开启驼峰自动映射-->
        <setting name="mapUnderscoreToCamelCase" value="false"/>
 </settings>
第二步:在接口中查询的方法上面添加注解@Results;
第三步:测试;

实现:

第一步:将之前核心配置文件中的开启驼峰自动映射设置为false。这样才可以演示出@Results的效果。

 <settings>
        <!--开启驼峰自动映射-->
        <setting name="mapUnderscoreToCamelCase" value="false"/>
 </settings>

第二步:在接口中查询方法上面添加注解:@Results ,然后通过@Result完成字段的别名和实体类的属性名之间的映射配置;

说明:这里我们使用之前的查询所用用户方法即可,也可以在接口中在定义一个根据id查询用户的方法。

	/*
        根据id查询用户
     */
    @Select("SELECT * FROM tb_user WHERE id = #{id}")
    @Results(value={
            @Result(column = "user_name",property = "userName")
    })
    User selectById(@Param("id") Long id);

第三步:测试

   @Test
    public void selectById(){
        User user = userMapper.selectById(1L);
        System.out.println("user = " + user);
    }

【结果】

在这里插入图片描述

小结:给别名映射到实体类中可以通过添加注解:@Results 中的 @Result实现;

总结

一、全局配置:能够影响mybatis的运行
	【1】能够配置的参数:
			properties:
			settings:
			typeAliases:
			mappers:
	【2】properties:属性
		作用:设置参数 ,加载外部的资源文件中的参数
		用法:
			1、设置参数:
				<properties>
					<property name="driver" value="com.mysql.jdbc.Driver"></property>
				</properties>
			   取参数: ${driver}
			2、加载外部的资源文件:从src路径下加载
				<properties resource="jdbc.properties"></properties>
				获取资源文件中的参数: ${key}

	【3】settings设置:
			开启驼峰自动映射:
				<settings>
                  		<setting name="mapUnderscoreToCamelCase" value="true"/>
				</settings>
			作用: 数据库下划线命名: user_name    驼峰命名:userName
	【4】typeAliases:类型别名 
			作用:给全限定类名 取一个 短名称  com.heima.mybatis.pojo.User ==> User
			用法:
				1、单独设置:
					<typeAliases>
                      	<typeAliase type="com.heima.mybatis.pojo.User" alias="User"></typeAliase>
					</typeAliases>

				2、批量设置:包扫描
					<typeAliases>
                      	<package name="com.heima.mybatis.pojo"></package>
          			</typeAliases>
	【5】mappers 映射器:
		【作用】管理映射文件 和  接口
		【配置】
			1、加载xml文件
				 从src下加载:resource="UserMapper.xml"
				 从本地磁盘: url="file:///E://aaa.xml"

			2、加载接口: 接口和映射文件同名,在相同的包下面
				 单独加载: class="com.heima.mybatis.dao.UserMapper"
				 批量加载: package="com.heima.mybatis.dao"


二、映射文件配置
	【1】作用:配置sql相关信息 
			 1、CRUD四类标签:
			 2、sql标签:sql片段
			 3、resultMap:
	【2】CRUD四类标签:
			增: <insert></insert>
			删: <delete></delete>
			改:<update></update>
			查:<select></select>

	【3】入参相关:<select resultType="User" paramType="int">
      				SELECT * FROM user WHERE id = #{id}
				</select>
			
		paramType:设置传入的参数的类型,可以省略
		insert语句相关:自增主键回填--数据插入到数据库之后,返回这条数据在数据库中的主键值
			【1】子标签:<selectKey></selectKey>
		<selectKey keyColumn="id" keyProperty="id" resultType="int" order="AFTER">
            SELECT LAST_INSERT_ID() ;
        </selectKey>
			【2】属性:
				useGeneratedKeys="true" keyColumn="id" keyProperty="id" 


	【4】sql参数传入:
			能够接收的参数类型: 基本类型数据,pojo,map

	【5】传入基本类型数据:string,int
		 单个数据传入: queryById(Integer id)        WHERE id = #{id}
		多个数据传入:queryByNameAndSex(String name,String sex):  
						WHERE username=#{} and sex= #{}
		最佳实践:命名参数取值  
				queryByNameAndSex(@Param("name")String name,@Param("sex")String sex):  
				WHERE username=#{name} and sex= #{sex}

	【6】传入pojo和map数据:
			pojo: User{id,username}   #{username}
			map:  Map<Key,Value>      #{key}
	
     【7】映射文件中sql语句取值: #{}  ${}
              相同点:都能够获取命名参数值
              不同点:
              		#{} 取值使用预编译方式设置参数
              		${} 直接标签获取的参数拼接到sql语句中
           最佳实践: 获取查询参数,防止SQL注入 使用  #{}取值
              
      【8】${}应用场景: 拼接SQL语句
       
       
       【9】sql返回值处理:
              resultType:基本类型数据,pojo,map
              	基本类型数据: resultType="int"
              	pojo类型:
              		单个pojo,多个pojo:   resultType="pojo"
              	map:
              		单条数据:map  默认    resulteType="map"
              		多条数据:map    @MapKey("id")
             
              resultMap:
				【1】设置数据库的列名  和  实体类的属性名之间  映射关系
              	 【2】多表关联配置:
              
        【10】SQL片段: <sql>id,username</sql>
         【11】动态sql:
              	判断: if,分支
              	trim: where,set
              	foreach:遍历

  • 24
    点赞
  • 30
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

攒了一袋星辰

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值