Since starting to use Mach-II I have asked (and seen many others ask) the question; “Can I split the mach-ii.xml config file to make it more manageable.”

There have been a few responses over time ranging from “you don’t need to” to split it into sub-applications, but just now on the Mach-II Coldfusion Topica list Jon Gunnip has posted an interesting solution to the problem.

The main reason the question of splitting the config file arises seems to be the problems with managing a single config file which is 1000’s of lines long. Although this can be a pain, especially if multiple developers share the same code-base without any version control (which we were guilty of until recently), this is not the reason I have been looking for a solution to have a more modularised config file.

What we currently have is about 8 applications which are basically variations on a single application, each will have certain “modules” removed or slightly tweaked for its particular needs, it’s not perfect but it is 10,000 times better than the pre-Mach-II “application(s)”. On a day to day basis, this works quite well as we don’t have to change these that much, however once you start adding or changing features which affect the config file in more than a couple of places, and need to affect every application, it can quickly become messy.

Jon Gunnip’s solution, which is derived from a post about entities with model-glue, is basically to use XML entities which can then reference smaller XML files, which will make it act like a single config file, like so:

<!DOCTYPE mach-ii [
	<!ENTITY properties SYSTEM "c:/path_to_config/properties.xml">
	<!ENTITY listeners SYSTEM "c:/path_to_config/listeners.xml">
	<!ENTITY filters SYSTEM "c:/path_to_config/filters.xml">
	<!ENTITY events-campaign SYSTEM "c:/path_to_config/events-campaign.xml">
	<!ENTITY events-help SYSTEM "c:/path_to_config/events-help.xml">
	...
	<!ENTITY plugins SYSTEM "c:/path_to_config/plugins.xml">
	<!ENTITY views SYSTEM "c:/path_to_config/views.xml">
]>

<mach-ii version="1.0">
	&properties;
	&listeners;
	&filters;
	&events-campaign;
	&events-help;
	...
	&plugins;
	&views;
</mach-ii>

I think this could be quite useful and for our needs seems to be the best solution suggested so far. It is definitely something to add to my list of things to do at work.

However I still dream of a real module based solution, this something which I’ve mentioned in a couple of places before. For example, such a solution could allow you to specify a module like so:

<module name="offers">
<listeners>
<listener name="offers" type="com.listeners.offers" />
<listeners>

<event-handlers>
<event-handler name="offers.homepage" access="public">
<view-page name="offers.homepage" contentKey="request.output.offersHomepage" />
...
</event-handler>

...

</event-handlers>

<page-views>
<page-view name="offers.homepage" view="/views/offers/homepage.cfm" />
...
</page-views>
</module>

You would package a module with all it’s requirements, listeners, event-handlers and views (I don’t feel that plugins would apply to modules). If you were include two modules which register the same listeners or views then they are only included once. The modules could have some sort of CSS-like cascade where you could then include application specific modules which override certain settings (such as page-views or single event-handlers).

I know that this would be a little complex to instigate, I keep threatening to setup a proof of concept using something like a directory event gateway in Coldfusion to do this, but its an idea that could be worth a further look down the line.