Several people seem to have the same problem(see this and this):
If you startup a glassfish(v 4) server with an MDB(Message Driven Bean) and there are messages to be consumed, the MDB will start consuming the messages while the container is still initializing. If the message processing requires any other service from the container it will throw an exception:
Caused by: javax.ejb.EJBException: Attempt to invoke when container is in Initializing
Has anyone managed to solve this problem?
Ideally the MDB should only start consuming messages after the container is fully initialized.
Is there a way to let the MDB check for container initialization and only start accepting messages when the container is up and running?
Edit:
Maybe the following annotation helps: #DependsOn("Dependency")
You may configure the application loading sequence (startup order), put a greater value for your application, and may be put a delaying application ahead of it.
Related
I'm writing some core features for developers who will use my library.
One of the features is to provide an ability to switch the message consumption between two different sources by flag configuration, the handling of these messages should remain as is, no mater to the source - for example switching message consumption from kafka to rabbitmq. the same business logic will be executed with income message.
**I try to figure out how to configure the consumer without using the #RabbitListener, is it possible? **
RabbitAdmin - responsible for connect to the source.
RabbitTemplete - responsible for publishing messages.
The only clue that I found is to use springs SimpleMessageListenerContainer, but the issue with him is that there is no ability to set multiple onMessage handlers?
Also I saw the option to use MessageListenerAdapter in this answer
The main issue with these answers is that I'm going to deal with multiple number of queues and bindings.. and here it seem like solution for single consumer in whole application. - am I wrong here?
You need a listener container for each listener.
You can use Boot's auto configured listener container factory to created each container and add a listener to it.
If the same listener can consume from multiple queues, you can configure the container to listen to those queues.
In our project, we have several Spring-based modules which are deployed on WAS as web applications. We need to skip deployment, or stop a module if its Spring context initialization fails (i.e. ContextLoaderListener#contextInitialized or DispatcherServlet#init throws an exception). Now, if such happens, app is got deployed and starts, but returns HTTP 500 for any request.
Websphere 8.5.5
Related question: https://stackoverflow.com/a/272747/3459206
This APAR seems to be relevant:
https://www-01.ibm.com/support/docview.wss?uid=swg1PI58875
From the APAR text:
Listener exceptions typically should not stop the application
from starting up for service. However, some applications depend
on their listeners to do the necessary setup before the
application is started for service. Such applications prefer to
stop the application from starting up when there is any
exception in their listeners.
Problem conclusion
The WebContainer Container code was modified to provide an
option to stop the application when there is any listener
exception during the application starting up process.
A new WebContainer custom property needs to be set to enable the
behavior provided by this APAR:
For Full Profiles
com.ibm.ws.webcontainer.stopappstartuponlistenerexception = true
(default is false)
For Liberty Profile
stopappstartuponlistenerexception=true
The fix for this APAR is currently targeted for inclusion in
WebSphere Application Server fix packs 8.5.5.11 and 9.0.0.2,
and Liberty 16.0.0.3
See the APAR link for additional information.
You can use jenkins + maven.
Add the part you need to check under your test like junit.
Then if this module do not pass test, jenkins would not deploy it.
But I prefer fix bugs before deployment
Had a very similar issue.
The thing is - webfear - sorry could not resist ;-) does not initialize everything on startup.
To trigger a controlled request, I added a ScheduledEJB to the startup of the application. This bean itself triggered a http-request to a defined URL, which itself triggered:
any filters to get initialized in the chain
any contexts which are needed are initialized
And this itself ensured that my application (EAR or WAR) got very quickly tested after deployment. This works well with some small amout of requests per minute
If you work with high load, means tons of requests per second, you need to choose a different approach.
In this case I added a polling mechanism into the #Startup of the application, which polled every second or 250ms (depends on the load of the application).
This firing to the server ensured, that my #Startup bean was the very first which triggered the possible init issues in the application. If this happened I initialized a filter which always reported a 500 (or better fitting error) to the requestor.
Of course stop your firing bean, as soon as you get the 500, else your admins may like to kill you. (happend to me, since I produced tons or monitoring issues ;-) )
And of course on the regular operation, after your application started properly, you should also disable the polling
Look for a try-catch in the top level of your application code that is catching the Spring exception and allowing the application to continue running.
If the Spring exceptions being thrown are permitted to propagate to the top of the stack, the JVM will stop and there's no way it can keep running, far as I know.
I am facing the problem of finding the best place to put some handling where I can check some of the properties in application.yml and fail app startup of Spring Boot app if they are invalid.
The main point is to find the first place where I can check these properties without running the entire app and fail in the end.
I tried:
#EventListener, but here I was able only to trigger events when the app was started.
Throwing an exception in #PostConstruct in one of my classes with #Configuration. I like this one, but it looks like a messy one.
Maybe there are better ways?
#EventListener, but here I was able only to trigger events when the
app was started
There are many different type of events and where you hook in to the startup process depends on the type of event that you listen for. In your case, consider listening for an ApplicationEnvironmentPreparedEvent if you want to check properties as soon as they are available.
I've been looking all around and cannot find any good explanations or examples of using Spring 4.x (Springboot) with an EmbdeddedTomcat container and manually setting the startStopThreads attribute described here
I've noticed our application's startup latency has been getting worse over time, but also see (in the logs) the thread pool labeled [localhost-startStop-1] is the only thread ever executing beyond [main]. I would like to add more threads into this pool to speed up our asynch startup.
Can anybody help me with Tomcat's startStopThreads issue?
UPDATE -
A good usecase for this is dynamically creating DynamoDb tables upon startup. The creation code is wrapped in an Executor.submit call, however the logs show these being executed serially. Here's an example of whats in the logs:
2017-02-22 15:000:000:01,000 [main ] INFO Creating table 1
2017-02-22 15:000:000:05,000 [localhost-startStop-1] INFO Creating table 2
2017-02-22 15:000:000:10,000 [localhost-startStop-1] INFO Creating table 3
Unfortunately, I am never seeing localhost-startStop-2 execute anything, which it should if it were in the threadpool
Configuring startStopThreads won't have any effect. It's used by each container in Tomcat (Service, Host, Context, etc) when starting their children. With more than one thread available a container with multiple children will start them in parallel. It won't have any effect in a typical Spring Boot application as each Tomcat container only has a single child.
Rather than trying to use Tomcat's threads to perform some initialisation in parallel, I'd recommend using a Java Executor or Spring Framework's TaskExecutor.
I have a web application which I'm trying to shut down by executing the close() method on the context:
((ConfigurableApplicationContext) appContext).close();
After executing this the application appears to be continuing running, health page produces the following exception:
org.springframework.web.util.NestedServletException: Request processing failed; nested exception is java.lang.IllegalStateException: BeanFactory not initialized or already closed - call 'refresh' before accessing beans via the ApplicationContext
at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:978)
Is there a way to shudown the whole thing via Spring or should I resort to System.exit()?
Any help would be kindly appreciated!
PLease have a look at these questions. They are on the same line as yours:
How to manage Tomcat via Java,
Start / stop a web application from itself?
As #chrylis suggested, I think the easiest way of shutting down the server(if it's not running in embedded mode) is to use Runtime class.