[ 
https://issues.apache.org/jira/browse/TOMEE-4712?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel
 ]

Markus Jung resolved TOMEE-4712.
--------------------------------
    Resolution: Fixed

> MDB endpoints are activated before the application's other EJBs are started
> ---------------------------------------------------------------------------
>
>                 Key: TOMEE-4712
>                 URL: https://issues.apache.org/jira/browse/TOMEE-4712
>             Project: TomEE
>          Issue Type: Bug
>    Affects Versions: 11.0.0-M1, 10.2.0
>            Reporter: Markus Jung
>            Assignee: Markus Jung
>            Priority: Major
>             Fix For: 11.0.0, 10.3.0
>
>          Time Spent: 50m
>  Remaining Estimate: 0h
>
> {{Assembler.startEjbs()}} deploys all beans of an application first and 
> starts them afterwards. {{MdbContainer.deploy()}} and 
> {{MdbInstanceManager.deploy()}} (for {{Pool=true}}) activate the message 
> endpoint right away, so the resource adapter can deliver messages during the 
> deploy pass. The other beans of the application are not started yet at that 
> point: stateless beans get their instance pool in 
> {{StatelessContainer.start()}}, {{@Startup}} singletons are initialized in 
> {{SingletonContainer.start()}}.
> Messages that are already waiting on the destination (for example because the 
> server was stopped with unprocessed messages) are therefore delivered to an 
> MDB whose injected stateless bean has no pool yet:
> {code}java.lang.NullPointerException: Cannot invoke 
> "org.apache.openejb.core.stateless.StatelessInstanceManager$Data.poolPop()" 
> because "data" is null
>     at 
> org.apache.openejb.core.stateless.StatelessInstanceManager.getInstance(StatelessInstanceManager.java:218)
>     at 
> org.apache.openejb.core.stateless.StatelessContainer.invoke(StatelessContainer.java:204)
>     ...
>     at 
> org.apache.openejb.core.mdb.MdbContainer$MdbActivationContext.start(MdbContainer.java:689)
>     at org.apache.openejb.core.mdb.MdbContainer.deploy(MdbContainer.java:251)
>     at 
> org.apache.openejb.assembler.classic.Assembler.startEjbs(Assembler.java:1690)
> {code}
> It also lets messages reach the application before its {{@Startup}} 
> singletons are initialized, which Jakarta Enterprise Beans 4.0 Core, [4.8.1 
> Singleton Session Bean 
> Initialization|https://jakarta.ee/specifications/enterprise-beans/4.0/jakarta-enterprise-beans-spec-core-4.0.html#singleton-session-bean-initialization]
>  forbids:
> bq. The container must initialize all such startup-time singleton session 
> beans before any external client requests (that is, client requests 
> originating outside of the application) are delivered to any enterprise bean 
> components in the application.
> Jakarta Connectors 2.1, [14.4.4 Application 
> Server|https://jakarta.ee/specifications/connectors/2.1/jakarta-connectors-spec-2.1.html#a2765]
>  explicitly allows a resource adapter to deliver during 
> {{endpointActivation}}:
> bq. Note, a resource adapter may attempt to deliver messages during the 
> endpointActivation method call.
> Reported on the [users 
> list|https://lists.apache.org/thread/pg3vv6xr9yd19wowj6lg31b4w4w19bnn] 
> against TomEE 10.2.0: an MDB with an injected {{@Stateless}} bean logs these 
> NPEs on startup while messages from before the shutdown are pending on its 
> topic.
> Fix: activate the endpoint in {{start()}} of both MDB containers instead of 
> {{deploy()}}. {{Assembler}} sorts MDBs to the end of the start pass, so every 
> session bean of the application is started before the first message is 
> delivered. {{MdbActiveOnStartup}}/{{DeliveryActive=false}} keep working as 
> before.



--
This message was sent by Atlassian Jira
(v8.20.10#820010)

Reply via email to