(Edited 2008-09-14 to include information from comments)
I have been working with a hosting company and seen what we developers pass off as applications.
These are some musings on what a developer needs to do in order to keep applications deployable.
The installation guide
All developers really, really should create an installation guide. They should then try to forget everything about their application and try to follow the guide.
Did it work? If not, it needs to be fixed. Modern development environments thrive on being able to have massive numbers of deployments. For a far better reasoning behind this than I can ever give in a short blog article, have a look at Refactoring databases by Ambler and Sadalage. Every project, team and developer should isolate themselves from errors made by someone outside their control. Virtualization technologies (or, if you are like me, I prefer to use my own workstation) have made this possible - but only if it is easy enough to deploy the application that people actually bother.
This is somewhat the same problem as testing. Architects need to make it very easy to write good tests, otherwise people won’t bother. So write that deployment guide, and try to make it as easy as possible to get from a source code repository to a running version of the system for someone who does not know the system.
Configuration should be split
A lot of developers seem to think that it is ok to place the configuration inside your application. Since I am a java developer, this often means inside some kind of java archive.
This is a really bad proposition for keeping an application deployable. Often, people will start to check in configurations for the test environments. There never seem to be provisions for configuring the production environment (or, when it comes to that, developer environments) without doing silly stuff.
It is perfectly ok to have all the static configuration inside the application. Whatever changes between installations - database logins and the like - need to go somewhere else. These are some guidelines I try to follow:
- Production passwords must never be checked into a developer repository. Developers should not have access to production passwords without a human giving it to them. Letting everyone tamper with the production database is a very good way to increase the risk of stability problems.
- The hosting organization must not be required to unpack an application, rewrite the configuration, and repack the application. Repacking leads to several different versions of the application floating around, with who knows what bugs. The release manager builds the application archive, period. Nobody messes with it afterwards.
- There must not be defaults for the installation-critical configuration bits that point to the test rig. If you do this, you are placing yourself in a situation where the only protection against accidentally putting production data into a test rig is a routing table entry. If the entry disappears, the best thing that can happen is a very costly reconciliation between the test and production data sets. Worst case, data is lost when someone tries to test the stuff that is in production - the stuff which by now is not behaving as expected - and clears the test database before the test starts. Please don’t write this off as far-fetched. I have seen it happen.
- If installation-critical configuration does not exist, the application needs to stop. This is one of the oversights of the JEE specifications. There is no way for an application to tell the application server that it wants to stop because continuing is not an option. This functionality usually needs to be written inside the application or be application server specific. If this condition is not met, people trying to install the application are going to spend lots of time reading logs, trying to find the log statement saying that it wasn’t possible to connect to the database. This statement should perferably be the last statement before the “I am stopping” statement in the application log.
I usually make some kind of provision for providing the name of a configuration file using either JNDI or command-line options to JAVA. Both are usually acceptable to hosting organizations.
A nice side effect of not hardcoding the location of the configuration file is that several instances of the application may suddenly run on one computer. This does away with a lot of virtual machines.
Use a production-like environment during development
The closer the system the developer uses is to the production enviroment, the fewer the problems.
How do you know that you are close to the production environment before this enviroment has been built? Specify how you want it to look. Lots of projects get into trouble because different team members think something is self evident - like how the production environment looks. It usually isn’t at this level. Knowing how the production environment needs to look also makes it easier to select a hosting provider.
Specifying how the application enviroment should be, seen from the development side, is the first step of starting a constructive information exchange with the hosting provider. A good, professional hosting provider will wish to make changes to the environment of the application in order to reduce the costs associated with hosting your application, and there is absolutely nothing a developer should attempt to do about this. A competent hosting vendor is the hosting technology expert, and needs to be able to exercise this kind of control.
Whatever changes to the application environment is agreed on also needs to be fed back into the development and test environments. As the first paragraph of this section started - the closer the system the developer uses is to the production environment, the fewer the problems.
Share the pain!
All developers should install a local copy of the application. If this is not possible, something is wrong. If it is too cumbersome to do so, only the developers are in a position to fix the problem - and hosting personnel is not much cheaper than developers, so it is better to fix the issue than to let the problem persist for the lifetime of the project.
Next: Installing deployable applications… When I get the time, at least. Shout if I should prioritize it.