Spring注解系列——@Configuration&@Bean给容器中注册组件

最近在研究springBoot,发现好多注解都有点陌生,重新温习一遍spring注解。废话不多说,让我们直接上代码吧。

按照spring2.5以前的版本,要将组件注册到spring容器中,需要配置spring的配置文件(applicationContext.xml),如下

<?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:mvc="http://www.springframework.org/schema/mvc"
    xsi:schemaLocation="
        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.xsd
        http://www.springframework.org/schema/mvc
        http://www.springframework.org/schema/mvc/spring-mvc.xsd">

    <context:annotation-config />

    <context:component-scan base-package="cn.cisol.mvcdemo">
        <context:exclude-filter type="annotation"
            expression="org.springframework.stereotype.Controller" />
    </context:component-scan>

    <bean id="student" class="com.sht.entity.Student">
        <property name="name" value="张三"/>
        <property name="age" value="30"/>
    </bean>
</beans>

并在spring配置文件中注册bean。本代码利用spring5作为演示,完全通过注解的方式来配置spring。

1.首先,新建一个maven工程(好处相信不用我介绍),引用spring-context包。

<?xml version="1.0" encoding="UTF-8"?>

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  <modelVersion>4.0.0</modelVersion>

  <groupId>com.sht</groupId>
  <artifactId>SpringAnnotation</artifactId>
  <version>1.0-SNAPSHOT</version>
  ………………此处省略不需要的代码

  <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.10.RELEASE</version>
    </dependency>
  </dependencies>

  ………………此处省略不需要的代码
</project>

2.新建一个类,作为配置类

package com.sht.configuration;

import com.sht.entity.Student;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

/**
 * 配置类,替代spring的配置文件applicationContext.xml
 * 在类上添加@Configuration
 */
@Configuration
public class MainConfiguration1 {

    /**
     * 替代配置文件中声明的组件bean
     * <bean id="student" class="com.sht.entity.Student">……</bean>
     * 默认方法名为id
     * @return
     */
    @Bean
    public Student student(){
        return new Student();
    }
}
package com.sht.entity;

/**
 * 实体类,学生
 */
public class Student {

    /** 姓名 */
    private String name;

    /** 年龄 */
    private Integer age;

    public Student() {
    }

    public Student(String name, Integer age) {
        this.name = name;
        this.age = age;
    }

    ……此处省略set和get方法
}

3.测试类

package com.sht.test;

import com.sht.configuration.MainConfiguration1;
import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;

/**
 * 测试类
 */
public class MainTest {

    //创建spring容器(基于注解方式创建),参数为配置类
    ApplicationContext context = new AnnotationConfigApplicationContext(MainConfiguration1.class);

    @Test
    public void test1(){
        //获取spring容器中的组件
        String[] beanDefinitionNames = context.getBeanDefinitionNames();
        for(String bean : beanDefinitionNames){
            System.out.println(bean);
        }
    }
}

4.结果

"C:\Program Files\Java\jdk1.8.0_121\bin\java.exe" -ea -Didea.test.cyclic.buffer.size=1048576 "-javaagent:D:\Program Files\JetBrains\IntelliJ IDEA 2018.1.3\lib\idea_rt.jar=3681:D:\Program Files\JetBrains\IntelliJ IDEA 2018.1.3\bin" -Dfile.encoding=UTF-8 -classpath "D:\Program Files\JetBrains\IntelliJ IDEA 2018.1.3\lib\idea_rt.jar;D:\Program Files\JetBrains\IntelliJ IDEA 2018.1.3\plugins\junit\lib\junit-rt.jar;D:\Program Files\JetBrains\IntelliJ IDEA 2018.1.3\plugins\junit\lib\junit5-rt.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\charsets.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\deploy.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\ext\access-bridge-64.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\ext\cldrdata.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\ext\dnsns.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\ext\jaccess.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\ext\jfxrt.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\ext\localedata.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\ext\nashorn.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\ext\sunec.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\ext\sunjce_provider.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\ext\sunmscapi.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\ext\sunpkcs11.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\ext\zipfs.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\javaws.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\jce.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\jfr.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\jfxswt.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\jsse.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\management-agent.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\plugin.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\resources.jar;C:\Program Files\Java\jdk1.8.0_121\jre\lib\rt.jar;D:\git\SpringAnnotation\target\test-classes;D:\git\SpringAnnotation\target\classes;D:\maven\repository\junit\junit\4.12\junit-4.12.jar;D:\maven\repository\org\hamcrest\hamcrest-core\1.3\hamcrest-core-1.3.jar;D:\maven\repository\org\springframework\spring-context\5.0.10.RELEASE\spring-context-5.0.10.RELEASE.jar;D:\maven\repository\org\springframework\spring-aop\5.0.10.RELEASE\spring-aop-5.0.10.RELEASE.jar;D:\maven\repository\org\springframework\spring-beans\5.0.10.RELEASE\spring-beans-5.0.10.RELEASE.jar;D:\maven\repository\org\springframework\spring-core\5.0.10.RELEASE\spring-core-5.0.10.RELEASE.jar;D:\maven\repository\org\springframework\spring-jcl\5.0.10.RELEASE\spring-jcl-5.0.10.RELEASE.jar;D:\maven\repository\org\springframework\spring-expression\5.0.10.RELEASE\spring-expression-5.0.10.RELEASE.jar" com.intellij.rt.execution.junit.JUnitStarter -ideVersion5 -junit4 com.sht.test.MainTest,test1
十一月 09, 2018 10:58:07 下午 org.springframework.context.support.AbstractApplicationContext prepareRefresh
信息: Refreshing org.springframework.context.annotation.AnnotationConfigApplicationContext@67f89fa3: startup date [Fri Nov 09 22:58:07 CST 2018]; root of context hierarchy
org.springframework.context.annotation.internalConfigurationAnnotationProcessor
org.springframework.context.annotation.internalAutowiredAnnotationProcessor
org.springframework.context.annotation.internalRequiredAnnotationProcessor
org.springframework.context.annotation.internalCommonAnnotationProcessor
org.springframework.context.event.internalEventListenerProcessor
org.springframework.context.event.internalEventListenerFactory
mainConfiguration1
student

Process finished with exit code 0

从结果看到,目前容器中含有8个组件,前6个为spring系统默认的,这里暂时不解释。后面有两个bean组件,分别为mainConfiguration1和student,其中student是配置类中声明的。那么mainConfiguration1是怎么来的呢?让我们来看看配置类上的@Configuration注解

* @author Rod Johnson
 * @author Chris Beams
 * @since 3.0
 * @see Bean
 * @see Profile
 * @see Import
 * @see ImportResource
 * @see ComponentScan
 * @see Lazy
 * @see PropertySource
 * @see AnnotationConfigApplicationContext
 * @see ConfigurationClassPostProcessor
 * @see org.springframework.core.env.Environment
 * @see org.springframework.test.context.ContextConfiguration
 */
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Component
public @interface Configuration {

从这里我们可以看出,@Configuration这个注解其实也是一个@Component组件,自Spring 3.0以后就存在了。在没有指定id(名称)前,spring会将此组件的类的类名(第一个字母小写)作为bean的id,注册到容器中。

那在这里有个人就会问了,当我们在spring配置文件中注册一个bean时,是可以自己取名的,这里我们如何来操作呢?

让我们来看看@Bean这个注解

Target({ElementType.METHOD, ElementType.ANNOTATION_TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Bean {

	/**
	 * Alias for {@link #name}.
	 * <p>Intended to be used when no other attributes are needed, for example:
	 * {@code @Bean("customBeanName")}.
	 * @since 4.3.3
	 * @see #name
	 */
	@AliasFor("name")
	String[] value() default {};

	/**
	 * The name of this bean, or if several names, a primary bean name plus aliases.
	 * <p>If left unspecified, the name of the bean is the name of the annotated method.
	 * If specified, the method name is ignored.
	 * <p>The bean name and aliases may also be configured via the {@link #value}
	 * attribute if no other attributes are declared.
	 * @see #value
	 */
	@AliasFor("value")
	String[] name() default {};

看到这个,我们就发现了,其实spring注解时允许我们自己来为bean取别名的。如下

@Configuration
public class MainConfiguration1 {

    /**
     * 替代配置文件中声明的组件bean
     * <bean id="student" class="com.sht.entity.Student">……</bean>
     * 默认方法名为id
     * @return
     */
    @Bean("stu")
    public Student student(){
        return new Student();
    }
}

这是Student类在spring容器中注册的别名就为stu了。我们这里就不来演示了,今天就到这了。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值