Spring中Aware的用法以及实现

Aware

在Spring当中有一些内置的对象是未开放给我们使用的,例如Spring的上下文ApplicationContext、环境属性Environment,BeanFactory等等其他的一些内置对象,而在我们可以通过实现对应的Aware接口去拿到我们想要的一些属性,一般命名都是xxxAware,在创建对象的时候, 会调用接口规定的方法注入到相关组件:Aware

常用的Aware:

用法示例:

源码解析

我们先了解什么是BeanPostProcessor,是在创建Bean之前以及创建Bean之后的一种后置处理器,这里就简单的讲一下这个,就是在我们使用的这些注解,例如:@Async (异步执行),@Bean,@Component、@Autowired、@PropertySource等等都需要经过BeanPostProcessor去处理才能加载到容器当中,

先看一个示例:

不仅仅有BeanPostProcessor还有BeanDefinitionRegistryPostProcessor(Bean注册器后置处 理器)、BeanFactoryPostProcessor(BeanFactory后置处理器),

在处理Aware实现类的时候就会有对应的一个AwareProcessor去处理,我们拿ApplicationContextAware做示例**:**

我们找到对应的后置处理器ApplicationContextAwareProcessor

因为BeanPostProcessor有两个接口实现,但是只对处理前做内置对象赋值,将对应的对象暴露给我们

复制代码
class ApplicationContextAwareProcessor implements BeanPostProcessor {

	private final ConfigurableApplicationContext applicationContext;

	private final StringValueResolver embeddedValueResolver;


	/**
	 * Create a new ApplicationContextAwareProcessor for the given context.
	 */
	public ApplicationContextAwareProcessor(ConfigurableApplicationContext applicationContext) {
		this.applicationContext = applicationContext;
		this.embeddedValueResolver = new EmbeddedValueResolver(applicationContext.getBeanFactory());
	}


	@Override
	@Nullable
	public Object postProcessBeforeInitialization(final Object bean, String beanName) throws BeansException {
		AccessControlContext acc = null;

		if (System.getSecurityManager() != null &&
				(bean instanceof EnvironmentAware || bean instanceof EmbeddedValueResolverAware ||
						bean instanceof ResourceLoaderAware || bean instanceof ApplicationEventPublisherAware ||
						bean instanceof MessageSourceAware || bean instanceof ApplicationContextAware)) {
			acc = this.applicationContext.getBeanFactory().getAccessControlContext();
		}

		if (acc != null) {
			AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
				invokeAwareInterfaces(bean);
				return null;
			}, acc);
		}
		else {
			invokeAwareInterfaces(bean);
		}

		return bean;
	}

	private void invokeAwareInterfaces(Object bean) {
		if (bean instanceof Aware) {
			if (bean instanceof EnvironmentAware) {
				((EnvironmentAware) bean).setEnvironment(this.applicationContext.getEnvironment());
			}
			if (bean instanceof EmbeddedValueResolverAware) {
				((EmbeddedValueResolverAware) bean).setEmbeddedValueResolver(this.embeddedValueResolver);
			}
			if (bean instanceof ResourceLoaderAware) {
				((ResourceLoaderAware) bean).setResourceLoader(this.applicationContext);
			}
			if (bean instanceof ApplicationEventPublisherAware) {
				((ApplicationEventPublisherAware) bean).setApplicationEventPublisher(this.applicationContext);
			}
			if (bean instanceof MessageSourceAware) {
				((MessageSourceAware) bean).setMessageSource(this.applicationContext);
			}
			if (bean instanceof ApplicationContextAware) {
				((ApplicationContextAware) bean).setApplicationContext(this.applicationContext);
			}
		}
	}

	@Override
	public Object postProcessAfterInitialization(Object bean, String beanName) {
		return bean;
	}

}

不得不说Spring的这种设计还是很厉害的,建议可以买本Spring IOC源码分析的书看看比较好,了解的更加细致

相关推荐
呆呆敲代码的小Y10 分钟前
【实战精选面试题】C# 面试题详细解答,按难易程度排序
android·java·游戏·c#·游戏开发·unity面试题·c#面试题
水无痕simon25 分钟前
3、工程重构
java·spring cloud·重构
阿里云基础软件35 分钟前
Agent 任务提速 10.71%,内存占用降低 21.60%|Alibaba Cloud Linux 4 重大发布
java·linux·人工智能·操作系统·agent
Y001 小时前
PostgreSQL 权限管理踩坑记:从 42501 到默认权限和 RLS
数据库·postgresql
呆萌很1 小时前
达梦(DM8)数据库常用SQL
数据库·sql
跟太阳说早安1 小时前
极简数据库SQL
数据库·sql
Wang's Blog1 小时前
Java 项目实战: 交友项目 - 项目:需求分析与滑动数据设计
java·开发语言·交友
前端 贾公子2 小时前
第 5 章:Codex 从可运行程序到可交付工具
java·前端·数据库
杨云龙UP2 小时前
MySQL 主从复制管理:暂停、恢复、清理主从关系及命令执行位置
运维·数据库·mysql·主从配置·主从命令·reset replica·清除复制
yzs872 小时前
openGauss branch diff能力解析
数据库·oracle