admin管理员组

文章数量:1122832

Heads up: I'm using Spring Boot 2.2.0.RELEASE, so it's not related to this.

I have a MessagingGateway as follows:

@Gateway(
            requestChannel = "myChannel",
            headers = @GatewayHeader(
                    name = "tenantId",
                    expression = "T(company.package.ContextHolder).getContext()?.tenant?.identifier"))
    void publishEvent(@Header(value = "eventType") String eventType,
                      @Payload Object payload);

My ContextHolder class is similar to SecurityContextHolder or RequestContextHolder, and I put some basic request related info in it, just like SecurityContext.

The issue is, this works perfectly on my machine, and for the most calls to the publishEvent method it does on the server, as well. However, for some methods, I get:

org.springframework.expression.spel.SpelEvaluationException: EL1005E: Type cannot be found 'company.package.ContextHolder'
        at org.springframework.expression.spel.support.StandardTypeLocator.findType(StandardTypeLocator.java:117) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.expression.spel.ExpressionState.findType(ExpressionState.java:155) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.expression.spel.ast.TypeReference.getValueInternal(TypeReference.java:69) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.expression.spel.ast.CompoundExpression.getValueRef(CompoundExpression.java:55) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.expression.spel.ast.CompoundExpression.getValueInternal(CompoundExpression.java:91) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.expression.spel.ast.SpelNodeImpl.getValue(SpelNodeImpl.java:112) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.expression.spel.standard.SpelExpression.getValue(SpelExpression.java:330) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper.evaluateHeaders(GatewayMethodInboundMessageMapper.java:213) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper.access$1000(GatewayMethodInboundMessageMapper.java:86) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper$DefaultMethodArgsMessageMapper.buildMessage(GatewayMethodInboundMessageMapper.java:434) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper$DefaultMethodArgsMessageMapper.toMessage(GatewayMethodInboundMessageMapper.java:340) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper$DefaultMethodArgsMessageMapper.toMessage(GatewayMethodInboundMessageMapper.java:288) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper.mapArgumentsToMessage(GatewayMethodInboundMessageMapper.java:198) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper.toMessage(GatewayMethodInboundMessageMapper.java:192) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper.toMessage(GatewayMethodInboundMessageMapper.java:86) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.support.converter.SimpleMessageConverter.toMessage(SimpleMessageConverter.java:111) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.messaging.core.AbstractMessageSendingTemplate.doConvert(AbstractMessageSendingTemplate.java:182) ~[spring-messaging-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.messaging.core.AbstractMessageSendingTemplate.convertAndSend(AbstractMessageSendingTemplate.java:150) ~[spring-messaging-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.messaging.core.AbstractMessageSendingTemplate.convertAndSend(AbstractMessageSendingTemplate.java:143) ~[spring-messaging-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.MessagingGatewaySupport.send(MessagingGatewaySupport.java:417) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayProxyFactoryBean.sendOrSendAndReceive(GatewayProxyFactoryBean.java:576) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayProxyFactoryBean.invokeGatewayMethod(GatewayProxyFactoryBean.java:508) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayProxyFactoryBean.doInvoke(GatewayProxyFactoryBean.java:478) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayProxyFactoryBean.invoke(GatewayProxyFactoryBean.java:468) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:212) ~[spring-aop-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at com.sun.proxy.$Proxy168.publishEvent(Unknown Source) ~[na:na]
        at company.project.services.SomeService.lambda$bulk$2(SomeService.java:434) ~[project-api-0.5.0.RELEASE.jar!/:na]
        at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.accept(ForEachOps.java:183) ~[na:na]
        at java.base/java.util.stream.SpinedBuffer.forEach(SpinedBuffer.java:246) ~[na:na]
        at java.base/java.util.stream.Nodes$SpinedNodeBuilder.forEach(Nodes.java:1270) ~[na:na]
        at java.base/java.util.stream.Nodes$InternalNodeSpliterator$OfRef.forEachRemaining(Nodes.java:1105) ~[na:na]
        at java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:484) ~[na:na]
        at java.base/java.util.stream.ForEachOps$ForEachTaskpute(ForEachOps.java:290) ~[na:na]
        at java.base/java.util.concurrent.CountedCompleter.exec(CountedCompleter.java:746) ~[na:na]
        at java.base/java.util.concurrent.ForkJoinTask.doExec(ForkJoinTask.java:290) ~[na:na]
        at java.base/java.util.concurrent.ForkJoinPool$WorkQueue.topLevelExec(ForkJoinPool.java:1020) ~[na:na]
        at java.base/java.util.concurrent.ForkJoinPool.scan(ForkJoinPool.java:1656) ~[na:na]
        at java.base/java.util.concurrent.ForkJoinPool.runWorker(ForkJoinPool.java:1594) ~[na:na]
        at java.base/java.util.concurrent.ForkJoinWorkerThread.run(ForkJoinWorkerThread.java:183) ~[na:na]

and the bulk method for SomeService is somewhat like:

StreamSupport
    .stream(worksheet.spliterator(), true)
    .skip(1)
    .forEach(row -> {

        // insert row into db and publish message

        this.applicationEventGateway.publishEvent("rowCreated", row);

    });

Worksheet being an Apache POI worksheet. I understand that the method is called in a parallel stream, but would it result in an error with class not being found? What am I missing?

Heads up: I'm using Spring Boot 2.2.0.RELEASE, so it's not related to this.

I have a MessagingGateway as follows:

@Gateway(
            requestChannel = "myChannel",
            headers = @GatewayHeader(
                    name = "tenantId",
                    expression = "T(com.company.package.ContextHolder).getContext()?.tenant?.identifier"))
    void publishEvent(@Header(value = "eventType") String eventType,
                      @Payload Object payload);

My ContextHolder class is similar to SecurityContextHolder or RequestContextHolder, and I put some basic request related info in it, just like SecurityContext.

The issue is, this works perfectly on my machine, and for the most calls to the publishEvent method it does on the server, as well. However, for some methods, I get:

org.springframework.expression.spel.SpelEvaluationException: EL1005E: Type cannot be found 'com.company.package.ContextHolder'
        at org.springframework.expression.spel.support.StandardTypeLocator.findType(StandardTypeLocator.java:117) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.expression.spel.ExpressionState.findType(ExpressionState.java:155) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.expression.spel.ast.TypeReference.getValueInternal(TypeReference.java:69) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.expression.spel.ast.CompoundExpression.getValueRef(CompoundExpression.java:55) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.expression.spel.ast.CompoundExpression.getValueInternal(CompoundExpression.java:91) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.expression.spel.ast.SpelNodeImpl.getValue(SpelNodeImpl.java:112) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.expression.spel.standard.SpelExpression.getValue(SpelExpression.java:330) ~[spring-expression-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper.evaluateHeaders(GatewayMethodInboundMessageMapper.java:213) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper.access$1000(GatewayMethodInboundMessageMapper.java:86) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper$DefaultMethodArgsMessageMapper.buildMessage(GatewayMethodInboundMessageMapper.java:434) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper$DefaultMethodArgsMessageMapper.toMessage(GatewayMethodInboundMessageMapper.java:340) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper$DefaultMethodArgsMessageMapper.toMessage(GatewayMethodInboundMessageMapper.java:288) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper.mapArgumentsToMessage(GatewayMethodInboundMessageMapper.java:198) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper.toMessage(GatewayMethodInboundMessageMapper.java:192) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayMethodInboundMessageMapper.toMessage(GatewayMethodInboundMessageMapper.java:86) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.support.converter.SimpleMessageConverter.toMessage(SimpleMessageConverter.java:111) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.messaging.core.AbstractMessageSendingTemplate.doConvert(AbstractMessageSendingTemplate.java:182) ~[spring-messaging-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.messaging.core.AbstractMessageSendingTemplate.convertAndSend(AbstractMessageSendingTemplate.java:150) ~[spring-messaging-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.messaging.core.AbstractMessageSendingTemplate.convertAndSend(AbstractMessageSendingTemplate.java:143) ~[spring-messaging-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.MessagingGatewaySupport.send(MessagingGatewaySupport.java:417) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayProxyFactoryBean.sendOrSendAndReceive(GatewayProxyFactoryBean.java:576) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayProxyFactoryBean.invokeGatewayMethod(GatewayProxyFactoryBean.java:508) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayProxyFactoryBean.doInvoke(GatewayProxyFactoryBean.java:478) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.integration.gateway.GatewayProxyFactoryBean.invoke(GatewayProxyFactoryBean.java:468) ~[spring-integration-core-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:212) ~[spring-aop-5.2.0.RELEASE.jar!/:5.2.0.RELEASE]
        at com.sun.proxy.$Proxy168.publishEvent(Unknown Source) ~[na:na]
        at com.company.project.services.SomeService.lambda$bulk$2(SomeService.java:434) ~[project-api-0.5.0.RELEASE.jar!/:na]
        at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.accept(ForEachOps.java:183) ~[na:na]
        at java.base/java.util.stream.SpinedBuffer.forEach(SpinedBuffer.java:246) ~[na:na]
        at java.base/java.util.stream.Nodes$SpinedNodeBuilder.forEach(Nodes.java:1270) ~[na:na]
        at java.base/java.util.stream.Nodes$InternalNodeSpliterator$OfRef.forEachRemaining(Nodes.java:1105) ~[na:na]
        at java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:484) ~[na:na]
        at java.base/java.util.stream.ForEachOps$ForEachTask.compute(ForEachOps.java:290) ~[na:na]
        at java.base/java.util.concurrent.CountedCompleter.exec(CountedCompleter.java:746) ~[na:na]
        at java.base/java.util.concurrent.ForkJoinTask.doExec(ForkJoinTask.java:290) ~[na:na]
        at java.base/java.util.concurrent.ForkJoinPool$WorkQueue.topLevelExec(ForkJoinPool.java:1020) ~[na:na]
        at java.base/java.util.concurrent.ForkJoinPool.scan(ForkJoinPool.java:1656) ~[na:na]
        at java.base/java.util.concurrent.ForkJoinPool.runWorker(ForkJoinPool.java:1594) ~[na:na]
        at java.base/java.util.concurrent.ForkJoinWorkerThread.run(ForkJoinWorkerThread.java:183) ~[na:na]

and the bulk method for SomeService is somewhat like:

StreamSupport
    .stream(worksheet.spliterator(), true)
    .skip(1)
    .forEach(row -> {

        // insert row into db and publish message

        this.applicationEventGateway.publishEvent("rowCreated", row);

    });

Worksheet being an Apache POI worksheet. I understand that the method is called in a parallel stream, but would it result in an error with class not being found? What am I missing?

Share Improve this question asked yesterday Hasan Can SaralHasan Can Saral 3,2876 gold badges46 silver badges88 bronze badges
Add a comment  | 

1 Answer 1

Reset to default 1

Feels like that parallel for the Stream makes it looking into a different ClassLoader.

Would be great if you can confirm how it works without parallel.

It also feel like Spring Integration's IntegrationEvaluationContextFactoryBean can be fixed for a StandardTypeLocator with a ClassLoader from BeanFactory.

You may look into a workaround like creating a bean for IntegrationEvaluationContextFactoryBean with the IntegrationContextUtils.INTEGRATION_EVALUATION_CONTEXT_BEAN_NAME name and set typeLocator to the StandardTypeLocator based on the BeanFactory class loader:

@Bean(name = IntegrationContextUtils.INTEGRATION_EVALUATION_CONTEXT_BEAN_NAME)
public IntegrationEvaluationContextFactoryBean integrationEvaluationContext(ConfigurableBeanFactory beanFactory) {
    final IntegrationEvaluationContextFactoryBean context = new IntegrationEvaluationContextFactoryBean();
    context.setTypeLocator(new StandardTypeLocator(beanFactory.getBeanClassLoader()));
    context.afterPropertiesSet();
    return context;
}

If that is a case, please, raise a GH issue, so we will fix it shortly.

本文标签: