Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/spring/14.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java Spring 4.2+;:如何从@EventListener条件表达式中引用Springbean实例_Java_Spring_Spring El_Spring Bean - Fatal编程技术网

Java Spring 4.2+;:如何从@EventListener条件表达式中引用Springbean实例

Java Spring 4.2+;:如何从@EventListener条件表达式中引用Springbean实例,java,spring,spring-el,spring-bean,Java,Spring,Spring El,Spring Bean,在Spring4.2+中,我们可以使用@EventListener注释和“条件”表达式 在我的场景中,我需要将事件对象的id与在.properties文件中配置的正则表达式相匹配 然而,似乎不可能从条件的正则表达式引用任何bean的属性或方法,因为根上下文似乎就是事件对象本身 到目前为止,我有一个抽象类,它根据类名设置事件id模式属性。目标是使每个事件侦听器的实现尽可能干净和简单 @Service @PropertySource(value = "classpath:subscriberEven

在Spring4.2+中,我们可以使用@EventListener注释和“条件”表达式

在我的场景中,我需要将事件对象的id与在.properties文件中配置的正则表达式相匹配

然而,似乎不可能从条件的正则表达式引用任何bean的属性或方法,因为根上下文似乎就是事件对象本身

到目前为止,我有一个抽象类,它根据类名设置事件id模式属性。目标是使每个事件侦听器的实现尽可能干净和简单

@Service
@PropertySource(value = "classpath:subscriberEventMapping.properties")
public abstract class AbstractEventHandler implements IEventHandler {

    private String eventIdPattern;

    @Autowired
    Environment env;

    @Autowired(required = true)
    public void configureEventIdPattern() {
        String simpleClassName = this.getClass().getSimpleName();
        String resolvedEventIdPattern = env.getProperty(
            simpleClassName.substring(0,1).toLowerCase() + 
            simpleClassName.substring(1, simpleClassName.length()));
        this.eventIdPattern = resolvedEventIdPattern == null ? ".*" : resolvedEventIdPattern;
    }

    public String getEventIdPattern() {
        return eventIdPattern;
    }
}
属性文件如下所示:

regExpEventHandler=^(901|909|998|1000)$
dummyEventHandler=^([1-9][0-9]{0,2}|1000)$
然后,我有一个扩展上述抽象类的示例事件侦听器:

@Service
public class RegExpEventHandler extends AbstractEventHandler {

    @Log
    private ILog logger;

    @Override
    @EventListener(condition = "#event.eventid matches @regExpEventHandler.getEventIdPattern()")
    public void onEvent(Event event) {
        logger.debug("RegExpEventHandler processing : {} with event pattern : {}", event, getEventIdPattern());
    }
}
问题是这个表达式

“#event.eventid与@regExpEventHandler.getEventIdPattern()匹配”

无法工作,因为在@EventListener使用的上下文中找不到bean“@RegeExpEventHandler”

这里有没有访问现有Springbean的方法或属性的方法?对于这种情况,还有其他更好的方法吗

我知道我可以通过以下方式轻松访问静态常量或方法:

#event.eventid matches T(my.package.RegExpEventHandler.MY_CONSTANT)
但是不能使用@Value表达式从属性文件初始化字符串常量(静态最终值)

使用非最终静态常量可以工作,但是每个事件侦听器都需要添加boiler plate,以便使用@Value表达式从非静态变量初始化静态常量,这是我们想要避免的


提前多谢

它对我有效-我查看了
EventExpressionEvaluator
,发现它在评估上下文中添加了一个bean解析器

public EvaluationContext createEvaluationContext(ApplicationEvent event, Class<?> targetClass,
        Method method, Object[] args, BeanFactory beanFactory) {

    Method targetMethod = getTargetMethod(targetClass, method);
    EventExpressionRootObject root = new EventExpressionRootObject(event, args);
    MethodBasedEvaluationContext evaluationContext = new MethodBasedEvaluationContext(
            root, targetMethod, args, getParameterNameDiscoverer());
    if (beanFactory != null) {
        evaluationContext.setBeanResolver(new BeanFactoryResolver(beanFactory));
    }
    return evaluationContext;
}
而且效果很好

bar:org.springframework.context.PayloadApplicationEvent[...
handler:foo

(这是4.3.7版本;boot 1.5.2版本)。

为什么
regExpEventHandler
会是一个bean?这是一个属性而不是一个bean…不确定我是否遵循。。。我的理解是,在Spring EL表达式中,可以使用@引用bean。我还尝试了一些更简单的方法,比如#event.eventid匹配${regExpEventHandler},它应该从属性文件中获取相应的值,但是表达式也失败了Yes beans,但是您尝试将属性引用为不起作用的bean。啊,您正在引用自己。首先,我认为您的
@Autowired
应该是一个
@PostConstruct
。尝试其他方法,如“#event.eventid匹配$regExpEventHandler”,希望从.properties文件中获取相应的属性,会产生错误:org.springframework.expression.spel.SpelEvaluationException:EL1008E:(pos 23):在类型为“org.springframework.context.event.EventExpressionRootObject”的对象上找不到属性或字段“$regExpEventHandler”-可能不是公共的?我正在尝试类似的方法,但到目前为止没有任何效果…非常感谢Gary的帮助。。。我们正在使用Spring4.2.6,我刚刚发现在这个版本中,EventExpressionEvaluator没有bean解析器。。。所以我头疼。。。我很确定切换到4.3.7可能会解决问题。。。再次非常感谢!切换到4.3.7后工作正常。。。非常感谢!
bar:org.springframework.context.PayloadApplicationEvent[...
handler:foo