zoukankan      html  css  js  c++  java
  • MyBatis-全局配置文件

    MyBatis 的配置文件包含了影响 MyBatis 行为甚深的 设置(settings)和属性(properties)信息。文档的 顶层结构如下:

    configuration 配置
    properties 属性:可以加载properties配置文件的信息
    settings 设置:可以设置mybatis的全局属性
    typeAliases 类型命名
    typeHandlers 类型处理器
    objectFactory 对象工厂
    plugins 插件
    environments 环境
    environment 环境变量
    transactionManager 事务管理器
    dataSource 数据源
    databaseIdProvider 数据库厂商标识
    mappers 映射器

     1.为全局配置文件绑定dtd约束:

    1)联网会自动绑定
    2)没网的时候【/org/apache/ibatis/builder/xml/mybatis-3-config.dtd】:解压mybatis 的jar包然后在eclipse中绑定

     2. properties属性

    <configuration>
    		<!-- 
    			1.mybatis可以使用properties来引入外部properties配置文件的内容
    			  resource:引入类路径下的资源
    			  url:引入网络路径或者磁盘路径下的资源
    		 -->
    		   <properties resource="jdbc.properties"></properties>
    			<environments default="development">
    				<environment id="development">
    					<transactionManager type="JDBC"/>
    					<dataSource type="POOLED">
    						<property name="driver" value="${jdbc.driver}"/>
    						<property name="url" value="${jdbc.url}"/>
    						<property name="username" value="${jdbc.user}"/>
    						<property name="password" value="${jdbc.passowrd}"/>
    					</dataSource>
    				</environment>
    			</environments>
    			<!-- 将我们写好的sql映射文件一定要注册到全局配置文件中 -->
    			<mappers>
    				<mapper resource="EmployeeMapper.xml"/>
    			</mappers>
    		</configuration>
    

     3.settings包含很多重要的设置项

          setting:用来设置每一个设置
          name:设置项名
          value:设置项取值

       举例:驼峰式命名

     <settings>
    	<setting name="mapUnderscoreToCamelCase" value="true"/>
    </settings> 

    1).mapUnderscoreToCamelCase:自动完成数据表标准列名和持久化类标准属性名之间的映射。
    例如:last_name和lastName

    4.typeAliases:【不建议大家使用别名】

    作用:A type alias is simply a shorter name for a Java type
    		
    		   <!-- typeAliases:别名处理器,可以为我们的java类型起别名,别名不区分大小写 -->
    		   <typeAliases>
    		   <!-- typeAlias:为某个java类型起别名
    				type:指定要起别名的类型全类名;默认别名就是类名小写;
    				alias:执行新的别名
    			-->
    				<typeAlias type="com.neuedu.mybatis.bean.Employee"/>
    				<!-- 
    					package:为某个包下的所有类批量起别名
    					   name:指定包名(为当前包以及下面所有的后代包的每一个类都起一个默认别名【类名小写】)
    				 -->
    				<package name="com.neuedu.mybatis.bean"/>
    				<!-- 批量起别名的情况下,使用@Alias注解为某个类型指定新的别名 -->
    		   </typeAliases>
    	 
    
    	   虽然有这么多的别名可以使用:但是建议大家还是使用全类名,看SQL语句是怎么被封装为JAVA 对象的时候简单!
    

     5.typeHandlers:类型处理器

    类型处理器:负责如何将数据库的类型和java对象类型之间转换的工具类

    6.environments【用于配置MyBatis的开发环境】

    <!--
         environments:环境们,mybatis可以配置多种环境,default指定使用某种环境。可以达到快速切换环境。
        environment:配置一个具体的环境信息;必须有两个标签;id代表当前环境的唯一标识
        transactionManager:事务管理器
       type:事务管理器的类型;type="[JDBC|MANAGED]"),这两个都是别名,在Configuration类中可以查看具体类!但是Spring对事务的控   制才是最终的管理方案!
       JDBC:这个配置就是直接使用了JDBC的提交和回滚设置,它依赖于从数据源得到的连接来管理事务。
       MANAGED:这个配置几乎没做什么,它从来不提交和回滚一个连接。而是让容器来管理事务的整个生命周期。

      所以综上:这里如果要配置事务处理器,就配置为JDBC。表示使用本地的JDBC事务。

        当然也可以自定义事务管理器:只需要和人家一样实现TransactionFactory接口,type指定为全类名。
       dataSource:数据源
       type:type="[UNPOOLED|POOLED|JNDI]"
       unpooled:无数据库连接池
        pooled:有数据库连接池
      JNDI:
       自定义数据源:实现DataSourceFactory接口,type也是全类名

       但是我们也说了,无论是事务管理器的配置还是数据源的配置我们都会使
        用spring来做,这里只需要了解一下即可!
    -->

    	<environments default="development">
    		<environment id="test">
    			<transactionManager type="JDBC"/>
    			<dataSource type="POOLED">
    				<property name="driver" value="${jdbc.driver}"/>
    				<property name="url" value="${jdbc.url}"/>
    				<property name="username" value="${jdbc.user}"/>
    				<property name="password" value="${jdbc.passowrd}"/>
    			</dataSource>
    		</environment>
    		<environment id="development">
    			<transactionManager type="JDBC"/>
    			<dataSource type="POOLED">
    				<property name="driver" value="${jdbc.driver}"/>
    				<property name="url" value="${jdbc.url}"/>
    				<property name="username" value="${jdbc.user}"/>
    				<property name="password" value="${jdbc.passowrd}"/>
    			</dataSource>
    		</environment>
    	</environments>
    

      

    补充:这里可以了解一下如何配置第三方数据源:
    定制自己的第三方数据源,如下所示:
    要求:需要自定义一个类继承UnpooledDataSourceFactory类,然后在构造器中初始化该对应的dataSource属性,如下所示:

    自定义类为:
    			public class C3P0DataSource  extends UnpooledDataSourceFactory{
    				public C3P0DataSource() {
    					this.dataSource = new ComboPooledDataSource(); 
    				}
    			}
    			
    		MyBatis的全局配置文件为:
    						<environments default="development">
    						<environment id="development">
    							<transactionManager type="JDBC"/>
    				<!-- 			<dataSource type="POOLED">
    								<property name="driver" value="${jdbc.driver}"/>
    								<property name="url" value="${jdbc.url}"/>
    								<property name="username" value="${jdbc.username}"/>
    								<property name="password" value="${jdbc.password}"/>
    							</dataSource> -->
    							<!-- 配置使用第三方的数据源。属性需要配置为第三方数据源的属性 -->
    							<dataSource type="com.neuedu.mapper.C3P0DataSource">
    								<property name="driverClass" value="${jdbc.driver}"/>
    								<property name="jdbcUrl" value="${jdbc.url}"/>
    								<property name="user" value="${jdbc.username}"/>
    								<property name="password" value="${jdbc.password}"/>
    							</dataSource>
    						</environment>
    		测试类:
    			@Test
    			public void test02(){
    				//1.获取sqlSessionFactory对象
    				SqlSessionFactory sqlSessionFactory = getSqlSessionFactory();
    				//2.利用sqlSessionFactory对象创建一个SqlSession对象
    				SqlSession session = sqlSessionFactory.openSession();
    				System.out.println(session.getConnection());
    				//提交事务
    				session.commit();
    			}
    	  当然这里需要加入c3p0的jar包;
    		c3p0-0.9.2.1.jar
    		mchange-commons-java-0.2.3.4.jar
    

      7.MyBatis的增删改查标签:

    <select></select>
    <insert></insert>
    <update></update>
    <delete></delete>
    例如:
    <insert id="saveEmployee">
    INSERT INTO tbl_employee(user_name,email,gender) VALUES(#{userName},#{email},#{gender})
    </insert>

    databaseIdProvider环境

    MyBatis is able to execute different statements depending on your database vendor. The
    ? MyBatis 可以根据不同的数据库厂商执行不同的语句

    <databaseIdProvider type="DB_VENDOR">
    <property name="SQL Server" value="sqlserver"/>
    <property name="DB2" value="db2"/>
    <property name="Oracle" value="" />
    <property name="MySQL" value="" />
    </databaseIdProvider>

    Type: DB_VENDOR
    –使用MyBatis提供的VendorDatabaseIdProvider解析数据库 厂商标识。也可以实现DatabaseIdProvider接口来自定义。
    Property-name:数据库厂商标识
    Property-value:为标识起一个别名,方便SQL语句使用

    这样在执行不同数据库的时候,就会执行不同数据库的语句了!当然如上所示:当有指定
    了databaseId属性的和没有指定databaseId属性的,都有的情况下那就按着有指定databaseId属性的sql语句执行!
    所以:databaseId属性:
    1).对于不同的数据库,做不同的SQL操作时,SQL语句会有不同。例如:
    MySQL和Oracle的分页[mysql分页为limit,而ORACLE分页我们使用rownumber]、插入主键的方式。
    MySQL:INSERT INTO tbl_employee(user_name,email,gender) VALUES(#{userName},#{email},#{gender})
    ORACLE:INSERT INTO employee(id,user_name,email) VALUES(test.seq.nextval,#{userName},#{email})
    所以要想使用ORACLE的自增序列还需要创建一个序列:
    如下所示:
    create sequence test_seq start with 1;

    这样做的好处:在service层只需要调用一个mybatis的方法,而不需要关注底层选择使用的数据库。
    employeeDao.insert(employee);

    那么:mybatis如何区分使用的是哪个数据库呢?使用databaseId属性

    ①.在mybatis-config.xml文件中进行配置
    		  		<databaseIdProvider type="DB_VENDOR">
    					<property name="ORACLE" value="oracle"/>
    					<property name="MySQL" value="mysql"/>
    				</databaseIdProvider>
    		    
    		  ②.在mybatis的映射文件中使用databaseId来区分使用的是哪一个数据库
    		  	  在mybatis的全局配置文件配置了这个之后,我们只需要在sql映射文件中通过在执行语句的标签上加一个属性databaseId即可!
    				<select id="getEmployeeById" resultType="emp">
    					select * from tbl_employee where id = #{id}
    				</select>
    				<select id="getEmployeeById" resultType="emp" databaseId="mysql">
    					select * from tbl_employee where id = #{id}
    				</select>
    				<select id="getEmployeeById" resultType="emp" databaseId="oracle">
    					select * from tbl_employee where id = #{id}
    				</select>
    
    		  
    		 
    	   
    			<environments default="dev_mysql">
    				<environment id="dev_oracle">
    					<transactionManager type="JDBC"/>
    					<dataSource type="POOLED">
    						<property name="driver" value="${jdbc.oracle.driver}"/>
    						<property name="url" value="${jdbc.oracle.url}"/>
    						<property name="username" value="${jdbc.oracle.user}"/>
    						<property name="password" value="${jdbc.oracle.passowrd}"/>
    					</dataSource>
    				</environment>
    				<environment id="dev_mysql">
    					<transactionManager type="JDBC"/>
    					<dataSource type="POOLED">
    						<property name="driver" value="${jdbc.driver}"/>
    						<property name="url" value="${jdbc.url}"/>
    						<property name="username" value="${jdbc.user}"/>
    						<property name="password" value="${jdbc.passowrd}"/>
    					</dataSource>
    				</environment>
    			</environments>
    

       8.mapper映射

      

    <!-- mappers:将sql映射注册到全局配置中 -->
    <mappers>
    <!-- mapper:注册一个sql映射
    注册配置文件:
    resource:引用类路径下的sql映射文件
    mybatis/mapper/EmployeeMapper.xml
    url:引用网络路径下或者磁盘路径下的sql映射文件
    url="file:///var/mappers/AuthorMapper.xml"

    注册接口
    class:引用(注册)接口
    1.有sql映射文件,映射文件名必须和接口同名,并且放在与接口同一个目录下;
    2.没有sql映射文件,所有的sql都是利用注解写在接口上;
    推荐:
    比较重要的,复杂的Dao接口我们来写sql映射文件
    不重要,见到的Dao接口为了开发快速可以使用注解


    -->
    <mapper resource="mybatis/mapper/EmployeeMapper.xml"/>
    <mapper class="com.neuedu.mybatis.mapper.EmployeeMapperAnnotation"/>
    <!-- 批量注册:
    1.注解版肯定是没问题的
    2.但是对于Mapper.xml映射文件和接口分开的,就需要保证在同一个包下了,否则找不到 -->
    <package name="com.neuedu.mybatis.mapper"/>
    </mappers>

    补充:MyBatis有基于XML文件的方式也有基于注解的方式,如下所示:
    1.使用基于注解的MyBatis映射
    1).新建一个XxxMapper接口。通常情况下,Mapper接口和Mapper.xml文件同名,且在同一个包下;
    MyBatis在加载Mapper接口的时候也会自动的加载Mapper.xml文件。

    2).在该接口中新建方法.
    若该方法上没有注解,则mybatis会去对应的Mapper.xml文件中查找和方法名匹配的id的节点进
    而执行该节点对应的SQL语句。
    3).在方法上使用MyBatis的注解

    如下所示:代码和配置如下所示:
    Mapper接口为:
    public interface EmployeeMapper {

    public Employee getEmployeeById(Integer id);
    //讲到此处了!此处以下没讲
    @Update("update tbl_employee set user_name = #{userName} where id = #{id}")
    public void updateEmployee(Employee employee);
    }
    MyBatis的sql映射文件可以没有,MyBatis的全局映射文件可以只用mapper标签加载Mapper接口

    <mappers>
    				<!-- resource="com/neuedu/mapper/EmployeeMapper.xml" -->
    				<mapper class="com.neuedu.mapper.EmployeeMapper"/>
    			</mappers>
    

      

    增删改操作需要提交事务:
    	  	@Test
    		public void test02(){
    			//1.获取sqlSessionFactory对象
    			SqlSessionFactory sqlSessionFactory = getSqlSessionFactory();
    			//2.利用sqlSessionFactory对象创建一个SqlSession对象
    			SqlSession session = sqlSessionFactory.openSession();
    			EmployeeMapper mapper = session.getMapper(EmployeeMapper.class);
    			Employee employee = new Employee(1, 1,"张三丰","tangseng@163.com");
    			
    			mapper.updateEmployee(employee);
    			//提交事务
    			session.commit();
    		}
    

      2.获取自增主键值【当向数据库中插入一条数据的时候,默认是拿不到主键的值的, 需要设置如下两个属性才可以拿到主键值!】

      

    对于mysql:
    			<!--设置userGeneratedKeys属性值为true:使用自动增长的主键。使用keyProperty设置把主键值设置给哪一个属性-->
    			<insert id="addEmp" parameterType="com.neuedu.mybatis.bean.Employee" 
    			  useGeneratedKeys="true" keyProperty="id" databaseId="mysql">
    				insert into tbl_employee(last_name,email,gender) 
    				values(#{lastName},#{gender},#{email})
    			</insert>	
    			
    对于ORACLE:
    					<insert id="addEmp" databaseId="oracle">
    			     <!-- order="BEFORE" 设置selectKey中包含的语句先执行。且返回的类型为resultType指定的类型。
    			          再把该值付给keyProperty指定的列 -->
    						<selectKey keyProperty="" resultType="int" order="BEFORE"></selectKey>
    						insert into tbl_employee(id,last_name,email,gender) 
    						values(#{id},#{lastName},#{gender},#{email})
    					</insert>
    		
    

      3.SQL节点:

      

    1).可以用于存储被重用的SQL片段
    2).在sql映射文件中,具体使用方式如下:

    <insert id="addEmp">
    			insert into tbl_employee(id,
    			<include refid="employeeColumns"></include>) 
    			values(#{id},#{lastName},#{gender},#{email})
    		</insert>	
    	
    	  <sql id="employeeColumns">
    	  	last_name,email,gender
    	  </sql>  
    

      

    五:参数处理
    单个参数:mybatis不会做特殊处理
    #{参数名}: 取出参数值

    多个参数:mybatis会做特殊处理
    多个参数会被封装成一个map,
    key:param1...paramN,或者参数的索引也可以
    value:传入的参数值

    #{}就是从map中获取指定的key的值

    异常:
    org.apache.ibatis.binding.BingdingException:
    Parameter 'id' not found.
    Available parameters are [1,0,param1,param2]
    操作:
    方法:public Employee getEmployeeAndLastName(Integer id,String lastName);
    取值:#{id},#{lastName}

    命名参数:明确指定封装参数时map的key:@param("id")
    多个参数会被封装成一个map,
    key:使用@Param注解指定的值
    value:参数值
    #{指定的key}取出对应的参数值


    POJO:
    如果多个参数正好是我们业务逻辑的数据模型,我们就可以直接传入pojo;
    #{属性名}:取出传入的pojo的属性值

    Map:
    如果多个参数不是业务模型中的数据,没有对应的pojo,不经常使用,为了方便,我们也可以传入map
    #{key}:取出map中对应的值

    List、Set
    #这里面的值也会被封装到map集合中:
    key:collection
    值:对应的参数值

    #{collection[0]}或#{list[0]}

    #关于参数的问题:
    ①.使用#{}来传递参数
    ②.若目标方法的参数类型为对象类型,则调用其对应的getter方法,如getEmail()
    ③.若目标方法的参数类型为Map类型,则调用其get(key)
    ④.若参数是单个的,或者列表,需要使用@param注解来进行标记
    ⑤.注意:若只有一个参数,则可以省略@param注解


    六、参数值的获取
    #{}:可以获取map中的值或者pojo对象属性的值
    ${}: 可以获取map中的值获取pojo对象属性的值

    案例演示:
    select * from tbl_employee where id = ${id} and last_name = #{lastName}
    preparing:select * from tbl_employee where id = 2 and last_name = ?

    区别:
    #{}:是以预编译的形式,将参数设置到sql语句中,PreparedStatement;防止sql注入
    ${}:取出的值直接拼装在sql语句中,会有安全问题;
    大多情况下,我们取参数的值都应该去使用#{};

    原生JDBC不支持占位符的地方我们就可以使用${}进行取值,#{}只是取出参数中的值!

    在某些情况下,比如分表、排序;按照年份分表拆分
    select * from ${year}_salary where xxx;[表名不支持预编译]
    select * from tbl_employee order by ${f_name} ${order} :排序是不支持预编译的!

    MyBatis-映射文件select元素

    Select元素来定义查询操作。
    Id:唯一标识符。
    – 用来引用这条语句,需要和接口的方法名一致
    parameterType:参数类型。
    –可以不传,MyBatis会根据TypeHandler自动推断
    resultType:返回值类型。
    – 别名或者全类名,如果返回的是集合,定义集合中元素的类型。不能和resultMap同时使用

    1.返回类型为一个List
    eg:public List<Employee> getEmpsByLastNameLike(String lastName);
    <!-- resultType:如果返回的是一个集合,要写集合中元素的类型 -->
    <selecct id="getEmpsByLastNameLike" resultType="com.neuedu.mybatis.bean.Employee">
    select * from tbl_employee where lastName like #{lastName}
    </select>

    2.返回单条记录为一个Map
    <!-- 返回一条记录的map:key就是列名,值就是对应的值 -->
    public Map<String,Object> getEmpByIdReturnMap(Integer id);

    <select id="getEmpByIdReturnMap" resultType="map">
    select * from tbl_employee where id = #{id}
    </select>


    3.返回为一个ResultMap:自定义结果集映射规则
    尤其是当数据表的列名和类的属性名不对应的时候:
    1.起别名
    2.符合下划线转驼峰式命名规范
    3.用这里的resultMap

    <!-- resultMap:自定义结果集映射规则 -->
    public Employee getEmployeById(Integer id);

    <!-- 自定义某个javaBean的封装规则
    type:自定义规则的javabean类型
    id:唯一id方便引用
    -->
    <resultMap type="com.neuedu.mybatis.bean.Employee" id = "myEmp">
    <!--
    指定主键列的封装规则
    id定义主键列会有底层优化
    column:指定是哪一列
    property:指定对应的javaBean属性
    -->
    <id column="id" property = "id">
    <!-- 定义普通列封装规则 -->
    <result column="last_name" property="lastName"/>
    <!--其它不指定的列只要属性名和列名会自动封装,我们只要写resultMap就把全部的映射规则
    都写上,不写是因为列名和属性名是对应的 -->

    </resultMap>

    <!--只需要在映射的地方映射一下就可以了 --》

    <select id="getEmployeById" resultMap="myEmp">
    select * from tbl_employee where id = #{}
    </select>

  • 相关阅读:
    keras 报错 ValueError: Tensor conversion requested dtype int32 for Tensor with dtype float32: 'Tensor("embedding_1/random_uniform:0", shape=(5001, 128), dtype=float32)'
    redis 安装启动及设置密码<windows>
    mysql配置主从数据库
    将已有的项目提交到GitHub
    Top 5 SSH Clients for Windows (Alternatives of PuTTY)
    jQuery 插件写法示例
    Spring 定时操作业务需求
    eclipse 修改js文件无法编译到项目中
    linux 目录结构图解
    MongoDB 概念解析
  • 原文地址:https://www.cnblogs.com/lc-java/p/7488069.html
Copyright © 2011-2022 走看看