# Which Deployment Option Would You Use For a Mission Critical Application?

You have the following deployment options in Java EE (J2EE/5/6):

Deploying an EAR / WAR to a multi-project or dedicated server
Cluster deployment: deployment units get spread across the nodes, you get HTTPSession and @Stateful Bean failover
Cluster deployment, but no replication or failover. You get easy distribution and management (deactivating, disabling) of deployment units
Dynamic environment: your application is split across loose-coupled modules, which could be managed independently


And the mission critical strategy is:

Minimization of moving parts - simplicity is the key!
Very simple upgrade and maintenance strategies - the system should always be in consistent state.
Dead simple monitoring and deployment - operations are rarely interested in our geeky frameworks, switches and whistles.
Avoidance of third party frameworks and libraries - they are faster EOL than you may think.


Although they are zillions of frameworks and options out there, we did the following:

We deployed not only the application, but also the application server with already installed application AND JDK as a zip with hardcoded classpath
The application consisted with as few as only possible external libraries, parts or frameworks. We started with JDK 1.6 then expanded the search to Java EE 6 (or lower versions)
Although we had logical packages and components, we tried to deploy the application as a "BLOB" e.g. maven-with-dependencies does a nice job here. The fewer jars you have - the less can go wrong.
We didn't used a cluster but also didn't relied on the HA-qualities of the HTTPSession and SFSB in particular.
A simple load balancer, sometimes a slightly more sophisticated strategy, distributed the load across mostly independent servers (with sticky sessions were possible).


In real world you have a lot more to consider (especially the other non-functional requirements, politics and policies), than only availability and criticality.The strategy above has an interesting side-effect: you can not only upgrade your application, but also your appserver AND the JDK, just by replacing a folder or extracting a zip. After re-routing the traffic and killing the process or virtual machine - you can consistently and atomically update not only the app, but also the whole environment.
Interestingly a "mission critical" strategy is fully compatible with building maintainable software.

[See chapter 1 in "Real World Java EE Patterns - Rethinking Best Practices" for more in depth transactions, clustering, state, optimistic concurrency discussion]
