Java-31 深入浅出 Spring - IoC 基础 启动IoC XML与注解结合的方式 配置改造 applicationContext.xml

点一下关注吧!!!非常感谢!!持续更新!!!

大数据篇正在更新!https://blog.csdn.net/w776341482/category_12713819.html

目前已经更新到了:

  • MyBatis(已更完)
  • Spring(正在更新...)

XML与注解结合的方式

需要注意:

  • 实际企业开发中,纯 XML 模式已经很少使用了
  • 引入注解功能,不需要引入额外的 Jar
  • XML+注解结合模式,XML 文件依然存在,所以,Spring IoC 容器仍然是从加载 XML 开始。
  • 哪些 Bean 定义需要写到 XML 中,哪些 Bean 的定义使用注解

简单来说,第三方的 Jar 中的 Bean 定义在 XML 中,自己开发的 Bean 使用注解的方式。

XML中标签与注解的对应

DI 依赖注入的注解实现方式

推荐使用 Autowired,该注解是 Spring 提供的注解,采取的策略为【按照类型注入】:

java 复制代码
public class WzkTransferServiceImpl {
    @Autowired
    private WzkAccountDao wzkAccountDao;
}

如上代码所示,这样装配回去 Spring 容器中找到类型为 AccountDao 的类,然后将其注入进来。这样会产生一个问题,当一个类型有多个 Bean 的值的时候,会造成无法选择具体注入哪一个的情况,这个时候我们需要配合着使用 Qualifier 注解。

Quailier 会告诉 Spring 用哪个对象来注入:

java 复制代码
public class WzkTransferServiceImpl {
    @Autowired
    @Qualifier(name="jdbcWzkAccountDaoImpl") 
    private WzkAccountDao wzkAccountDao;
}

当然,我们也可以使用 JDK 提供的 Resource 注解,该注解默认按照【byName】自动注入:

java 复制代码
public class WzkTransferService {
    
    @Resource 
    private AccountDao accountDao;
    
    @Resource(name="studentDao") 
    private StudentDao studentDao;
    
    @Resource(type="TeacherDao") 
    private TeacherDao teacherDao;
     
    @Resource(name="manDao",type="ManDao") 
    private ManDao manDao;

}

这里需要注意:

  • 如果同时指定了 name 和 type,则从 Spring 上下文中寻找唯一匹配的 Bean进行装配。
  • 如果指定了 name,则从上下文中查找名称(id)匹配的 bena 进行装配,找不到则抛出异常
  • 如果指定了 type,则从上下文找到类似的匹配的唯一bean进行装配,找不到或是找到多个,都会抛出异常
  • 如果既没有指定 name,又没有的指定 type,则自动按照 byName 方式进行装配

我们需要注意的是:

Resource 在 JDK11 中已经移除了,如果要使用的话,需要单独引入 Jar 包:

xml 复制代码
<dependency>
 <groupId>javax.annotation</groupId>
 <artifactId>javax.annotation-api</artifactId>
 <version>1.3.2</version>
</dependency>

applicationContext.xml

写入内容如下:

xml 复制代码
<?xml version="1.0" encoding="UTF-8"?>
<beans  xmlns="http://www.springframework.org/schema/beans"
        xmlns:context="http://www.springframework.org/schema/context"
        xmlns:aop="http://www.springframework.org/schema/aop"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="
        http://www.springframework.org/schema/beans
        https://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/context
        https://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/aop
        https://www.springframework.org/schema/aop/spring-aop.xsd
">

</beans>

对应的截图如下所示:

对应截图如下所示:

我们之前是自己写的 beans.xml,我们现在希望借助 Spring 的情况下,一步一步改造我们之前自己手动控制 Bean 的方式。

web.xml

xml 复制代码
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"
         version="3.1">
    <context-param>
        <param-name>contextConfigLocation</param-name>
        <param-value>classpath:applicationContext.xml</param-value>
    </context-param>
    <listener>
        <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
    </listener>
</web-app>

对应的截图如下所示:

配置改造

接下来我们将刚才的 纯 XML 的模式的代码,改造成 注解 + XML 的方式,解放出一定的 XML 来。

比如在 纯 XML 模式下,我们写的:

xml 复制代码
<!-- 配置 Bean -->
    <bean id="wzkTransferService" class="wzk.service.impl.WzkTransferServiceImpl">
        <constructor-arg name="wzkAccountDao" ref="wzkAccountDao"></constructor-arg>
    </bean>

这个目的是让 Spring 接管我们的 Bean,而此时,我们可以将这一系列的 Bean 配置都移除出去,使用注解的方式来满足我们的 Bean 管理。

此时,我们将 Bean 的 XML 配置移除,并在需要交由 Spring 管理的 Bean 上加入注解、加入DI 的管理。

但是此时,Spring 是不知道哪些对象要处理的,所以我们需要告诉 Spring 哪些需要进行扫描:

xml 复制代码
<context:annotation-config/>
<context:component-scan base-package="wzk"/>

对应的结果如下图所示:

JdbcWzkAccountDaoImpl

这里加入注解和 ID 的管理方式,部分如下:

java 复制代码
@Component
public class JdbcWzkAccountDaoImpl implements WzkAccountDao {

    @Autowired
    private WzkConnectionUtils wzkConnectionUtils;

//    public void setWzkConnectionUtils(WzkConnectionUtils wzkConnectionUtils) {
//        this.wzkConnectionUtils = wzkConnectionUtils;
//    }

对应截图如下所示:

WzkTransferServiceImpl

java 复制代码
@Component
public class WzkTransferServiceImpl implements WzkTransferService {

    @Autowired
    private WzkAccountDao wzkAccountDao;

对应的就截图如下所示:

WzkServlet(重要!!!)

这里需要注意,按理来说,我们应该在 WzkServlet 上也写 Compont 和 Autowired 来注入我们的 WzkTransferService,但是实际上呢,Component 和 Servlet 注解是冲突的。

  • WebServlet 是 Servlet 的注解,交由给 Tomcat 管理。
  • Component 是 Spring 的注解,交由给 Spring 管理。

此时要求我们不能在这里使用 Component注解,我们需要用 WebApplicationContext 来进行处理:

java 复制代码
@WebServlet(name="wzkServlet", urlPatterns = "/wzkServlet")
public class WzkServlet extends HttpServlet {

    private WzkTransferService wzkTransferService;

    @Override
    public void init() throws ServletException {
        ApplicationContext context = WebApplicationContextUtils
                .getWebApplicationContext(getServletContext());
        this.wzkTransferService = context.getBean(WzkTransferService.class);

    }

    @Override
    protected void doGet(javax.servlet.http.HttpServletRequest req, javax.servlet.http.HttpServletResponse resp) throws javax.servlet.ServletException, IOException {
        try {
            wzkTransferService.transfer("1", "2", 100);
        } catch (Exception e) {
            e.printStackTrace();
            System.out.println("=== transfer error ====");
        }
        resp.setContentType("application/json;charset=utf-8");
        resp.getWriter().print("=== WzkServlet doGet ===");
    }

}

对应的截图如下所示:

工具类

比如用到的一些工具,我们有依赖关系,所以也交给 Spring 进行管理,这里就不一一写了,大家用到了自己注入即可。

java 复制代码
@Component
public class WzkConnectionUtils {

    private final ThreadLocal<Connection> threadLocal = new ThreadLocal<>();

对应的截图如下:

相关推荐
TT哇6 分钟前
*【每日一题 基础题】 [蓝桥杯 2024 省 B] 好数
java·蓝桥杯
小张认为的测试14 分钟前
如何更改 maven 指定的 java 版本 set JAVA_HOME=C:\Program Files\Java\jdk1.8
java·开发语言·maven
阿哈8315 分钟前
240004基于ssm+maven+mysql+Java的房屋租赁系统的设计与实现
java·mysql·maven
杨荧20 分钟前
【开源免费】基于Vue和SpringBoot的靓车汽车销售网站(附论文)
java·前端·javascript·vue.js·spring boot·spring cloud·开源
龙少954321 分钟前
【深入理解Maven】
java·maven
新加坡内哥谈技术32 分钟前
OpenAI 第七日 推出了一项新功能——ChatGPT的“Projects”
大数据·人工智能·语言模型·自然语言处理·chatgpt
ThetaarSofVenice41 分钟前
【Spring框架 三】
java·后端·spring
Starshime1 小时前
【Java】网络套接字
java·开发语言·网络
等什么君!1 小时前
学习反射(反射的使用,反射的应用场景)
java·开发语言·学习
TT哇1 小时前
练习题 逆波兰表达式求值
java·开发语言