Tomcat stop after failed deployment? - tomcat7

I would like to stop Tomcat when a war deployment fails. Is there some hook or listener which could be used for that?
I know, normally one would not make the container stop when a deployment fails. In my case I would like to implement a Fail-fast error model with Tomcat since there is currently no chance to replace the WAR with a fat jar with an embedded Servlet engine (e.g., Spring-Boot).

In the mean time I have implemented a Tomcat LifecycleListener which shuts down TC when a deployment fails: https://github.com/ascheman/tomcat-lifecyclelistener
Thanks to Thomas Meyer who gave some hints on Twitter: https://twitter.com/thomasmey/status/752971635825729537.

Spring boot provides shutdown hook. SOF has similar query as below
Spring Boot shutdown hook
This can give and idea to implement your app Fail Fast behavior with hook.

Related

Replace old Spring Boot Jar with new one

I'm running a spring boot executable jar as a service under Linux and it works fine.
My question is, there is a way to replace the running jar with new jar without stopping and rerunning the service?
Thanks,
Avi
In a nutshell, it is impossible to reload spring-boot jar in production environment.
I guess your final goal is to "hotswap" your application without user notified. Thanks to service discovery, you can do this by:
Start your new application and keep the old ones running.
After the new one started and registered in service discovery server, shutdown the old ones.
That's how we do upgrade of our services, and Docker saves us a lot of time.

Prevent database shutdown command from Spring Boot

When I run my Spring Boot application (from within Intellij IDEA) and either trigger a stop, restart or automatic redeploy of the application; something is issuing a shutdown command to my HSQLDB.
I run a HSQLDB (v.2.3.4) in Server mode from an external terminal window.
HSQLDB Server log at the moment I restart or stop my Spring Boot application:
[Server#4f023edb]: Initiating shutdown sequence...
[Server#4f023edb]: Shutdown sequence completed in 101 ms.
[Server#4f023edb]: 2017-05-05 21:47:01.878 SHUTDOWN : System.exit() is called next
This is of course very annoying since I have to go through the hassle of manually bringing up my HSQLDB every time I redeploy the application. How do I prevent this from happening, or an explanation of what is actually going on.
This only seems to happen when running the Spring Boot application from within Intellij IDEA, if I start the Spring Boot application-jar from a terminal window and issue shutdown Ctrl+C, then HSQLDB is not affected.
Turns out the reason why I only experience this problem when running from within Intellij IDEA is because spring-boot-devtools (a maven dependency included in my project) is not packaged in the application-jar that I run from a terminal window.
Developer tools are automatically disabled when running a fully packaged application. If your application is launched using java -jar or if it’s started using a special classloader, then it is considered a “production application”. Flagging the dependency as optional is a best practice that prevents devtools from being transitively applied to other modules using your project. Gradle does not support optional dependencies out-of-the-box so you may want to have a look to the propdeps-plugin in the meantime.
spring-boot-devtools is active when running the application from within Intellij IDEA and provides a shutdown hook that will try to gracefully shutdown the database resource (amongst other things).
The shutdown hook can be disabled the following way;
SpringApplication app = new SpringApplication(MyApplication.class);
app.setRegisterShutdownHook(false); //This disables the shutdown hook
app.run(args);
This solution resolved the problem I had.

Spring Integration Invoking Spring Batch

Just looking for some information if others have solved this pattern. I want to use Spring Integration and Spring Batch together. Both of these are SpringBoot applications and ideally I'd like to keep them and their respective configuration separated, so they are both their own executable jar. I'm having problems executing them in their own process space and I believe I want, unless someone can convince me otherwise, each to run like they are their own Spring Boot app and initialize themselves with their own profiles and properties. What I'm having trouble with though is the invocation of the job in my SpringBatch project from my SpringIntegration project. At first I couldn't get the properties loaded from the batch project, so I realized I need to pass the spring.active.profiles as a Job Parameter and that seemed to solve that. But there are other things in the Spring Boot Batch application that aren't loading correctly like the schema-platform.sql file and the database isn't getting initialized, etc.
On this initial launch of the job I might want the response to go back to Spring Integration for some messaging on Job Status. There might be times when I want to run a job without Spring Integration kicking off the job, but still take advantage of sending statuses back to the Spring Integration project providing its listening on a channel or something.
I've reviewed quite a few Spring samples and have yet to find my exact scenario, most are with the two dependencies in the same project, so maybe I'm doing something that's not possible, but I'm sure I'm just missing a little something in the Spring configuration.
My questions/issues are:
I don't want the Spring Integration project to know anything about the SpringBatch configuration other than the job its kicking off. I have found a good way to do that reference to the Job Bean without getting my entire batch configuration loading.
Should I keep these two projects separated or would it be better to combine them since I have two-way communication between both.
How should the Job be launch from the integration project. We're using the spring-batch-integration project with JobLaunchRequest and JobLauncher. This seems to run it in the same process as the Spring Integration project and I'm missing a lot of my SpringBootBatch projects initialization
Should I be using a CommandLineRunner instead to force it to another process.
Is SpringApplication.run(BatchConfiguration.class) the answer?
Looking for some general project configuration setup to meet these requirements.
Spring Cloud Data Flow in combination with Spring Cloud Task does exactly what you're asking. It launches Spring Cloud Task applications (which can contain batch jobs) as new processes on the platform you choose. I'd encourage you to check out that project here: http://cloud.spring.io/spring-cloud-dataflow/

How to only auto configure the embedded container?

I'm trying bootify my app, which is XML configured. I'd love to have an embedded tomcat server that I can just run through the main method.
The simplest way to do it is to bootstrap the app using the existing XML config through #ImportResource("classpath:app-servlet.xml").
I cannot use auto configuration. We have certain circular dependencies that are not trivial to fix at this point.
The problem is that the embedded tomcat server only gets automatically configured if you use #EnableAutoConfiguration.
Is there a way to only auto configure the embedded server? I tried looking that Spring Boot's sources, namely EmbeddedServletContainerAutoConfiguration, including extending it and "running" it through my setup, but it only runs the customizers, not the ServletInitializer, therfore I'm getting an error "Root context already initialized".
Any help would be greatly appreciated.

glassfish 3.1.2 monitoring EJB container, bean-methods

the glassfish application server provides a nice monitoring REST interface.
To use it u can enable several monitorable items in the admin console, for example the EJB container. The documentation says, you can retreive EJB-statistics for every deployed application.
If you request a URL like localhost:4848/monitoring/domain1/server/applications/APPNAME/EJBNAME you will get statistics for a given EJB of the application.
Further, there is a possibility to look more deeply into each bean-method of the ejb, for example the executiontime, about which the documentation says:
"Time, in milliseconds, spent executing the method for the last successful/unsuccessful attempt to run the operation. This is collected for stateless and stateful session beans and entity beans if monitoring is enabled on the EJB container."
The problem now is, monitoring is enabled on the EJB-container (Level set to HIGH), but nothing is sampled in any bean-method in any EJB in any deployed application.
Is there something special to do in the bean and/or the glassfish ?
Thanks in advance for help,
Chris
EDIT:
Ok, I noticed something more about that behaviour:
In the server log you get a log message for each deployed EJB like that:
INFO: EJB5181:Portable JNDI names for EJB DataFetcher // ...
If I set the ejb-container monitoring level to HIGH (which is what I want to do), I get the following warning for each deployed EJB, regardless which app I deploy:
WARNING: MNTG0201:Flashlight listener registration failed for listener class : com.sun.ejb.monitoring.stats.StatelessSessionBeanStatsProvider , will retry later
I googled the warning but none of the resulst really help me enabling EJB monitoring...
This seems to be a Bug in Glassfish.
EJB Monitoring is currently not working in 3.1.2.
JIRA issue is already raised: http://java.net/jira/browse/GLASSFISH-19677
There is nothing "special" to do.
http://docs.oracle.com/cd/E18930_01/html/821-2431/abeea.html
For me it seems as if you probably enabled the monitoring option on the wrong configuration. Please double check.
To get rid of this message you can disable the monitoring on ejb container option below in the image
From Monitor Data--->Configure monitoring--->make ejb container log off

Resources