zoukankan      html  css  js  c++  java
  • Spring/Spring-Boot 学习 Bean注入的方式

    背景

    我们谈到Spring的时候一定会提到IOC容器DI依赖注入。Spring通过将一个个类标注为Bean的方法注入到IOC容器中,这样可以避免我们手动去将bean构造出来,而是在有需要的时候由IOC容器为我们提供它“制造”好的bean, 从而达到了控制反转的效果。
    既然要让Spring来帮我们完成bean的注入,我们就需要通过一定的方法让Spring知道我们需要它为我们管理哪些bean。一般来说有两种种方法来配置spring注入:xml文件配置、注解

    xml文件注入

    这是最原始的注入方法,在Spring的配置文件 appilcationContext.xml 中用<bean>标签一个一个注入:

    <bean id="student" class="com.autowiredtest.entity.Student">
        <property name="name" value="小红"/>
    </bean>
    

    启动项目的时候,使用ClassPathXmlApplicationContext 去装载这个xml文件,spring 容器就会自动的为我们管理这些bean的生命周期。
    但当项目较大的时候,会有成千上百个Bean要去注入,一行行去写就太麻烦了。于是Spring为我们提供了用注解来实现注入的方法。

    使用注解注入

    要启用注解,需要在配置文件中开启:

        <!-- 自动扫描 -->
        <context:annotation-config />
        <context:component-scan base-package="com.autowiredtest">
        </context:component-scan>
    

    这个配置告诉spring去自动扫描并处理com.autowiredtest包下的所有注解
    具体来说,有多种注解的方法都可以实现注入。

    配置类+@Bean注解

    假设我们的bean的定义如下:

    public class Student {
        private String name;
        //setter & getter
    }
    

    这种方式其实是对xml文件配置bean的一种映射。首先我们需要专门写一个配置类,这个配置类就对应上一种方法的xml文件。上一种方法用xml文件指示Spring如何装配bean, 这种方法用java代码(配置类)来指示Spring如何装配。
    首先我们需要写一个配置类, 并为它打上@configuration注解,这个配置类就对应上一种方法的xml文件:

    @Configuration
    public class StudentConfiguration {
    }
    

    然后我们可以在配置类中写入生成bean的方法, 并为这些方法打上@Bean注解。这些方法就对应上一种方法xml文件中一行行<bean>配置:

    @Configuration
    public class StudentConfiguration {
        @Bean
        Student student01(){
            Student student = new Student();
            student.setName("long");
            return student;
        }
    
        @Bean
        Student student02(){
            Student student = new Student();
            student.setName("xing");
            return student;
        }
    }
    

    这里面的student01和student02方法就是告诉Spring容器去生成两个Student类型的bean,生成的bean的名称由方法名称决定。上面两个方法生成的bean在IOC容器的实例的名称分别为student01和student02。知道了名称之后方便我们去使用它,如@Resource注解默认就是按照bean的名称去IOC容器中找实例。
    配置类处理好了,接下来就是使用了。使用很简单,在有需要这些bean的地方,打上@Autowired或者 @Resource注解即可。这里有关于@Autowired@Resource的区别

    @Controller
    public class AutowiredController {
        @Autowired
        Student student01; //有了@Autowired注解,Spring容器会自动在这个地方注入student01的实例,无需为它额外赋值或者创建实例。
        @Autowired
        Student student02;
    
        @RequestMapping("/good")
        @ResponseBody
        public String say(){
            String answer = "ok";
            System.out.println(student01.getName());
            System.out.println(student02.getName());
            return answer+" " + student01.getName()+" "+student02.getName();
        }
    }
    

    这样当项目启动起来,我们用浏览器访问 localhost:8080/good, 就会得到如下结果:
    res1

    @Component注解注入

    不需要写额外的配置类,在定义类的时候,只要给这个类加上@Component注解,Spring容器就可以为我们自动的去管理这个类的实例化。像下面的这样,我们定义SchoolComponent类的时候加上了@Component注解,后面我们需要SchoolComponent实例的时候,使用@Autowired或者@Resource就可以把它召唤出来啦!

    @Component
    @Data
    public class SchoolComponent {
        @Autowired //此处是沿用了之前的Student类的注解设置,直接让Spring框架注入student01。
        private Student student01;
    }
    

    测试类,注意我们并没有在配置类中为SchoolComponent类写用@Bean标注的配置函数哦。

    @Controller
    public class AutowiredController {
        @Autowired
        SchoolComponent schoolComponent;
    
        @RequestMapping("/good")
        @ResponseBody
        public String say(){
            String answer = "ok";
            return answer+" " + schoolComponent.getStudent01().getName();
        }
    }
    

    测试结果,我们仍然能为schoolComponent注入实例:

    这种方法实例化的时候,除了用上述的@Autowired注解注入属性外,还可以通过设置该类的setter方法或者 写该类的构造方法来为该类的实例提供属性的设置。
    也就是说,下面三种方法为SchoolComponent的实例化提供属性设置的效果是一样的:

    @Component
    @Data
    public class SchoolComponent {
        /*下面三种方法是等效的*/
    
        //通过@Autowired属性注入
        @Autowired
        private Student student01;
    
        //通过构造函数设置属性
        @Autowired
        public SchoolComponent(Student student01){
          this.student01 = student01; 
        }
        
        //通过set方法设置属性
        @Autowired
        public void setStudent(Student student01){
            this.student01 = student01;
        }
    }
    

    需要注意的是我们在使用构造函数或者setter方法设置属性的时候,仍然需要在在这两个方法上打上@Autowired注解,这是在让方法的入参自动注入。

    另外我们常见的 @Controller注解, @Service注解,@Repository注解, 都是Component的细化注解,这几个注解也能像上面@Component注解这样使用,只不过他们有着更细分的使用场景。

    • @Controller 标注在Controller层
    • @Service 标注在Service层
    • @Repository 标注在dao层

    参考文章 : Spring注入Bean的几种方式

  • 相关阅读:
    5. 字符串提取
    4.字符串连接
    3. 忽略大小写的字符串比较
    2.Calendar类的使用
    1.==和equals()
    50.使用DOM4J解析XML文件
    C# json提取多层嵌套到数组
    打开SDK Manager检查Android SDK下载和更新失败的解决方法
    (微信API接口开发) 使用HttpWebRequest进行请求时发生错误:基础连接已关闭,发送时发生错误处理
    javascript里面的数组,json对象,动态添加,修改,删除示例
  • 原文地址:https://www.cnblogs.com/greatLong/p/11907553.html
Copyright © 2011-2022 走看看