Spring学习--通过注解配置 Bean (三)
2017-03-03 15:17
453 查看
组件装配:
<context:component-sacan> 元素还会自动注册 AutowiredAnnotationBeanPostProcesser 实例 , 该实例可以自动装配具有 @Autowired 和 @Resource 、 @Inject 注解的属性。
使用 @Autowired 自动装配 Bean:
@Autowired 注解自动装配具有兼容类型的单个 Bean 属性:
构造器 , 普通字段(即使是非 public) , 一切具有参数的方法都可以用 @Autowired 注解。
默认情况下 , 所有使用 @Autowired 注解的属性都需要被设置。当 Spring 找不到匹配的 bean 装配属性时 , 会抛出异常 , 若某一属性允许不被设置 , 可以设置 @Autowired 注解的 required 属性为 false。
默认情况下 , 当 IOC 容器里存在多个类型兼容的 bean 时 , 通过类型的自动装配将无法工作 , 此时可以在 @Qualifier 注解里提供 bean 的名称。Spring 允许对方法的入参标注 @Qualifiter 已指定注入 bean 的名称。或在需要自动装配的注解中通过 value 属性值标识组件的名称。
@Autowired 注解也可以应用在数组类型的属性上 , 此时 Spring 将会把所有匹配的 bean 进行自动装配。
@Autowired 注解也可以应用在集合属性上 , 此时 Spring 读取该集合的类型信息 , 然后自动装配所有与之兼容的 bean。
@Autowired 注解用在 java.util.Map 上时 , 若该 Map 的键值为 String , 那么 Spring 将自动装配与之 Map 值类型兼容的 bean , 此时 bean 的名称作为键值。
控制台输出:
原因:IOC 容器中虽然每个 bean 节点都存在 , 但是没有引入到需要引入的 bean 节点中 , 需要将需要引入的 bean 节点引入相应的 bean 节点中。
控制台输出:
假如我们将 IOC 容器中不存在的 bean 节点引入到 bean 节点中 , 会出现什么状况呢?
控制台输出:
解决方法:
控制台输出:
使用 @Resource 或 @Inject 自动装配 Bean:
Spring 还支持 @Resource 和 @Inject 注解 , 这两个注解和 @Autowired 注解的功能类似。
@Resource 注解要求提供一个 bean 名称的属性 , 若该属性为空 , 则自动采用标注出的变量或方法名作为 bean 的名称。
@Inject 和 @Autowired 注解一样也是按类型匹配注入的 bean , 但没有 required 属性。
建议使用 @Autowired 注解。
<context:component-sacan> 元素还会自动注册 AutowiredAnnotationBeanPostProcesser 实例 , 该实例可以自动装配具有 @Autowired 和 @Resource 、 @Inject 注解的属性。
使用 @Autowired 自动装配 Bean:
@Autowired 注解自动装配具有兼容类型的单个 Bean 属性:
构造器 , 普通字段(即使是非 public) , 一切具有参数的方法都可以用 @Autowired 注解。
默认情况下 , 所有使用 @Autowired 注解的属性都需要被设置。当 Spring 找不到匹配的 bean 装配属性时 , 会抛出异常 , 若某一属性允许不被设置 , 可以设置 @Autowired 注解的 required 属性为 false。
默认情况下 , 当 IOC 容器里存在多个类型兼容的 bean 时 , 通过类型的自动装配将无法工作 , 此时可以在 @Qualifier 注解里提供 bean 的名称。Spring 允许对方法的入参标注 @Qualifiter 已指定注入 bean 的名称。或在需要自动装配的注解中通过 value 属性值标识组件的名称。
@Autowired 注解也可以应用在数组类型的属性上 , 此时 Spring 将会把所有匹配的 bean 进行自动装配。
@Autowired 注解也可以应用在集合属性上 , 此时 Spring 读取该集合的类型信息 , 然后自动装配所有与之兼容的 bean。
@Autowired 注解用在 java.util.Map 上时 , 若该 Map 的键值为 String , 那么 Spring 将自动装配与之 Map 值类型兼容的 bean , 此时 bean 的名称作为键值。
<?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" 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"> <!-- 指定 Spring IOC 容器扫描的包 --> <context:component-scan base-package="com.itdjx.spring.annotation"/> </beans>
package com.itdjx.spring.annotation.controller; import com.itdjx.spring.annotation.service.UserService; import org.springframework.stereotype.Controller; /** * @author Wáng Chéng Dá * @create 2017-03-03 9:28 */ @Controller public class UserController { private UserService userService; public void execute() { System.out.println("I am UserController's execute method..."); userService.add(); } }
package com.itdjx.spring.annotation.service; import com.itdjx.spring.annotation.repository.UserRepository; import org.springframework.stereotype.Service; /** * @author Wáng Chéng Dá * @create 2017-03-03 9:26 */ @Service public class UserService { private UserRepository userRepository; public void add() { System.out.println("I am UserService's add method..."); userRepository.sava(); } }
package com.itdjx.spring.annotation.repository; /** * @author Wáng Chéng Dá * @create 2017-03-03 9:23 */ public interface UserRepository { void sava(); }
package com.itdjx.spring.annotation.repository; import org.springframework.stereotype.Repository; /** * @author Wáng Chéng Dá * @create 2017-03-03 9:24 */ @Repository("userRepository") public class UserRepositoryImpl implements UserRepository { @Override public void sava() { System.out.println("I am UserRepositoryImpl's sava method..."); } }
package com.itdjx.spring.annotation; import com.itdjx.spring.annotation.controller.UserController; import org.springframework.context.ApplicationContext; import org.springframework.context.support.ClassPathXmlApplicationContext; /** * @author Wáng Chéng Dá * @create 2017-03-03 9:34 */ public class Main { public static void main(String[] args) { ApplicationContext cxt = new ClassPathXmlApplicationContext("beans-annotation.xml"); UserController userController = (UserController) cxt.getBean("userController"); userController.execute(); } }
控制台输出:
Exception in thread "main" java.lang.NullPointerException at com.itdjx.spring.annotation.controller.UserController.execute(UserController.java:16) at com.itdjx.spring.annotation.Main.main(Main.java:17) |
package com.itdjx.spring.annotation.controller; import com.itdjx.spring.annotation.service.UserService; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Controller; /** * @author Wáng Chéng Dá * @create 2017-03-03 9:28 */ @Controller public class UserController { @Autowired private UserService userService; public void execute() { System.out.println("I am UserController's execute method..."); userService.add(); } }
package com.itdjx.spring.annotation.service; import com.itdjx.spring.annotation.repository.UserRepository; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; /** * @author Wáng Chéng Dá * @create 2017-03-03 9:26 */ @Service public class UserService { @Autowired private UserRepository userRepository; public void add() { System.out.println("I am UserService's add method..."); userRepository.sava(); } }
控制台输出:
I am UserController's execute method... I am UserService's add method... I am UserRepositoryImpl's sava method... |
package com.itdjx.spring.annotation; /** * @author Wáng Chéng Dá * @create 2017-03-03 8:44 */ public class TestObject { }
package com.itdjx.spring.annotation.repository; import com.itdjx.spring.annotation.TestObject; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Repository; /** * @author Wáng Chéng Dá * @create 2017-03-03 9:24 */ @Repository("userRepository") public class UserRepositoryImpl implements UserRepository { @Autowired private TestObject testObject; @Override public void sava() { System.out.println("I am UserRepositoryImpl's sava method..."); System.out.println(testObject); } }
控制台输出:
警告: Exception encountered during context initialization - cancelling refresh attempt: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'userController': Unsatisfied dependency expressed through field 'userService'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'userService': Unsatisfied dependency expressed through field 'userRepository'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'userRepository': Unsatisfied dependency expressed through field 'testObject'; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'com.itdjx.spring.annotation.TestObject' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)} Exception in thread "main" org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'userController': Unsatisfied dependency expressed through field 'userService'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'userService': Unsatisfied dependency expressed through field 'userRepository'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'userRepository': Unsatisfied dependency expressed through field 'testObject'; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'com.itdjx.spring.annotation.TestObject' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)} at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:588) at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:88) at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:366) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1264) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:553) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:483) at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306) at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302) at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:197) at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:761) at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:866) at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:542) at org.springframework.context.support.ClassPathXmlApplicationContext.<init>(ClassPathXmlApplicationContext.java:139) at org.springframework.context.support.ClassPathXmlApplicationContext.<init>(ClassPathXmlApplicationContext.java:83) at com.itdjx.spring.annotation.Main.main(Main.java:15) Caused by: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'userService': Unsatisfied dependency expressed through field 'userRepository'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'userRepository': Unsatisfied dependency expressed through field 'testObject'; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'com.itdjx.spring.annotation.TestObject' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)} at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:588) at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:88) at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:366) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1264) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:553) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:483) at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306) at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302) at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:202) at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:208) at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1138) at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1066) at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:585) ... 15 more Caused by: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'userRepository': Unsatisfied dependency expressed through field 'testObject'; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'com.itdjx.spring.annotation.TestObject' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)} at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:588) at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:88) at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:366) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1264) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:553) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:483) at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306) at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302) at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:202) at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:208) at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1138) at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1066) at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:585) ... 28 more Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'com.itdjx.spring.annotation.TestObject' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)} at org.springframework.beans.factory.support.DefaultListableBeanFactory.raiseNoMatchingBeanFound(DefaultListableBeanFactory.java:1486) at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1104) at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1066) at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:585) ... 41 more |
package com.itdjx.spring.annotation.repository; import com.itdjx.spring.annotation.TestObject; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Repository; /** * @author Wáng Chéng Dá * @create 2017-03-03 9:24 */ @Repository("userRepository") public class UserRepositoryImpl implements UserRepository { @Autowired(required = false) private TestObject testObject; @Override public void sava() { System.out.println("I am UserRepositoryImpl's sava method..."); System.out.println(testObject); } }
控制台输出:
I am UserController's execute method... I am UserService's add method... I am UserRepositoryImpl's sava method... null |
Spring 还支持 @Resource 和 @Inject 注解 , 这两个注解和 @Autowired 注解的功能类似。
@Resource 注解要求提供一个 bean 名称的属性 , 若该属性为空 , 则自动采用标注出的变量或方法名作为 bean 的名称。
@Inject 和 @Autowired 注解一样也是按类型匹配注入的 bean , 但没有 required 属性。
建议使用 @Autowired 注解。
相关文章推荐
- Spring学习笔记三: 通过注解配置Bean
- spring学习十一 通过注解配置bean
- Spring学习笔记之通过注解配置Bean(1)
- Spring学习笔记之通过注解配置Bean
- Spring4学习笔记-通过注解配置bean
- spring学习笔记----通过注解配置Bean(2)
- Spring学习--通过注解配置 Bean (一)
- spring学习笔记----通过注解配置Bean(1)
- Spring4学习笔记-通过注解配置bean
- Spring学习--通过注解配置 Bean (二)
- Spring学习笔记之通过注解配置Bean(2)
- Spring学习笔记三: 通过注解配置Bean
- spring学习小结9—通过注解来配置bean
- Spring学习(14)--- 基于Java类的配置Bean 之 @ImportResource & @Value 注解
- Spring学习第十一天:通过工厂方式配置Bean
- Spring学习记录(九)---通过工厂方法配置bean
- Spring_通过注解配置 Bean(2)
- Spring学习(二十二) Bean配置的三种方式(XML、注解、Java类)介绍与对比
- Spring零配置通过注解实现Bean依赖注入总结<转>
- Spring学习笔记----注解方式配置bean