Mybatis2-Generator(MBG)-分页查询-存储过程-spring整合

动态SQL内置参数

在这里插入图片描述

       前面的例子中,配置映射关系的xml文件里,所有的参数都是来自接口方法的传值,但是Mybatis内部,其实还有两个很有作用的内置参数的,他们是:
①_databaseId: 在全局变量中配置了多数据库支持的databaseIdProvider属性的前提下,这个内置参数的值就是databaseIdProvider配置的数据库的别名。
②_parameter: 这个内置参数是接口方法传过来的参数的整体的应用,两种情况,一是如果接口方法传来的是单个参数,_parameter就是这个单参数的值,另一种情况是接口方法传来了多个参数的时候会被封装为一个map对象,_parameter就是这个map对象的引用变量。

举例来说明一下
前面的例子中,我们有两种数据库,这里可用_databaseId,来作判断,它的值由系统自动设置,这样我可以不用分开写方法。
在这里插入图片描述
_parameter参数:
在这里插入图片描述
实际上,以前写的就是省略了_parameter。

动态SQL的绑定和公共sql语句片段

前面把Mybatis的大部分动态标签都讲完了,最后还有三个标签,分别是bind,sql和include:

①bind:这个标签作用就是将OGNL标签里的值,进行二次加工,在绑定到另一个变量里,供其他标签使用,举个例子:
在这里插入图片描述
调用getUsers方法的时候,我们可不可以只传入“a”呢,不传%百分号?bind标签就可以帮我们实现:
在这里插入图片描述
bind绑定共享语句。 模糊查询中,不用输入百分了。不建议这样用,因为它不拼接null,会出现空指针异常。

②sql和include:这两个标签是配合一起使用的,作用就是将一些重复的slq片段,像提公因式样,单独抽出来可以重复调用,这个很好用。看例子:
       在查询,插入,修改中,真正项目中不可能用’*'这个通配符,而又当字段多的时候,又很烦锁也容易出错,所以我们可以把这些字段代码,提出来,当作一个变量用。

在这里插入图片描述
1.sql和include配合使用,sql标签里和其他增删改查标签一样支持动态slq标签 2.include标签可以通过property子标签给sql标签里传值,sql标签里用${name}获取

讲到这里,就单纯的Mybatis的基本使用的知识点,基本讲完了,也就是说凭着前面讲过的知识点,你就可以将Mybatis用起来了,但是实际上想要真正在项目开发上用好Mybatis需要的知识点还有很多,比如它的第三方插件通用Mapper,增强工具插件mybatis-plus,分页插件Mybatis_PageHelper,调用存储过程,和spring框架的整合,根据特殊的项目需要编写自己的插件,还有官方提供的自动生成xml和pojo类的Mybatis Generator工具等等,这些知识点,这门Mybatis基础课程会讲一部分,剩下的后面再开专题课程讲!下一次课我们就看看Mybatis Generator工具的使用!

Generator(MBG)

              MyBatis Generator(MBG),这是官方帮我们提供的一个自动生成代码的工具,前面的课程中,我们都是脑袋里想好,pojo有哪些属性,属性的类型是什么,对应的数据表中的字段名字是什么,匹配的类型是什么…然后还要写接口xxxDao,以及它的实现配置文件xxxDao.xml等等都是手动自己操作,以前我们学习Hibernate的时候,感觉方便就是写好pojo启动服务器Hibernate会自动帮助我们生成对应的数据表,MyBatis也有类似的工具,MBG就是官方给我提供的这样的工具,但它和Hibernate有点不一样就是,Hibernate帮我们生成表,MBG帮我们根据表生成接口、pojo类和xml这些文件!方向是反的。

使用MBG

       要使用MBG首先要导jar包和建立一个XML配置文件
导包

<dependency>
	<groupId>org.mybatis.generator</groupId>
	<artifactId>mybatis-generator-core</artifactId>
	<version>1.3.7</version>
</dependency>
以下元素就是MBG的最小配置
<jdbcConnection>  元素指定如何连接数据库
<javaModelGenerator>元素指定生成Model的目标package与目标project
<sqlMapGenerator>元素指定生成Mapping XML文件的目标package与目标project
(Optionally)<javaClientGenerator>元素指定生成Mapper(即DAO)文件的目标package与目标project, 如果不指定这个元素就不会生成Mapper文件
至少一个<table>元素

resources/mbgConfig.xml

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE generatorConfiguration
        PUBLIC "-//mybatis.org//DTD MyBatis Generator Configuration 1.0//EN"
        "http://mybatis.org/dtd/mybatis-generator-config_1_0.dtd">

<generatorConfiguration>

    <!-- 数据库的驱动, JAR/ZIP文件的全路径,maven工程,驱动已经依赖了,没用-->
   <!--  <classPathEntry location="/Program Files/IBM/SQLLIB/java/db2java.zip"/> -->

  
    <context id="DB2Tables" targetRuntime="MyBatis3">

        <commentGenerator>
            <!-- 去除自动生成的注释 -->
            <property name="suppressAllComments" value="true"/>
        </commentGenerator>

        <!--基础的数据库连接-->
        <jdbcConnection driverClass="com.mysql.jdbc.Driver"
                        connectionURL="jdbc:mysql://124.220.60.104:3306/mybatisdemo2?allowMultiQueries=true"
                        userId="root"
                        password="xiong">
        </jdbcConnection>

        <!--Java类型解析器, 目前也就只有forceBigDecimals可以给你玩-->
        <javaTypeResolver>
            <!--当数据类型为DECIMAL或者NUMERIC的时候, 如果是true的话则总是使用java.math.BigDecimal-->
            <!--以下是false, 即默认值的情况-->
            <!--如果有小数或者decimal长度大于18, Java类型为BigDecimal-->
            <!--如果没有小数, 以及decimal长度为10至18, Java类型为Long-->
            <!--如果没有小数, 以及decimal长度为5至9, Java类型为Integer-->
            <!--如果没有小数, 以及decimal长度少于5, Java类型为Short-->
            <property name="forceBigDecimals" value="false"/>
        </javaTypeResolver>

        <!--Domain生成器,生成modle类-->
        <javaModelGenerator targetPackage="cn.ybzy.mybatisdemo.model" targetProject=".\src\main\java">
            <!--据说可以自动添加schema名, 可是我没用到过-->
            <property name="enableSubPackages" value="true"/>

            <!--生成全属性构造器, 没什么用, 如果有指定immutable元素的话这个会被忽略-->
            <property name="constructorBased" value="true"/>

            <!--生成不可变的domain, 这个我也很少用-->
            <property name="immutable" value="true"/>

            <!--每个Domain都继承这个bean-->
            <property name="rootClass" value="com.github.prontera.domain.base.BasicEntity"/>

            <!--当遇到String的时候setter是否会先trim()-->
            <property name="trimStrings" value="true"/>
        </javaModelGenerator>

        <!--Mapping生成器-->
        <sqlMapGenerator targetPackage="cn.ybzy.mybatisdemo.mapper" targetProject=".\src\main\java">
            <property name="enableSubPackages" value="true"/>
        </sqlMapGenerator>

        <!--Mapper生成器, 当type为ANNOTATEDMAPPER时是带有@annotation的Mapper, MIXEDMAPPER是XML文件-->
        <javaClientGenerator type="XMLMAPPER" targetPackage="cn.ybzy.mybatisdemo.mapper" targetProject=".\src\main\java">
            <property name="enableSubPackages" value="true"/>

            <!--每个Mapper所继承的接口-->
            <property name="rootInterface" value="com.github.prontera.Mapper"/>
        </javaClientGenerator>

        <!--字段命名策略过程: <columnRenamingRule> >> property name="useActualColumnNames"-->
        <!--alias属性是个神器, 会为所有SQL都添加, 做关联的时候就非常方便了-->
        <!--至于什么Example, 全关了就是-->
        <table alias="u" tableName="sb_users" domainObjectName="User"
               enableCountByExample="false" enableUpdateByExample="false"
               enableDeleteByExample="false" enableSelectByExample="false"
               selectByExampleQueryId="false">

            <!--指定是否用数据库中真实的字段名, 而不是采用MBG转换后的驼峰-->
            <!-- <property name="useActualColumnNames" value="true"/> -->

            <!--自动集成改类-->
            <!-- <property name="rootClass" value="com.github.prontera.domain.base.HelloBasicClass"/> -->

            <!--Mapper自动继承的接口-->
            <!-- <property name="rootInterface" value="com.github.prontera.Mapper"/> -->

            <!--当遇到String的时候setter是否会先trim()-->
            <!-- <property name="trimStrings" value="true"/> -->

            <!--先进行columnRenamingRule, 再进行useActualColumnNames. 如果有columnOverride则忽略该配置-->
  <!--关于columnRenamingRule的具体例子 http://www.mybatis.org/generator/configreference/columnRenamingRule.html-->
            <!-- <columnRenamingRule searchString="^CUST_"      replaceString=""/> -->

            <!--顾名思义, 忽略某些列-->
            <!-- <ignoreColumn column="CREATE_TIME"/> -->

            <!--也是忽略数据列, 但是可以通过正则表达式, except子元素是可选的, 代表忽略除UPDATE_TIME外的列-->
             <!--  <ignoreColumnsByRegex pattern=".*_TIME$">
                      <except column="UPDATE_TIME"/>
                </ignoreColumnsByRegex> -->
        </table>
        
        <table alias="r" tableName="sb_roles" domainObjectName="Role"
               enableCountByExample="false" enableUpdateByExample="false"
               enableDeleteByExample="false" enableSelectByExample="false"
               selectByExampleQueryId="false">
          </table>
    </context>
</generatorConfiguration>

Java的方法运行插件

官方文档中,介绍了下图所示的几种方法,我选第四种方法
在这里插入图片描述
在这里插入图片描述

  @Test
    public void runmgb() throws IOException, XMLParserException, InvalidConfigurationException, SQLException, InterruptedException {
    	List<String> warnings=new ArrayList<String>();
    	boolean overwrite=true;
    	String path= this.getClass().getClassLoader().getResource("mbgConfig.xml").getPath();
    	File configFile=new File(path);
    	ConfigurationParser cp =new ConfigurationParser(warnings);
    	Configuration config = cp.parseConfiguration(configFile);
    	DefaultShellCallback callback =new DefaultShellCallback(overwrite);
    	MyBatisGenerator myBatisGenerator=new MyBatisGenerator(config, callback, warnings);
    	myBatisGenerator.generate(null);
    	
    	
    }

注意:生成的User.java,Role.java…模型类中,要添加一个无参构造方法,不然会出现没有构造方中找到字段异常

Mybatis的分页插件

简单使用PageHelper的步骤:
1.导入jar包:

<dependency>
    <groupId>com.github.pagehelper</groupId>
    <artifactId>pagehelper</artifactId>
    <version>5.1.4</version>
</dependency>

2.在Mybatis中全局配置文件中配置拦截器
在这里插入图片描述

3.Mapper接口方式的调用,推荐这种使用方式。

//分页查询测试
	@Test
	public void pagetest() throws IOException {  
		InputStream inputStream=Resources.getResourceAsStream("mybatisConfig.xml");
		SqlSessionFactory sessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
		SqlSession session=sessionFactory.openSession();
		try {
			UserMapper userMapper=session.getMapper(UserMapper.class);

			Page<User> page = PageHelper.startPage(1,5);  //设定一页记录有5条,默认是最开始5条
			List<User> users= userMapper.getAllUser();
			for(User user:users) {
			   System.out.println(user);
			}
			
		}finally {
			session.close();
		}
/*
User [id=14, username=xiong1, password=xiong, state=1, regDate=Thu Nov 20 19:55:13 CST 2025, roleId=0]
User [id=15, username=xiong2, password=xiong, state=1, regDate=Thu Nov 20 19:55:13 CST 2025, roleId=0]
User [id=16, username=xiong3, password=xiong, state=1, regDate=Thu Nov 20 19:55:13 CST 2025, roleId=0]
User [id=17, username=xiong4, password=xiong, state=1, regDate=Thu Nov 20 19:55:13 CST 2025, roleId=0]
User [id=9, username=tttt, password=tt, state=1, regDate=Sat Sep 01 00:00:00 CST 2018, roleId=0] */

     try {
			UserMapper userMapper=session.getMapper(UserMapper.class);

			Page<User> page = PageHelper.startPage(1,5);  //设定一页记录有5条,默认是最开始5条
			List<User> users= userMapper.getAllUser();
			for(User user:users) {
			   System.out.println(user);
			}
			System.out.println(page.getPageNum());  //显示页数 1
			System.out.println(page.getPageSize());  //显示一页的条数 5
			System.out.println(page.getTotal());     //显示整个表的记录数  13
		}finally {
			session.close();
		}
/*
User [id=14, username=xiong1, password=xiong, state=1, regDate=Thu Nov 20 19:55:13 CST 2025, roleId=0]
User [id=15, username=xiong2, password=xiong, state=1, regDate=Thu Nov 20 19:55:13 CST 2025, roleId=0]
User [id=16, username=xiong3, password=xiong, state=1, regDate=Thu Nov 20 19:55:13 CST 2025, roleId=0]
User [id=17, username=xiong4, password=xiong, state=1, regDate=Thu Nov 20 19:55:13 CST 2025, roleId=0]
User [id=9, username=tttt, password=tt, state=1, regDate=Sat Sep 01 00:00:00 CST 2018, roleId=0] 
1
5
13
*/

也可以返回PagerInfo类型,它里边包含了更丰富的分页信息:

//PageInfo包含了非常全面的分页属性
assertEquals(1, page.getPageNum());  //当前而的
assertEquals(10, page.getPageSize());
assertEquals(1, page.getStartRow());
assertEquals(10, page.getEndRow());
assertEquals(183, page.getTotal());
assertEquals(19, page.getPages());
assertEquals(1, page.getFirstPage());
assertEquals(8, page.getLastPage());
assertEquals(true, page.isFirstPage());
assertEquals(false, page.isLastPage());
assertEquals(false, page.isHasPreviousPage());
assertEquals(true, page.isHasNextPage());
   try {
			UserMapper userMapper=session.getMapper(UserMapper.class);
			//User user = userMapper.selectByPrimaryKey(2);//利用mbg自动依据表生成的Mapper接口和实现(xml格式)的文件。
			//System.out.println(user);
			//Page<User> page = PageHelper.startPage(1,5);  //第一页记录有5条
			Page<User> page2 = PageHelper.startPage(2,5);  ////第二页记录有5条
			List<User> users= userMapper.getAllUser();
			
			for(User user:users) {
			   System.out.println(user);
			}

			System.out.println(page2.getTotal());     //显示整个表的记录数  13
			PageInfo<User> pageInfo = new PageInfo<>(users);
			System.out.println(pageInfo.getPageNum());  //显示页数 2
			System.out.println(pageInfo.getPageSize());  //显示一页的条数 5
			System.out.println(pageInfo.isHasNextPage());  //还有没有下一页,true
			
		}finally {
			session.close();
		}

Mybatis做批量操作

前面我们将动态标签foreach的时候,做过批量操作,但是foreach只能处理记录数不多的批量操作,数据量大了后,先不说效率,能不能成功操作都是问题,所以这里讲一讲Mybatis正确的批量操作方法:在获取opensession对象的时候,我们可以传入参数,告诉Mybatis我要批量操作:

在这里插入图片描述
测试批量插入10000条记录:这是我们是用了有选择性的插入,当然了在User中要有一个构造方法,三个字段,username,password,reg_date.
在这里插入图片描述

调用存储过程

在mysql数据库中创建一个存储过程:查询所有用户记录信息

DELIMITER $$

CREATE
    
    PROCEDURE `mybatisdemo`.`getusersprocedure`(IN sid INT,IN eid INT)
       
    BEGIN
       SELECT * FROM sb_users WHERE id>=sid AND id<=eid;
    END$$

DELIMITER ;

在Mapper接口里创建方法,和普通的查询数据方法没区别:

public List<User> getUsersByProcedure(@Param("sid") int sid,@Param("eid") int eid);

在Mybatis中调用存储过程
在这里插入图片描述
UserMapper.xml

<!-- 调用存过程来获取所有用户记录 -->
  <select id="getUsersByProcedure"  resultType="cn.ybzy.mybatisdemo.model.User" statementType="CALLABLE" >
     {call getusersprocedure(
     
         #{sid,mode=IN,jdbcType=INTEGER},
         #{eid,mode=IN,jdbcType=INTEGER}
         
     )}
  </select>

测试

//调用存储过程测试,这里我们获取所有用户记录,再查询记录号在sid,eid之间的记录
	@Test
	public void procedureTest() throws IOException { 
		InputStream inputStream=Resources.getResourceAsStream("mybatisConfig.xml");
		SqlSessionFactory sessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
		SqlSession session=sessionFactory.openSession();
		try {
		   UserMapper userMapper=session.getMapper(UserMapper.class);
		   List<User> users=userMapper.getUsersByProcedure(1,5);
		   System.out.println(users);
		   
		}finally {
			session.close();
		}
	}

spring,springmvc整合mybatis

开发工具-sts 3.9,创建一个maven web项目
在这里插入图片描述
在这里插入图片描述

在这里插入图片描述
在这里插入图片描述
1.导入jar包,pom.xml的配置如下:

<dependencies>
<dependency>
	<groupId>junit</groupId>
	<artifactId>junit</artifactId>
	<version>4.12</version>
	<scope>test</scope>
</dependency>
		<dependency>
			<groupId>org.springframework</groupId>
			<artifactId>spring-context</artifactId>
			<version>5.0.6.RELEASE</version>
		</dependency>
		<dependency>
		   <groupId>org.springframework</groupId>
		   <artifactId>spring-orm</artifactId>
		   <version>5.0.6.RELEASE</version>
		</dependency>
		<dependency>
			<groupId>org.springframework</groupId>
			<artifactId>spring-web</artifactId>
			<version>5.0.6.RELEASE</version>
		</dependency>
		<dependency>
			<groupId>org.springframework</groupId>
			<artifactId>spring-webmvc</artifactId>
			<version>5.0.6.RELEASE</version>
		</dependency>
		<dependency>
			<groupId>org.springframework</groupId>
			<artifactId>spring-tx</artifactId>
			<version>5.0.6.RELEASE</version>
		</dependency>
		<dependency>
			<groupId>org.springframework</groupId>
			<artifactId>spring-aspects</artifactId>
			<version>5.0.6.RELEASE</version>
		</dependency>
		<dependency>
			<groupId>javax.servlet</groupId>
			<artifactId>javax.servlet-api</artifactId>
			<version>3.1.0</version>
			<scope>provided</scope>
		</dependency>
		<dependency>
			<groupId>javax.servlet.jsp</groupId>
			<artifactId>jsp-api</artifactId>
			<version>2.2</version>
			<scope>provided</scope>
		</dependency>
		<dependency>
			<groupId>org.slf4j</groupId>
			<artifactId>slf4j-log4j12</artifactId>
			<version>1.7.25</version>
			<scope>test</scope>
		</dependency>
		<dependency>
			<groupId>commons-logging</groupId>
			<artifactId>commons-logging</artifactId>
			<version>1.2</version>
		</dependency>
		<dependency>
			<groupId>org.apache.taglibs</groupId>
			<artifactId>taglibs-standard-spec</artifactId>
			<version>1.2.5</version>
			<type>bundle</type>
		</dependency>
		<dependency>
			<groupId>org.apache.taglibs</groupId>
			<artifactId>taglibs-standard-impl</artifactId>
			<version>1.2.5</version>
			<type>bundle</type>
		</dependency>
		<dependency>
			<groupId>mysql</groupId>
			<artifactId>mysql-connector-java</artifactId>
			<version>5.1.46</version>
		</dependency>
		<dependency>
			<groupId>com.oracle</groupId>
			<artifactId>ojdbc6</artifactId>
			<version>12.1.0.1-atlassian-hosted</version>
		</dependency>
		<dependency>
			<groupId>com.mchange</groupId>
			<artifactId>c3p0</artifactId>
			<version>0.9.5.2</version>
		</dependency>
		<dependency>
			<groupId>org.mybatis</groupId>
			<artifactId>mybatis</artifactId>
			<version>3.4.6</version>
		</dependency>
		<dependency>
			<groupId>org.mybatis</groupId>
			<artifactId>mybatis-spring</artifactId>
			<version>1.3.2</version>
		</dependency>
		<dependency>
			<groupId>org.mybatis.generator</groupId>
			<artifactId>mybatis-generator-core</artifactId>
			<version>1.3.7</version>
		</dependency>
		<dependency>
			<groupId>org.mybatis.caches</groupId>
			<artifactId>mybatis-ehcache</artifactId>
			<version>1.1.0</version>
		</dependency>
		<dependency>
			<groupId>com.github.pagehelper</groupId>
			<artifactId>pagehelper</artifactId>
			<version>5.1.4</version>
		</dependency>
	</dependencies>
	<build>
		<plugins>
			<plugin>
				<groupId>org.apache.felix</groupId>
				<artifactId>maven-bundle-plugin</artifactId>
				<extensions>true</extensions>
			</plugin>
		</plugins>
	</build>

依赖有:spring核心:上下文依赖(context),springmvc的web,事务处理(spring-tx),切面编程(aspects),持久化包orm.JAVAWEB:Servlet-api,jsp-api 这两个包不发布到生产环境中去(proviced),日志包三个,oracle,mysql数据库驱动两个包,mybatis整合包(mybatis-spring),分页插件,jstl包,因为它要bundle功能,所以有一个maven-bundle-plugin插件。

2.在web.xml里做spring和springmvc的初始配置,这样我们就不用在应用中创建SqlSessionFactory对象打开会话了,直接调用映射方法即可

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" id="WebApp_ID" version="3.1">
  
    <!-- 给spring框架指定配置文件的位置,当在该文件中输入ContextLoaderListener会自动生成之,但要手工写位置 -->
	<context-param>
		<param-name>contextConfigLocation</param-name>
		<!-- <param-value>location</param-value> -->
		<param-value>classpath:spring.xml</param-value>
	</context-param>

	<!-- spring和javaweb应用之间的一个整合 -->
	<listener>
		<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
	</listener>


    <!--springmvc整合javaweb,当在该文件中输入DispatcherServlet回车后,逢动成生一些文件,我们再修改一下即可 -->
	<servlet>
		<servlet-name>springDispatcherServlet</servlet-name>
		<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
		<init-param>
			<param-name>contextConfigLocation</param-name>
			<!-- <param-value>location</param-value> -->
			<param-value>classpath:springmvc.xml</param-value>
		</init-param>
		<load-on-startup>1</load-on-startup>
	</servlet>

	<servlet-mapping>
		<servlet-name>springDispatcherServlet</servlet-name>
		<url-pattern>/</url-pattern>
	</servlet-mapping>
</web-app>

3.SpringMVC只扫描Controller和ControllerAdvice:
在这里插入图片描述

创建spring.xml与psringmvc.xml
在这里插入图片描述
spring必要命名空间
在这里插入图片描述

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xmlns:context="http://www.springframework.org/schema/context"
	xmlns:tx="http://www.springframework.org/schema/tx"
	xmlns:aop="http://www.springframework.org/schema/aop"
	xmlns:mybatis-spring="http://mybatis.org/schema/mybatis-spring"
	xsi:schemaLocation="http://mybatis.org/schema/mybatis-spring http://mybatis.org/schema/mybatis-spring-1.2.xsd
		http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
		http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.3.xsd
		http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.3.xsd
		http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-4.3.xsd">
  <!-- spring注解只扫描的包,不扫描Controller控制层,其它都扫描,把类放到反转容器里面,生成bean对象 -->
  <context:component-scan base-package="cn.ybzy.ssmweb">
      <context:exclude-filter type="annotation" expression="org.springframework.stereotype.Controller"/>
      <context:exclude-filter type="annotation" expression="org.springframework.web.bind.annotation.ControllerAdvice"/>
  </context:component-scan>
  <!-- 配置数据库连接与C3P0连接池, 要读取jdbc.properties-->
  <context:property-placeholder location="classpath:jdbc.properties"/>
  <bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
       <property name="user" value="${orcl.user}"></property>
       <property name="password" value="${orcl.password}"></property>
       <property name="jdbcUrl" value="${orcl.jdbcUrl}"></property>
       <property name="driverClass" value="${orcl.driverClass}"></property>
       
       <property name="initialPoolSize" value="${jdbc.initialPoolSize}"></property>
       <property name="acquireIncrement" value="${jdbc.acquireIncrement}"></property>
       <property name="minPoolSize" value="${jdbc.minPoolSize}"></property>
       <property name="maxPoolSize" value="${jdbc.maxPoolSize}"></property>
       <property name="maxStatements" value="${jdbc.maxStatements}"></property>
       <property name="maxStatementsPerConnection" value="${jdbc.maxStatementsPerConnection}"></property>
    </bean>
    
    <!-- 事务配置,hibernate的类不一样 -->
    <bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
        <property name="dataSource" ref="dataSource"></property>
    </bean>
    
    <!-- 事务属性,get,find,select,load等开头的方法这种查询的方法都是只读,其它可写的 -->
    <tx:advice id="txAdvice" transaction-manager="transactionManager">
      <tx:attributes>
         <tx:method name="get*" read-only="true"/>
         <tx:method name="find*" read-only="true"/>
         <tx:method name="load*" read-only="true"/>
         <tx:method name="select*" read-only="true"/>
      </tx:attributes>
    </tx:advice>
    <!-- 切入点的配置 -->
    <aop:config>
       <aop:pointcut expression="execution(* cn.ybzy.ssmweb.service.*.*(..))" id="txPointcut"/>
       <aop:advisor advice-ref="txAdvice" pointcut-ref="txPointcut"/>
    </aop:config>
     <!-- 整合mybatis,配sessionFactory的bean -->
    <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
       <property name="dataSource" ref="dataSource"></property>
       <property name="configLocation" value="classpath:mybatis-config.xml"></property>
       <property name="mapperLocations" value="classpath:cn/ybzy/ssmweb/mapper/*.xml"></property>
    </bean>
    <mybatis-spring:scan base-package="cn.ybzy.ssmweb.mapper"/>
</beans>

springmvc必要的命名空间

在这里插入图片描述

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xmlns:mvc="http://www.springframework.org/schema/mvc"
	xmlns:context="http://www.springframework.org/schema/context"
	xmlns:tx="http://www.springframework.org/schema/tx"
	xsi:schemaLocation="http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-4.3.xsd
		http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
		http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.3.xsd
		http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-4.3.xsd">
  <!-- springmvc注解只扫描的包,具只扫描Controller控制层,把类放到反转容器里面,生成bean对象,关掉默认扫描功能 -->
  <context:component-scan base-package="cn.ybzy.ssmweb" use-default-filters="false">
      <context:include-filter type="annotation" expression="org.springframework.stereotype.Controller"/>
      <context:include-filter type="annotation" expression="org.springframework.web.bind.annotation.ControllerAdvice"/>
  </context:component-scan>
   <!-- 必须要的标签:这是一个简化的注解类驱动,把如系统的异常处理,静态资源的转换等等通通放到IOC中 -->
   <mvc:annotation-driven/>
   <!-- 注册默认视图解析器bean,前缀:设定把如.jsp文件放到指定的文件中,后缀指定文件格式为.jsp -->
   <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
      <property name="prefix" value="/WEB-INF/views/"></property>
      <property name="suffix" value=".jsp"></property>
   </bean>
   <!-- 将css,jpg,js这些静态资源,让springmvc自动识别,不用在运行执行 -->
   <mvc:default-servlet-handler/>
</beans>

jdbc.properties—mysql,oracle,C3P0连接池的最低配置

jdbc.user=root
jdbc.password=xiong
jdbc.driverClass=com.mysql.cj.jdbc.Driver
jdbc.jdbcUrl=jdbc:mysql://124.220.60.104:3306/mybatisdemo

orcl.user=scott
orcl.password=xiong
orcl.driverClass=oracle.jdbc.OracleDriver
orcl.jdbcUrl=jdbc:oracle:thin:@124.220.60.104:1521:orcl

jdbc.acquireIncrement=5
jdbc.initialPoolSize=10
jdbc.minPoolSize=1
jdbc.maxPoolSize=100
jdbc.maxStatements=20
jdbc.maxStatementsPerConnection=5

log4j.properties

log4j.rootLogger = debug,stdout, D
log4j.appender.stdout = org.apache.log4j.ConsoleAppender
log4j.appender.stdout.Target = System.out
log4j.appender.stdout.Threshold = INFO
log4j.appender.stdout.layout = org.apache.log4j.PatternLayout
log4j.appender.stdout.layout.ConversionPattern=%d %p %m%n
log4j.appender.D = org.apache.log4j.DailyRollingFileAppender
log4j.appender.D.File = ./log4j.log
log4j.appender.D.Append = true
log4j.appender.D.Threshold = DEBUG
log4j.appender.D.layout = org.apache.log4j.PatternLayout
log4j.appender.D.layout.ConversionPattern=%d %p %m%n

mybatis-config.xml—这里我们不用配连接数据库配置和映射文件配置,它们在spring.xml中配了

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
  PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
  "https://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
     <properties resource="jdbc.properties"></properties>
  
  <settings>
     <setting name="mapUnderscoreToCamelCase" value="true"/><!--驼峰命名规则允许,这样就可以让java类与数据库表字段可以这样对应regDate对应reg_date,不然查询会出出null-->
     <!-- 下面两个项,是开启懒加载功能 -->
     <setting name="lazyLoadingEnabled" value="true"/>
     <setting name="aggressiveLazyLoading" value="false"/>
     <!-- 开启二级缓存 -->
      <setting name="cacheEnabled" value="true"/> 
  </settings>
  <plugins>
     <plugin interceptor="com.github.pagehelper.PageInterceptor"></plugin>
  </plugins>
  <!--  <environments default="mysql">
    <environment id="mysql">
      <transactionManager type="JDBC"/>
      <dataSource type="POOLED">
        <property name="driver" value="com.mysql.cj.jdbc.Driver"/>
        <property name="url" value="jdbc:mysql://124.220.60.104:3306/mybatisdemo"/>
        <property name="username" value="root"/>
        <property name="password" value="xiong"/>
      </dataSource>
    </environment>
    
 
    <environment id="oracle">
      <transactionManager type="JDBC"/>
      <dataSource type="POOLED">
        <property name="driver" value="${orcl.driverClass}"/>
        <property name="url" value="${orcl.jdbcUrl}"/>
        <property name="username" value="${orcl.user}"/>
        <property name="password" value="${orcl.password}"/>
      </dataSource>
    </environment>
    
  </environments>-->
  <databaseIdProvider type="DB_VENDOR">
  <!-- 为各数据库起别名,以便在Mapper映射文件中用 
           可用如下代码查询当前厂商名
     String databasemark=session.getConnection().getMetaData().getDatabaseProductName();
	 System.out.println(databasemark);
  
  -->
     <property name="MySQL" value="mysql"/>
     <property name="Oracle" value="oracle"/>
     <property name="SQL Server" value="sqlserver"/>
  
  </databaseIdProvider>
  <mappers>
    <!-- <mapper resource="cn/ybzy/mybatisdemo/model/UserMapper.xml"/> -->
    <!-- <mapper class="cn.ybzy.mybatisdemo.mapper.UserMapper"/> -->
    <!--  <package name="cn.ybzy.mybatisdemo.mapper"/>  spring中配了-->
  </mappers>
</configuration>

简单应用

       我们这里必竞不是做真正的项目,只是做一个讲解应用过程,所以在这里,我的服务层只搞一个方法,所询所有记录,分页之,显示第二页所有记录。模型类必有一个无参构造方法,这里我用了上面的Generator(MBG)插件依据表sb_users,反向生成了User.java,UserMapper.xml,UserMapper.java.具体代码参考上面的Generator(MBG)讲解。
Dao层UserMapper.java,UserMapper.xml

public interface UserMapper {
    //.....
      public List<User> getAllUsers();//这个是我自已加的主法,mbg自动生成的文件中没有
}
<?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="cn.ybzy.ssmweb.mapper.UserMapper">
  <resultMap id="BaseResultMap" type="cn.ybzy.ssmweb.model.User">
    <constructor>
      <idArg column="id" javaType="java.lang.Integer" jdbcType="INTEGER" />
      <arg column="username" javaType="java.lang.String" jdbcType="VARCHAR" />
      <arg column="password" javaType="java.lang.String" jdbcType="VARCHAR" />
      <arg column="state" javaType="java.lang.Integer" jdbcType="INTEGER" />
      <arg column="reg_date" javaType="java.util.Date" jdbcType="TIMESTAMP" />
      <arg column="role_id" javaType="java.lang.Integer" jdbcType="INTEGER" />
    </constructor>
  </resultMap>
  
  <sql id="Base_Column_List">
    id, username, password, state, reg_date, role_id
  </sql>
 
  <!--查询所有用记录-->
  <select id="getAllUsers" resultType="cn.ybzy.ssmweb.model.User">
      select 
         <include refid="Base_Column_List" />
      from sb_users
  </select>
 </mapper>

SERVICE服务层UserService.java,UserServcieImpl.java

public interface UserService {
	public List<User> getAllUsers();

}
@Service("userService")
public class UserServiceImpl implements UserService {
	@Autowired  //spring.xml中 <mybatis-spring:scan base-package="cn.ybzy.ssmweb.mapper"/>,把映射实现放进IOC中了,我们只用即可。
	private UserMapper userMapper;

	@Override
	public List<User> getAllUsers() {
		//Page是分页功能类,导的外部包com.github.pagehelper,、
		//下行代码是,我们获取一页记录,记录数为5条,从第二页开始
		Page<User> page2 = PageHelper.startPage(2,5);  
		System.out.println(page2.getPageSize());
		System.out.println(page2.getPageNum());
		return userMapper.getAllUsers();  //获取第二页的所有记录
	}

}

控制层UserController.java

@Controller
public class UserControlloer {
	@Autowired
	private UserService userService;
	
	@RequestMapping("/")
	public String index(Model model) {
		List<User> users=userService.getAllUsers();
		model.addAttribute("users", users);
		
		return "index";
	}
	

}

视图层/WEB-INF/views/index.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
    <%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>显示用户信息</title>
</head>
<body>
 
   <h4>显示所有用户信息</h4>
   <table border="1">
      <tr>
         <td>id</td>
         <td>用户名</td>
         <td>用户密码</td>
         <td>注册日期</td>
         <td>现在状态</td>
         
      </tr>
     <c:forEach var="user" items="${users}"> <!-- users 在控制类中,映射数据据表通过Model注入到了域中 -->
         <tr>
         <td>${user.id }</td>
         <td>${user.username }</td>
         <td>${user.password }</td>
         <td>${user.regDate }</td>
         <td>${user.state }</td>
       
      </tr>
     </c:forEach>
   </table>
</body>
</html>

测试:不用像在jar工程那样在测试类中要建如下session会话,这里我通过spring把建session对象的类放进IOC容器中了,再在web.xml中配置了监听器,监听到当web tomcat启动时,马上创建会话。

   @Test
	public void test() throws IOException, SQLException {
		//1.获取到创建数据库连接的会话的工厂,根据mybatis配置文件创 建
		InputStream inputStream=Resources.getResourceAsStream("mybatisConfig.xml");
		SqlSessionFactory sessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
	   //2.通过工厂类,获取到数据库连接的会话
		SqlSession session=sessionFactory.openSession();
		
		//3.通过session操作数据库
		try {
           userMapper=session.getMapper(UserMapper.class);
         }finally{
            session.close();
         }
  }

而我只要启动tomcat就可以了,执行控制层方法了。再到浏览器中输入:http://localhost:8081/ssmweb/回车即可看到如下图所示效果
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

熊少文

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

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

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

打赏作者

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

抵扣说明:

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

余额充值