September 18th, 2008

Radiant file-based layouts

A few weeks ago I went over to see Tim O’Donovan at Horan Construction (no website yet, we’re working on it). They are a successful civil engineering company based in South Wales that undertake a variety of projects, varying from road surfacing to the design and construction of household-waste disposal centers. Despite being successful and respected in their industry they currently have no web presence.

Beanlogic are developing a new content-managed website for them. This kind of small-scale project is a common occurrence and we have a streamlined process and a collection of the tools and frameworks that we have become proficient with to implement just this kind of project. One of the tools we use is Radiant , an open-source Ruby on Rails based content management system (CMS).

Radiant

We use Radiant for a number of our content-managed projects. “A bespoke software company using off-the-shelf application?” I hear you ask. Well, yes we we do. We’re busy developing extensions to Radiant that solve our customers’ business needs rather than re-inventing the content management wheel. Besides, Radiant has a strong and active community that is always improving the offering. Something we have been actively involved in.

Radiant covers the vast majority of the functionality one would need in terms of content-management. However, we have found it lacking in some specific areas. One is navigation ordering, which will be the subject of another article. Another is the fact that the layout HTML templates reside in the database.

Database layouts

Layouts or view templates are the ubiquitous wrapper for every view in a web-application or website. They provide an easy way to apply to each view in the application with a standard or uniform decoration. In the average web-application (implemented using Rails perhaps) the layouts are stored on the file system, in the source tree.

In Radiant, which by it’s very nature allows the user to create and modify pages, all the view information, including the layouts are stored in the database. This is generally fine if all we were dealing with is a solely content-driven website. In most cases however we are not. We’re dealing with a content-driven website that has software-based extensions. In our projects, these extensions vary from reservation systems found in La Manga Direct and Park Cottages to an on-line shop extension we’re developing for a current project.

In a standard Radiant deployment the extensions are forced to use the same database-driven layouts that the content-managed views use. This means that we have source code that is part of extension software residing in the database. This is something I find unpalatable for two reasons.

Source code belongs in version control

I include HTML in the term source code. We use a VCS (Version Control System) – Subversion to be precise – for all our projects here, it’s an essential component of developing software (any software developer that doesn’t employ some form of VCS is not be trusted in my humble opinion). In any ordinary web application the views and layouts for those views usually reside in the source tree, and therefore in the VCS. This means that they can be subjected to the usual view testing. It also means that changes made to layouts on a developer’s workstation are made available to every other developer and any staging machines by virtue of the fact they all get the source code from the VCS. This cannot be achieved with database layouts unless we start storing all or part of the database content in the VCS, which creates it’s own problems.

This leads me on to the second reason for being unhappy with storing layouts in the database, and that is concurrency issues.

Which database is the authority?

After the launch of a new website and especially in the final stages of the development of a project the customer – or someone acting on their behalf – is busy populating or modifying the content for their website. What is also usually happening during this period is final tweaks and bug fixes. Some of these changes sometimes involve changes to layouts. If the layouts reside in the database there is potential for there being multiple, conflicting versions of the database on multiple workstations or staging servers.

The short-sighted (non)answer is to prevent changes on other copies of the database whilst working on another. The correct solution is to solve the root-cause of the problem. That is the fact that there is software source code in the database, somewhere it has no business being.

The right answer?

The answer is to view it from a pure software point of view. That is to employ the same methodologies and principles to any Radiant project that we would apply to a pure software project, and to do this without compromise. These methodologies include test-driven development (TDD), behavior-driven development (BDD) and – more relevantly to this article – the compulsory use of source management using version control.

File-based layouts

Before we tried to solve this problem ourselves we had a look at what already available on the open-source shelf.

file-system-extension

One solution that first cropped up was the Radiant extension file-system-extension . This extension provides some handy rake tasks to extract the database content (including the layouts) and place it on the file-system and vice-versa. With some tweaking we could modify these tasks to act exclusively on the layout data. However this doesn’t solve our problem. Regardless of what we are editing to change the layouts, Radiant will still be looking for them in the database.

This extension does allow us to keep our layout in the VCS but it doesn’t solve the problem of database concurrency.

file_based_layout

The next thing we tried is the file_based_layout extension . The name alone sounds promising if does what it says on the tin.

This extension allows us to define layouts in Radiant that us a file on the file system rather than database content. That means that the layouts can now reside in the VCS and that all versions (developers’ workstations and deployed servers) use layout from the file system. It satisfies the criteria I have set out above. This is what we are currently using for our Radiant-based projects and the respective extensions. If anyone has any other recommendations I’d be happy to hear about it.

Sorry, comments are closed for this article.