二,Spring IOC以及整合mybatis

news2024/11/17 23:28:43

0 复习

  1. 工厂设计模式

    工厂设计模式代替new方式创建对象,目的是解耦合。

  2. Spring做为工厂的使用

    applicationContext.xml配置bean标签

    如何从工厂中获取对象

    //创建工厂
    ApplicationContext ctx = new ClassPathXmlApplicationContext("classpath:applicationContext.xml");
    //从工厂中获取bean
    ctx.getBean("id值");
    
  3. 属性注入(Spring工厂创建对象的同时,为属性赋值)

    1. set注入

      1. 简单类型

        <bean id="id值" class="全类名">
        	<property name="属性名" value="简单属性值"/>
        </bean>
        
      2. 复杂自定义类型

        <bean id="id值" class="全类名">
        	<property name="属性名" ref="另外一个bean的id"/>
        </bean>
        
      3. 数组、List、Set

        <bean id="id值" class="全类名">
        	<property name="属性名">
            	<array>
                	<value>简单值</value>
                    <ref bean="另外一个bean的id"/>
                    ...
                </array>
            </property>
        </bean>
        
        <bean id="id值" class="全类名">
        	<property name="属性名">
            	<list>
                	<value>简单值</value>
                    <ref bean="另外一个bean的id"/>
                    ...
                </list>
            </property>
        </bean>
        
        <bean id="id值" class="全类名">
        	<property name="属性名">
            	<set>
                	<value>简单值</value>
                    <ref bean="另外一个bean的id"/>
                    ...
                </set>
            </property>
        </bean>
        
      4. Map

        <bean id="id值" class="全类名">
        	<property name="属性名">
            	<map>
                	<entry key="键的值" value="简单值"/>
                    <entry key="键的值" value—ref="另外一个bean的id"/>
                </map>
            </property>
        </bean>
        
      5. Properties

        <bean id="id值" class="全类名">
        	<property name="属性名">
            	<props>
                	<prop key="字符串的键">字符串的值</prop>
                    <prop key="字符串的键">字符串的值</prop>
                    ...
                </props>
            </property>
        </bean>
        
    2. 构造注入

      <bean id="id值" class="全类名">
      	<constructor-arg value="简单值"/>
          <constructor-arg ref="另外一个bean的id"/>
      </bean>
      
      <bean id="id值" class="全类名">
      	<constructor-arg value="简单值" type="值的类型" index="0"/>
          <constructor-arg ref="另外一个bean的id" type="值的类型" index="1"/>
      </bean>
      

1 注入补充【了解】

1.1 注入null值

需要显式的为一个属性赋null值时,需要使用null子标签。

<bean id="addr" class="com.bz.entity.Address">
    <constructor-arg value="硅谷"/>
    <constructor-arg><null></null></constructor-arg>
</bean>

1.2 内部bean

当一个bean只为另外一个bean使用时,可以写成内部bean的形式。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-tUSeN7Jm-1673589459943)(Spring day02.assets/image-20200331110913137.png)]

2 FactoryBean技术(创建复杂对象)

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-NyZ6NhUP-1673589459944)(Spring day02.assets/image-20210614212427106.png)]

当Spring工厂需要创建一些无法通过new直接创建的对象,就需要使用FactoryBean技术创建复杂对象。

通过完成Spring创建JDBC中Connection的需求,演示FactoryBean的使用步骤:
准备工作:pom.xml导入mysql-connector-java依赖

 <dependency>
     <groupId>mysql</groupId>
     <artifactId>mysql-connector-java</artifactId>
     <version>8.0.23</version>
</dependency>
  1. 定义一个用于创建复杂对象的类,必须实现FactoryBean接口

    public class ConnectionFactoryBean implements FactoryBean<Connection> {
        @Override
        // 用于返回 创建的复杂对象
        public Connection getObject() throws Exception {
            Class.forName("com.mysql.jdbc.Driver");
            String url = "jdbc:mysql://localhost:3306/bz?useUnicode=true&characterEncoding=utf-8&useSSL=false&serverTimezone=Asia/Shanghai";
            String username = "root";
            String password = "root";
    
            return DriverManager.getConnection(url,username,password);
        }
    
        @Override
        //返回 复杂对象的类型(类对象)
        public Class<?> getObjectType() {
            return Connection.class;
        }
    
        @Override
        //决定复杂对象是不是单例
        public boolean isSingleton() {
            return false;
        }
    }
    
  2. 在applicationContext.xml中配置上一步定义的FactoryBean

    <!--
            getBean("conn")获取不是ConnectionFactoryBean类型的对象,获取getObject()返回的复杂对象
         -->
    <bean id="conn" class="com.bz.factory.ConnectionFactoryBean"/>
    

​ 3.测试

@Test
    public void a(){
        ApplicationContext ac= new ClassPathXmlApplicationContext("classpath:applicationContext.xml");
        Object o1=ac.getBean("conn");
        Object o2=ac.getBean("conn");
        Object o3=ac.getBean("conn");
        System.out.println(o1);
        System.out.println(o2);
        System.out.println(o3);
    }

注意:

  1. 复杂对象的单例控制,由isSingleton()方法返回值决定
  2. 通过getBean(“&id属性”),可以获取自定义的FactoryBean对象

3 Spring的IOC和DI

IOC(Inversion of Control)控制反转、反转控制。
DI(Dependency Injection)依赖注入

控制:对于类中属性的赋值的控制权。

传统的正向控制:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-uNgYg5OC-1673589459945)(Spring day02.assets/image-20210615224410283.png)]

正向控制存在的问题:类和类之间强耦合。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-LpPdaBhk-1673589459946)(Spring day02.assets/image-20210615225645602.png)]

IOC和DI对同一件事,不同角度的描述。IOC更加偏重思想,DI更加偏重于实现手段。

IOC:属性的赋值权力从代码反转到Spring框架中。

DI:Spring通过依赖注入完成属性赋值。

3 Spring配置文件的拆分

3.1 applicationContext.xml的拆分

一个复杂的企业应用会拆分成多个模块,不同模块中有各自的spring配置,最终还需要聚合在一起。

<import resource="classpath:datasource/a.xml"/>

classpath:JVM寻找类的起始路径,可以认为java、resources都是classpath。

3.2 Spring配置文件的xsd

XML的格式约束文件有2种:DTD(Document Type Definition)和XSD(XML Schema Definition)。XSD和DTD一样用来约束配置文件,DTD编写简单,XSD功能强大。

一般地,简单的配置文件用dtd约束(如Struts2的配置文件,MyBatis的配置文件),复杂的配置文件使用xsd约束(如Spring)。

  1. xsd的基本使用

    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-OB6O7Pzd-1673589459946)(Spring day02.assets/image-20200331154014258.png)]

  2. 在一个配置文件中使用多个xsd

    Spring不同的模块定义了不同的xsd文件,在一个Spring配置文件中使用多个模块的功能,也就要在配置文件中使用多个xsd。

    在这里插入图片描述

    使用步骤:

    1. 在跟标签中添加xmlns:前缀=“其它xsd的命名空间”
    2. 在xsi:schemaLocation=“添加路径对”
    3. 使用其它xsd中定义的标签需要添加前缀:

    示例:

    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-gJz6Cjnd-1673589459947)(Spring day02.assets/image-20200331155251020.png)]

3.3 Spring 配置文件properties的拆分

程序中关于数据库的参数配置,一般都抽取到jdbc.properties文件中。Spring的applicationContext.xml中关于数据库的配置也一样要抽取。

  1. 将数据库参数抽取到jdbc.properties中

    driverClassName=com.mysql.jdbc.Driver
    url=jdbc:mysql://localhost:3306/bz?useUnicode=true&characterEncoding=utf-8
    user=root
    password=root
    
  2. 在Spring的配置文件中读取jdbc.properties

    <!-- 读取配置文件 使用context.xsd定义property-placeholder标签读取jdbc.properties文件-->
    <context:property-placeholder location="classpath:jdbc.properties"/>
    
  3. 在需要使用参数的地方,通过${参数名}获取参数值

    <bean id="conn" class="com.bz.factory.ConnectionFactoryBean" >
        <property name="url" value="${url}"/>
        <property name="driverClassName" value="${driverClassName}"/>
        <property name="username" value="${user}"/>
        <property name="password" value="${password}"/>
    </bean>
    

注意:${username}会优先读取操作系统的用户名,jdbc.properties中必须改名

4 Spring整合MyBatis

4.1 整合效果分析

首先,回顾下MyBatis项目开发步骤:

  1. 搭建开发环境

    1. 新建项目

    2. 导入依赖

      数据库驱动依赖:mysql-connector-java.jar

      MyBatis相关的依赖

      servlet+jsp+jstl的依赖

      junit+hutool+druid

    3. 配置文件+工具类

      jdbc.properties

    log4j.properties

    xxxMapper.xml

    mybatis-config.xml

    1. 配置文件初始化

    mybatis-config.xml 初始化配置

  2. 建表

  3. 实体

  4. mapper

    1. 接口
    2. 实现:XxxMapper.xml
  5. service

    1. 接口

    2. 实现:

      SqlSession sqlSession = MyBatisUtils.openSession();

      XxxMapper mapper = sqlSession.getMapper(XxxMapper.class);

  6. test

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-odfbVCz7-1673589459947)(Spring day02.assets/image-20210614214830286.png)]

Spring整合MyBatis的效果就是使用Spring的工厂功能创建MyBatis项目中需要的关键对象:Dao对象和Service对象。

4.2 整合思路分析

整合的关键在于如何在applicationContext.xml中配置,由Spring工厂创建Dao对象。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-gpsHBs68-1673589459948)(Spring day02.assets/image-20210614222528122.png)]

思路:原dao的编码创建过程中需要创建哪些对象,在Spring中也需要创建哪些对象,只不过编码方式转为Spring的配置。原来编码创建的对象,在Spring中以bean标签的形式体现。

4.3 整合实战

准备工作,添加 mybatis-spring依赖

<dependency>
    <groupId>com.alibaba</groupId>
    <artifactId>druid</artifactId>
    <version>1.1.22</version>
</dependency>

<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-context</artifactId>
    <version>5.2.8.RELEASE</version>
</dependency>
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-jdbc</artifactId>
    <version>5.2.8.RELEASE</version>
</dependency>
<!-- 整合spring mybatis的依赖-->
<dependency>
    <groupId>org.mybatis</groupId>
    <artifactId>mybatis-spring</artifactId>
    <version>2.0.4</version>
</dependency>

初版配置:

<!-- 读取jdbc.properties-->
<context:property-placeholder location="classpath:jdbc.properties"/>
<!-- 0 定义一个连接池 -->
<bean id="druidDataSource" class="com.alibaba.druid.pool.DruidDataSource">
    <property name="driverClassName" value="${jdbc.driverClassName}"/>
    <property name="url" value="${jdbc.url}"/>
    <property name="username" value="${jdbc.username}"/>
    <property name="password" value="${jdbc.password}"/>
</bean>

<!-- 定义SqlSessionFactory-->
<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">

    <property name="dataSource" ref="druidDataSource"/>
    <!--
            配置实体类的包名,自动为实体配置短类名的别名
         -->
    <property name="typeAliasesPackage" value="com.bz.entity"/>
    <property name="mapperLocations">
        <!-- 配置mapper.xml的路径-->
        <list>
            <!--<value>classpath:com/bz/mapper/UserMapper.xml</value>
                <value>classpath:com/bz/mapper/StudentMapper.xml</value>
                <value>classpath:com/bz/mapper/BookMapper.xml</value>-->
            <value>classpath:com/bz/mapper/*Mapper.xml</value>
        </list>
    </property>
</bean>

<!-- 定义SqlSession -->
<bean id="sqlSession" class="org.mybatis.spring.SqlSessionTemplate">
    <constructor-arg ref="sqlSessionFactory"/>
</bean>

<!-- 创建 UserMapper实现类对象-->
<bean id="userMapper" class="org.mybatis.spring.mapper.MapperFactoryBean">
    <property name="sqlSessionTemplate" ref="sqlSession"/>
    <property name="mapperInterface" value="com.bz.mapper.UserMapper"/>
</bean>

<!--<bean id="bookMapper" class="org.mybatis.spring.mapper.MapperFactoryBean">
        <property name="sqlSessionTemplate" ref="sqlSession"/>
        <property name="mapperInterface" value="com.bz.mapper.BookMapper"/>
    </bean>-->

<bean id="userService" class="com.bz.service.impl.UserServiceImpl">
    <property name="userMapper" ref="userMapper"/>
</bean>

最终配置:

<!-- 读取jdbc.properties-->
    <context:property-placeholder location="classpath:jdbc.properties"/>
    <!-- 0 定义一个连接池 -->
    <bean id="druidDataSource" class="com.alibaba.druid.pool.DruidDataSource">
        <property name="driverClassName" value="${jdbc.driverClassName}"/>
        <property name="url" value="${jdbc.url}"/>
        <property name="username" value="${jdbc.username}"/>
        <property name="password" value="${jdbc.password}"/>
    </bean>

    <!-- 定义SqlSessionFactory-->
    <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">

        <property name="dataSource" ref="druidDataSource"/>
        <!--
            配置实体类的包名,自动为实体配置短类名的别名
         -->
        <property name="typeAliasesPackage" value="com.bz.entity"/>
        <property name="mapperLocations">
            <!-- 配置mapper.xml的路径-->
            <list>                
                <value>classpath:com/bz/mapper/*Mapper.xml</value>
            </list>
        </property>
    </bean>
    <!--
        自动创建Mapper实现类对象
        自动扫描basePackage包下的Mapper接口,自动创建Mapper接口的实现类对象

    -->
    <bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
        <!--
            mapper实现类对象的id规则:接口名首字母小写
            UserMapper  ==> userMapper
            BookMapper ==> bookMapper
        -->
        <property name="basePackage" value="com.bz.mapper"/>
    </bean>

    <bean id="userService" class="com.bz.service.impl.UserServiceImpl">
        <property name="userMapper" ref="userMapper"/>
    </bean>

注意:Service中的编码式事务控制,对由Spring创建的Dao无效。所以,我们删除service中事务控制代码,暂时以无事务的状态运转。

5 Spring整合Servlet

5.1 整合效果分析

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Geq1duLf-1673589459948)(Spring day02.assets/image-20210615132416834.png)]

预期效果:Servlet中获取Service对象的方式从new改为从工厂中获取。

5.2 整合方案

Spring整合Servlet的关键在于从Spring工厂中获取Service对象,这就必须先解决2个问题:

  • 如何创建Spring工厂
  • 何时创建Spring工厂

方案1: 直接在Servlet的服务方法中,创建工厂。

public class XxxController extends HttpServlet{
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // 收参 
        ...
        //调用业务层方法
        ApplicationContext ctx = new ClassPathXmlApplicationContext("classpath:applicationContext.xml");
        XxxService xxxService = (XxxService) ctx.getBean("xxxService");
       	//跳转
        ...
    }
}

存在的问题:每请求一次服务方法,就重新创建1次工厂(工厂是重量级对象,占用内容空间较大),性能较差

方案2:将工厂做成属性

public class XxxController extends HttpServlet{
    private ApplicationContext ctx = new ClassPathXmlApplicationContext("classpath:applicationContext.xml");
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // 收参 
        ...
        //调用业务层方法
        XxxService xxxService = (XxxService) ctx.getBean("xxxService");
       	//跳转
        ...
    }
}

存在的问题:每一个Servlet独有一个工厂属性,有多少Servlet就会有多少Spring工厂,性能仍待提升

方案3:工厂应该全局共享,整个web应用中只创建一个工厂

public class bzWebApplicationContextUtils{
    private static ApplicationContext ctx = new ClassPathXmlApplicationContext("classpath:applicationContext.xml");
    public static ApplicationContext getWebApplicationContext(){
        return ctx;
    }
}

public class XxxController extends HttpServlet{
   
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // 收参 
        ...
        //调用业务层方法
        ApplicationContext ctx = bzWebApplicationContextUtils.getWebApplicationContext();
        XxxService xxxService = (XxxService) ctx.getBean("xxxService");
       	//跳转
        ...
    }
}

存在的问题:第1次访问Servlet在调用WebApplicationContextUtils时需要创建工厂,工厂的创建比较耗时。第1次请求的响应会比较耗时,用户体验差。

方案4:可以在Web应用一启动时就提前创建Spring工厂,在ServletContextListener中监听到Web应用的启动

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ShaxJZFr-1673589459949)(Spring day02.assets/image-20210615220557477.png)]

public class ContextLoaderListener implements ServletContextListener {
  
    @Override
    public void contextInitialized(ServletContextEvent sce) {
        ApplicationContext ctx = new ClassPathXmlApplicationContext("classpath:applicationContext.xml");
        ServletContext servletContxt = sec.getServletContext();
        servletContext.setAttribute("ctx",ctx);
    }
    
}
public class bzWebApplicationContextUtils{

    public static ApplicationContext getWebApplicationContext(ServletContext sc){
        return (ApplicationContext).getAttribute("ctx");
    }
}


public class XxxController extends HttpServlet{
   
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // 收参 
        ...
        //调用业务层方法
        ApplicationContext ctx = bzWebApplicationContextUtils.getWebApplicationContext(req.getServletContext());
        XxxService xxxService = (XxxService) ctx.getBean("xxxService");
       	//跳转
        ...
    }
}

方案5(重点):和上一个方案的思路一致,只不过使用Spring-Web模块内置的监听器和工具类。

准备工作,pom.xml添加 spring-web依赖

<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-web</artifactId>
    <version>5.2.8.RELEASE</version>
</dependency>

web.xml

<!-- 设置applicationConext.xml的路径-->
<context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>classpath:applicationContext.xml</param-value>
</context-param>
<!-- 配置监听器:在web应用启动时,自动的创建工厂并保存到ServletContext中-->
<listener>
    <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
public class XxxController extends HttpServlet{
   
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // 收参 
        ...
        //调用业务层方法
        ApplicationContext ctx = WebApplicationContextUtils.getWebApplicationContext(req.getServletContext());
        XxxService xxxService = (XxxService) ctx.getBean("xxxService");
       	//跳转
        ...
    }
}

方案1~方案4为思路过渡方案,最终在理解各种方案的优缺点后,掌握最终的标准方案即可。

6 总结:SM项目开发步骤

  1. 搭建开发环境

    1. 新建web项目(补全项目结构)

    2. 导入依赖,pom.xml引入依赖

      数据库依赖:

      mysql-connector-java.jar

      druid

      spring依赖:

      spring-context

      mybatis依赖:

      mybatis

      slf4j-log4j12

      mybatis和spring整合

      spring-jdbc

      mybatis-spring

      servlet+jsp+jstl依赖

      servlet-api

      jsp-api

      jstl

      springmvc依赖

      spring-webmvc

      hutool工具

      hutool-all

    3. 配置文件和工具类

      jdbc.properties

      lo4j.properties

      mybatis-config.xml (不再需要)

      xxxMapper.xml

      web.xml

      applicationContext.xml

      MyBatisUtils.java (不再需要)

    4. 配置文件初始化

      web.xml中配置Spring监听器,创建Spring工厂

  2. 建表

  3. 实体

  4. dao

    1. 接口
    2. 实现: mapper.xml中定义sql语句
  5. service

    1. 接口
    2. 实现:暂不提供事务控制(删除掉事务控制的代码)
  6. test

  7. Controller+jsp

    ​ Controller:从ServletContext中获取工厂,再从工厂中获取Service对象

  8. 集成测试

pom.xml

<!-- jdbc依赖-->
<dependency>
    <groupId>mysql</groupId>
    <artifactId>mysql-connector-java</artifactId>
    <version>8.0.23</version>
</dependency>

<!-- 阿里巴巴连接池依赖 -->
<dependency>
    <groupId>com.alibaba</groupId>
    <artifactId>druid</artifactId>
    <version>1.0.24</version>
</dependency>

<!--引入Spring依赖-->
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-context</artifactId>
    <version>5.2.8.RELEASE</version>
</dependency>

<dependency>
    <groupId>org.aspectj</groupId>
    <artifactId>aspectjweaver</artifactId>
    <version>1.9.5</version>
</dependency>

<!-- mybatis依赖-->
<dependency>
    <groupId>org.mybatis</groupId>
    <artifactId>mybatis</artifactId>
    <version>3.5.4</version>
</dependency>
<dependency>
    <groupId>org.slf4j</groupId>
    <artifactId>slf4j-log4j12</artifactId>
    <version>1.7.30</version>
</dependency>

<!-- spring 整合 mybatis 依赖-->
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-jdbc</artifactId>
    <version>5.2.8.RELEASE</version>
</dependency>
<dependency>
    <groupId>org.mybatis</groupId>
    <artifactId>mybatis-spring</artifactId>
    <version>2.0.4</version>
</dependency>

<!-- servlet jsp jstl 依赖-->
<dependency>
    <groupId>javax.servlet</groupId>
    <artifactId>javax.servlet-api</artifactId>
    <version>4.0.1</version>
    <scope>provided</scope>
</dependency>

<dependency>
    <groupId>javax.servlet.jsp</groupId>
    <artifactId>javax.servlet.jsp-api</artifactId>
    <version>2.3.3</version>
    <scope>provided</scope>
</dependency>
<dependency>
    <groupId>jstl</groupId>
    <artifactId>jstl</artifactId>
    <version>1.2</version>
</dependency>
<!-- https://mvnrepository.com/artifact/taglibs/standard -->
<dependency>
    <groupId>taglibs</groupId>
    <artifactId>standard</artifactId>
    <version>1.1.2</version>
</dependency>


<!-- SpringMVC依赖 -->
 <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-webmvc</artifactId>
        <version>5.2.8.RELEASE</version>
    </dependency>

<!--
       hutool工具类
    -->
<!-- https://mvnrepository.com/artifact/cn.hutool/hutool-all -->
<dependency>
    <groupId>cn.hutool</groupId>
    <artifactId>hutool-all</artifactId>
    <version>5.2.3</version>
</dependency>

<!-- junit测试依赖-->
<dependency>
    <groupId>junit</groupId>
    <artifactId>junit</artifactId>
    <scope>test</scope>
    <version>4.12</version>
</dependency>

web.xml

<!-- 配置spring配置文件的路径-->
<context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>classpath:applicationContext.xml</param-value>
</context-param>
<!-- 监听器:监听web应用启动,根据上面配置的spring配置文件路径创建Spring工厂-->
<listener>
    <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>

applicationContext.xml

<context:property-placeholder location="classpath:jdbc.properties"/>
<!-- 创建连接池 DataSource -->
<bean id="druidDataSource" class="com.alibaba.druid.pool.DruidDataSource">
    <!-- 必须的配置 -->
    <property name="url" value="${url}"/>
    <property name="driverClassName" value="${driverClassName}"/>
    <property name="username" value="${user}"/>
    <property name="password" value="${password}"/>
    <!-- 额外的配置-->
</bean>

<!-- 定义SqlSessionFactory-->
<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">

    <property name="dataSource" ref="druidDataSource"/>
    <!--
            配置实体类的包名,自动为实体配置短类名的别名
         -->
    <property name="typeAliasesPackage" value="com.bz.entity"/>
    <property name="mapperLocations">
        <!-- 配置mapper.xml的路径-->
        <list>                
            <value>classpath:com/bz/mapper/*Mapper.xml</value>
        </list>
    </property>
</bean>
<!--
        自动创建Mapper实现类对象
        自动扫描basePackage包下的Mapper接口,自动创建Mapper接口的实现类对象

    -->
<bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
    <!--
            mapper实现类对象的id规则:接口名首字母小写
            UserMapper  ==> userMapper
            BookMapper ==> bookMapper
        -->
    <property name="basePackage" value="com.bz.mapper"/>
</bean>

<!-- 定义service对象-->
<bean id="userService" class="com.bz.service.impl.UserServiceImpl">
    <property name="userMapper" ref="userMapper"/>
</bean>
<!--
        配置实体类的包名,自动为实体配置短类名的别名
     -->
<property name="typeAliasesPackage" value="com.bz.entity"/>
<property name="mapperLocations">
    <!-- 配置mapper.xml的路径-->
    <list>                
        <value>classpath:com/bz/mapper/*Mapper.xml</value>
    </list>
</property>
```

在这里插入图片描述
文章对应源代码地址: https://download.csdn.net/download/qq_36827283/87382597

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/160233.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

AWS实战:Aurora到Redshift数据同步

什么是AuroraAmazon Aurora是一种基于云且完全托管关系型数据库服务&#xff0c;与MySQL 和 PostgreSQL 数据库兼容&#xff0c;完全托管意味着自动对数据库进行管理&#xff0c;包括管理数据备份、硬件配置和软件更新等操作Amazon Aurora提供了企业级性能Amazon Aurora提供了多…

【C/C++】动态顺序表详解(附完整源码)

本章内容 写在前面 1.静态与动态是指什么&#xff1f; 2.动态顺序表结构的定义 3.动态顺序表的函数接口实现 4.动态顺序表的问题及思考 5.关于顺序表的OJ题 6.OJ答案及解析 1.移除元素 2.删除有序数组中的重复项 ​3.合并两个有序数组 7.动态顺序表完整源码 1.SeqL…

《mSystems》最新研究| 李香真老师亲临凌波微课LorMe云讲堂解读贡嘎山反硝化菌群组装模式和驱动因素

2021年11月2日&#xff0c;李香真团队在《mSystems》期刊正式发表了题为“Patterns and Drivers of nirK-Typeand nirS-Type Denitrifier Community Assembly along an Elevation Gradient”的研究论文。该研究以青藏高原东部边界最高山——贡嘎山作为研究平台&#xff0c;比较…

小程序与普通网页开发有什么区别?

小程序的开发同普通的网页开发相比有很大的相似性&#xff0c;小程序的主要开发语言也是 JavaScript&#xff0c;但是二者还是有些差别的。 普通网页开发可以使用各种浏览器提供的 DOM API&#xff0c;进行 DOM 操作&#xff0c;小程序的逻辑层和渲染层是分开的&#xff0c;逻…

[前端笔记] 1.WEB基本概念

[前端笔记] 1.WEB基本概念基本概念1.资源 resourse2.链接3.HTTP 协议4.网页的真实样子&#xff1a;HTML静态网页与动态网页1.静态网页2.动态网页现代网站架构1.网站架构当我们访问一个网站时&#xff0c;后台都会发生什么事情捏?www——万维网 www&#xff1a;World Wide Web …

JAVA中医舌诊接口使用示例代码,JAVA舌象图特征人工智能识别代码,JAVA实现舌象特征检测与识别

中医舌诊接口使用示例-Java示例项目 中医舌诊健康状态检测API 1&#xff0e;此文档适用于集成中国中医舌诊开放平台功能的用户。 2&#xff0e;此文档说明了与中国中医舌诊开放平台的数据交互方法&#xff08;restful接口&#xff09;&#xff0c;按需使用体质健康API、脏腑健…

盖子的c++小课堂——第十讲:字符

前言 我呢&#xff0c;早上刚发布第九讲&#xff0c;心里想的是马桶盖终于保住了&#xff0c;结果…… 生产队的刘同学&#xff1a;快&#xff0c;继续更&#xff0c;不然你下次吃泡面没调料包 其他粉丝&#xff1a;啊……啊对对对 啊&#xff01;&#xff01;&#xff01;&…

OPTEE TA介绍

前言 本文主要介绍OPTEE的TA(Trusted Applications)&#xff0c;翻译自官方文档&#xff1a;Trusted Applications — OP-TEE documentation documentation (optee.readthedocs.io) 有两种方法可以实现可信应用程序 &#xff08;TA&#xff09;&#xff1a;伪 TA 和用户模式 T…

Speedoffice(word)如何输入特殊符号?

Word文档有时需要输入人民币单位“元”&#xff08;&#xff09;的符号&#xff0c;那么怎么打出来了&#xff0c;以我最常用的Speedoffice为例和大家分享一下方法。步骤&#xff1a;1&#xff0c;首先运行office软件&#xff0c;新建一份word&#xff0c;找到“插入”菜单栏里…

再学C语言33:函数——地址运算符

C中最重要、最复杂的概念之一就是指针&#xff08;pointer&#xff09; 指针是用于存储地址的变量 例如&#xff1a;scanf()函数中使用地址作为参数 当需要改变调用函数中的某个值时&#xff0c;任何被调用的无返回值的C函数都需要使用地址参数完成该任务 一、地址运算符&a…

c语言重点

1、以下代码循环几次&#xff1f;&#xff08;面试题&#xff09; void test(){int i; // 局部变量 i 的值是不确定的for(;i<10;i){;} }答案是---------不确定&#xff0c;在 c 语言中局部变量 i 没有初始化&#xff0c;值是不确定的&#xff0c;所以 i 的值可能是…

GeoHash 的编码方法

对一组经纬度进行 GeoHash 编码时&#xff0c;我们要先对经度和纬度分别编码&#xff0c;然后再把经纬度各自的编码组合成一个最终编码。 对于一个地理位置信息来说&#xff0c;它的经度范围是[-180,180]。GeoHash 编码会把一个经度值编码成一个 N 位的二进制值&#xff0c;我…

MySQL进阶篇之存储引擎

01、存储引擎 1.1、MySQL体系结构 连接层 最上层是一些客户端和链接服务&#xff0c;主要完成一些类似于连接处理、授权认证、及相关的安全方案。服务器也会为安全接入的每个客户端验证它所具有的操作权限。 服务层 第二层架构主要完成大多数的核心服务功能&#xff0c;如SQL…

重要的字符(串)函数的使用及其实现

目录 字符串函数注意点 1、\0 2、适当使用const修饰 3、多使用assert断言 4、库函数不可能完全安全 1、求字符串长度strlen 1、计数实现 2、递归实现 3、指针相减求元素个数 2、长度不受限制的字符串函数 1、strcpy 2、strcat 3、strcmp 3、长度受限制的字符串函数…

ESP32设备驱动-MLX90614红外测温传感器驱动

MLX90614红外测温传感器驱动 1、MLX90614介绍 MLX90614 是一款用于非接触式温度测量的红外温度计。IR 敏感型热电堆检测器芯片和信号调节 ASIC 都集成在同一 TO-39 罐封装中。MLX90614 集成有低噪声放大器、17 位 ADC 和强大的 DSP 单元,因此温度计兼具高精度和高分辨率。 …

少儿Python每日一题(22):杨辉三角

原题解答 本次的题目如下所示: 杨辉三角形又称Pascal三角形,它的第i+1i+1行是的展开式的系数。 它的一个重要性质是:三角形中的每个数字等于它两肩上的数字相加。 下面给出了杨辉三角形的前4行: 1 1 1 1 2 1 1 3 3 1 给出n,输出它的前n行。 输入: 输入包含一个数n。 输出…

学习CSS3,使用双旋转实现福到了的迎春喜庆特效

春节快到了&#xff0c;因为疫情已经好久没有回老家了&#xff0c;今年终于可以回家过年了&#xff0c;我已经抑制不住自己激动的心情了。因此&#xff0c;我利用css3的旋转做了一个福到了的特效&#xff0c;而且是双旋转哦。 目录 1、实现思路 2、大红纸的渲染过程 3、错误…

【自学Python】Python运算符优先级

Python运算符优先级 Python运算符优先级教程 我们知道&#xff0c;在数学运算中&#xff0c;有 “先乘除后加减” 的运算规则&#xff0c;在我们程序语言中一样有运算符的优先级问题&#xff0c;来决定我们运算的顺序问题&#xff0c;这就是运算符的优先级。 即所谓运算符的…

C++STL之set与map的使用

本文目录前言一、关联式容器二、键值对(pair)三、树形结构的关联式容器1.set1.1set的介绍1.2set的使用1.2.1set的模板参数列表1.2.2set的构造(1)构造空的set(2)以数组的形式构造(3)用迭代器区间进行构造(4)拷贝构造1.2.3set的迭代器(1)iterator begin()(2)iterator end()(3)con…

一天变现100w就是这么简单!呆头鹅批量剪辑软件批量剪辑带货视频

呆头鹅剪辑是一款全自动的视频剪辑软件&#xff0c;包含剪辑、合成、去重、特效、配音、字幕、水印、后期处理、自动生成片头等功能&#xff0c;可以用于视频批量搬运&#xff0c;给视频增加特效&#xff0c;图片合成视频&#xff0c;视频混剪&#xff0c;自动加配音字幕&#…