The ultimate of reusable code: using one codebase to serve many sites. Not copies of that codebase mind you, but one actual set of code templates. Update a template to fix a bug or add a feature and...? Presto! You've just updated X number of sites at once. Genius! Or is it?
There are a lot of things you must consider when writing this type of application. In this series of posts I want to discuss the concept thoroughly. And I say "discuss" because there is always more than one way to skin a cat, and there are definitely some developers out there reading this that are smarter than I am. Running many sites off a single codebase can be very tricky, and it's not something you should "just do" without some serious consideration. It isn't something you would do in every situation, and there are some serious pitfalls you would want to avoid, especially in terms of scalability.
Along the way I'll be including code. It will be written for ColdFusion 9, but in most cases could be adjusted for earlier server versions. I'll also make suggestions on architecture such as file system structure, web and app server configurations, error handling, and more. Remember that none of this is gospel, but merely suggestions, as every environment and application are different. I also welcome any feedback along the way on ideas for better architecture.
When running multiple sites from a single codebase, my first recommendation is that you use a dedicated server instance. This provides some degree of sandboxing, allowing one to do some things that you wouldn't ordinarily do in most environments. Best to work with a VPS or a dedicated machine. I would also suggest using a 64-bit system with a 64-bit JVM and 64-bit ColdFusion. 32-bit systems limit your RAM utilization, because a 32-bit JVM can only access about 1.4 GB of RAM. This can fill up very quickly with multiple applications (each site is it's own application) and thousands or more user sessions. Using a 64-bit JVM will allow you to allocate more RAM to your ColdFusion instance, meaning you can run more applications/sites and accomodate more concurrent users. For these examples I'll be using the Apache Webserver and the JRun J2EE server used by the default ColdFusion Multi-Instance setup. I have a series of (dated) posts on creating Multi-Instance setups on Apache that you can follow (with modern Apache adjustments) to help you get your initial server configurations in place, though you can just as easily use IIS for your webserver, or Tomcat or JBoss for your J2EE server.
Consideration: Scope Usage
One major consideration, when creating a MSOC (Many Sites, One Codebase) environment are the decisions we make about persistent scope usage. Every time we consider what scope to use for a variable, it is imperative to weigh the pros and cons of where that variable will live. You may quickly find that a variable you might typically put in the session scope really belongs in the application scope, or that an application variable you've been using could be part of the server scope because it's used by every application (this is one of the reasons it is best to use a dedicated server instance). Another consideration is your object usage. We all want to write better applications, and an MVC architecture and frameworks are very appealing. But most frameworks can be very object intensive, and aren't necessarily the best choice in an MSOC environment.
When considering persistent scope, you also have to consider your server/RAM overhead very carefully. I've used a User object in the session scope many times in the past, but we have to consider the memory footprint of that object. How many concurrent users might be in each app at any given time? Do I really need a User object? Or can I get by with a small, basic struct? If I have a million concurrent users across multiple applications, what does the memory footprint look like? Can I shift a variable to a better scope, and reduce my memory utilization without negatively impacting my application? By placing this object in this scope, have I verified that it's thread safe? All are important things to consider.
Our next post we'll start to look at setting up the file system and web server for our sites. We'll talk about some code organization specific to an MSOC environment, and some architecture considerations. If you have any suggestions, comments, or questions, please post a comment and I'll either answer it here of in another post.