Multithreading SpelExpression线程安全吗?
具体来说,getValue(StandardEvaluationContext,Class)是否可以从同一SpelExpression上具有不同上下文的多个线程安全地调用 我看到Spring Source的Gary Russell提出并回答了这个问题。但是,我也看到有人报告并发性问题。我浏览了相关Spring类的源代码,我不能确定 我想从与Spring el合作过的Spring开发人员或在高度并发环境中使用过此类的Spring用户那里得到一个明确的答案Multithreading SpelExpression线程安全吗?,multithreading,spring,spring-el,Multithreading,Spring,Spring El,具体来说,getValue(StandardEvaluationContext,Class)是否可以从同一SpelExpression上具有不同上下文的多个线程安全地调用 我看到Spring Source的Gary Russell提出并回答了这个问题。但是,我也看到有人报告并发性问题。我浏览了相关Spring类的源代码,我不能确定 我想从与Spring el合作过的Spring开发人员或在高度并发环境中使用过此类的Spring用户那里得到一个明确的答案 谢谢。我知道您需要另一种意见,但我会澄清,
谢谢。我知道您需要另一种意见,但我会澄清,只要您在另一个线程使用评估上下文时不改变它,它是线程安全的(或者您每次都使用一个新的评估上下文,如果您需要使用变量等对其进行自定义) 但是,您必须将根对象传递到getValue()中,而不是在上下文中设置根对象(使用
setRootObject()
——这将改变上下文)。如果您有#root
对象,请使用
getValue(EvaluationContext context, Object rootObject, Class<T> expectedResultType)
getValue(EvaluationContext上下文、对象rootObject、类expectedResultType)
如果您没有根对象,并且没有改变上下文,那么可以使用
getValue(EvaluationContext context, Class<T> expectedResultType)
getValue(EvaluationContext上下文,类expectedResultType)
具有共享上下文
SpringIntegration在(在许多情况下)高度多线程环境中广泛使用SpEL。我们对所有静态情况使用相同的计算上下文(没有运行时变量),并将根对象(通常是消息)传递到
getValue()
调用中。对于需要向上下文添加变量的情况,每次评估都会获得一个新的评估上下文。Gary,感谢您的保证。这就是我们正在做的私有表达式exp=new-SpelExpressionParser().parseExpression(“#msg['direction']=='BUY'”)//希望上面的表达式是线程安全的,正如下面的方法所使用的那样。//公共布尔传递(映射消息){StandardEvaluationContext=new StandardEvaluationContext();context.setVariable(“msg”,message);返回exp.getValue(context,boolean.class);}是的,这很好,因为每次都创建一个新的计算上下文。但是,由于您只有一个变量msg
,因此可以使用共享上下文并使用['direction']='BUY'
(其中msg
是#root
对象。getValue(context,msg,Boolean.class)
。谢谢你,Gary。我从你那里学到了很多。我现在缓存EvaluationContext和表达式,并使用exp.getValue(context,msg,Boolean.class)。