Spring DI与CDI';注射点在哪里?
我想创建一个Spring的bean producer方法,它知道是谁调用了它,因此我从以下代码开始:Spring DI与CDI';注射点在哪里?,spring,dependency-injection,java-ee-6,cdi,producer,Spring,Dependency Injection,Java Ee 6,Cdi,Producer,我想创建一个Spring的bean producer方法,它知道是谁调用了它,因此我从以下代码开始: @Configuration public class LoggerProvider { @Bean @Scope("prototype") public Logger produceLogger() { // get known WHAT bean/component invoked this producer Class<?&
@Configuration
public class LoggerProvider {
@Bean
@Scope("prototype")
public Logger produceLogger() {
// get known WHAT bean/component invoked this producer
Class<?> clazz = ...
return LoggerFactory.getLogger(clazz);
}
}
@配置
公共类日志提供程序{
@豆子
@范围(“原型”)
公共记录器produceLogger(){
//了解哪个bean/组件调用了这个生产者
类clazz=。。。
返回LoggerFactory.getLogger(clazz);
}
}
我如何获得信息谁想要注射豆子
我正在寻找一些与Spring世界中的类似概念。据我所知,Spring没有这样的概念 那么,唯一知道被处理点的是一个
例如:
@Target(PARAMETER)
@Retention(RUNTIME)
@Documented
public @interface Logger {}
public class LoggerInjectBeanPostProcessor implements BeanPostProcessor {
public Logger produceLogger() {
// get known WHAT bean/component invoked this producer
Class<?> clazz = ...
return LoggerFactory.getLogger(clazz);
}
@Override
public Object postProcessBeforeInitialization(final Object bean,
final String beanName) throws BeansException {
return bean;
}
@Override
public Object postProcessAfterInitialization(final Object bean,
final String beanName) throws BeansException {
ReflectionUtils.doWithFields(bean.getClass(),
new FieldCallback() {
@Override
public void doWith(final Field field) throws IllegalArgumentException, IllegalAccessException {
field.set(bean, produceLogger());
}
},
new ReflectionUtils.FieldFilter() {
@Override
public boolean matches(final Field field) {
return field.getAnnotation(Logger.class) != null;
}
});
return bean;
}
}
@Target(参数)
@保留(运行时)
@记录
public@interface Logger{}
公共类LoggerInjectBeanPostProcessor实现BeanPostProcessor{
公共记录器produceLogger(){
//了解哪个bean/组件调用了这个生产者
类clazz=。。。
返回LoggerFactory.getLogger(clazz);
}
@凌驾
初始化之前的公共对象后处理(最终对象bean,
最后一个字符串(beanName)抛出BeanException{
返回豆;
}
@凌驾
公共对象后处理后初始化(最终对象bean,
最后一个字符串(beanName)抛出BeanException{
ReflectionUtils.doWithFields(bean.getClass(),
新字段回调(){
@凌驾
public void doWith(最终字段)抛出IllegalArgumentException、IllegalAccessException{
set(bean,produceLogger());
}
},
新的ReflectionUtils.FieldFilter(){
@凌驾
公共布尔匹配(最终字段){
返回字段.getAnnotation(Logger.class)!=null;
}
});
返回豆;
}
}
Spring 4.3.0为bean生成方法启用和依赖描述符参数:
@Configuration
public class LoggerProvider {
@Bean
@Scope("prototype")
public Logger produceLogger(InjectionPoint injectionPoint) {
Class<?> clazz = injectionPoint.getMember().getDeclaringClass();
return LoggerFactory.getLogger(clazz);
}
}
@配置
公共类日志提供程序{
@豆子
@范围(“原型”)
公共记录器produceLogger(注入点注入点){
类clazz=injectionPoint.getMember().getDeclaringClass();
返回LoggerFactory.getLogger(clazz);
}
}
顺便说一下,链接到哪个链接到这个问题。谢谢拉尔夫!好的,所以只要在任何地方注入任何bean,就会调用这个
BeanPostProcessor
。有没有办法让我知道注射的是什么豆子?我的意思是,我得到:postProcessBeforeInitialization(objectbean,stringbeanname)
其中bean
是一个希望进行注入的bean(我在问题中问的who部分),而beanName
是bean
名称。现在我不知道bean
中的哪个字段希望进行注入-换句话说,我不知道注入的bean是LoggerProvider
还是其他什么。据我所知,在创建bean后会调用后处理器!(不在任何地方注射)。我们的想法是在bean后处理器之上实现您自己的小型注入框架。好的,所以每当创建bean时,都会调用beanpstoprocessor
实现器。因此,您的想法是在初始化之前实施后处理
,例如,扫描具有我的自定义注释的字段(比如@Logger
),并通过反射,使用我自己的自定义逻辑初始化此类字段。这是你的方法还是我把事情弄得太复杂了?再次感谢@皮奥特·诺维斯基:是的,但这真的很容易,而且工作量也不多。请参见我添加的示例。(我还没有测试过该代码,但它应该会给你一个好主意,扩展Spring有多容易,Spring utils有多强大。)如果我将其注入另一个bean(也适用于prototype),那么这不会为该bean的每个实例创建一个日志程序吗,而不是共享一个静态实例?@RupertMadden-Abbott日志框架通常会缓存记录器。例如,请参见关于SLF4J日志框架的以下问题: