死磕面试系列。
标签:【初级】【Spring】
在我们平常的编码中,如果你使用Spring,会发现大量以Aware结尾的类。它们有什么规律么?面试官想从中获取些什么?
#1. 问
spring中,以 Aware结尾的类,都是干什么用的?能举例说明么?
#2. 解析
题目用于考察面试者的基础编码能力和总结能力。本题目属于初级定位,因为ApplicationContextAware的使用频率很高,使用Spring就一定会遇到。
#3. 答
Aware就是感知的意思,一般以该单词结尾的类,都实现了Aware接口, Aware 的目的是为了让bean获取spring容器的服务。具体回调方法由子类实现,比如ApplicationContextAware。
#4. 扩展
要搞明白这个问题,我们只需要了解Spring的Bean生命周期就可以了。
Bean生命周期分为初始化和销毁两个部分。当然,在每一个部分,都可以做一些Hook,比如常用的InitializingBean
,DisposableBean
等。当然,Aware也不例外。
spring 提供的aware的接口:
1)BeanNameAware
:可以获取容器中bean的名称
void setBeanName(String name);
复制代码
2)BeanFactoryAware
: 获取当前bean factory这也可以调用容器的服务
void setBeanFactory(BeanFactory beanFactory)
throws BeansException;
复制代码
3)ApplicationContextAware
: 当前的applicationContext, 这也可以调用容器的服务
void setApplicationContext(ApplicationContext applicationContext)
throws BeansException;
复制代码
4) MessageSourceAware
:获得message source,这也可以获得文本信息
void setMessageSource(MessageSource messageSource);
复制代码
5)ResourceLoaderAware
: 获得资源加载器,可以获得外部资源文件的内容
void setResourceLoader(ResourceLoader resourceLoader);
复制代码
还有很多,不一一列举。最常用的就是ApplicationContextAware,几乎每个项目都有一个。
ApplicationContextAware可以获取到spring的上下文,再由此获得相关的bean,这也是获取注入bean的一种方法,在某些无法autowired的情况下使用。
这会打乱Spring的注入体系,应该有限度使用。
典型代码如下:
@Component
public class SpringContextUtil implements ApplicationContextAware {
private static ApplicationContext applicationContext = null;
@Override
public void setApplicationContext(ApplicationContext ctx) throws BeansException {
applicationContext = ctx;
}
public static ApplicationContext getApplicationContext() {
return applicationContext;
}
public static <T> T getBean(Class<T> cls) {
return applicationContext.getBean(cls);
}
}
复制代码
这里使用静态字段注入,用的时候难受,就好像如鲠在喉似的。
这么常用的一个工具类,为什么Spring不默认提供一个呢?而要开发者都搞这样一个又脏又臭的类?
Spring还真的默认提供了一个,不过必须是web项目,使用下面的代码即可获取Context。
org.springframework.web.context.WebApplicationContext
.getCurrentWebApplicationContext();
复制代码
扯远了。平常的编码中还是要注意这些命名上的规律。