Creating new document components
This HOWTO will show you how to add a new document component to MKDoc. A document component allows editors to add content to documents and manages the display of content to users. For example, editors use the HTML component to add HTML to their documents and the file component to attach files to documents.
The Fictitious POD Component
For the purposes of illustration I'll walk through the process of creating a POD component. POD stands for Plain Old Documentation; it's a markup language which is easy to write and easy to read. I'm writing this HOWTO in POD right now, and this section looks like:
=head2 The Fictitious POD Component
For the purposes of illustration I'll walk through the process of creating a POD component. POD stands for Plain Old Documentation; it's a markup language which is easy to write and easy to read. I'm writing this HOWTO in POD right now, and this section looks like:
Of course, a POD component wouldn't really make a very good addition to MKDoc because POD is mostly used by Perl programmers writing code documentation. For more information about POD see:
http://www.perlpod.com/5.8.4/pod/perlpod.html
It's Gotta Have Flo
All the code for the MKDoc component system is contained in the flo/
directory inside the MKDoc root. Why flo
? Bruno Postle told me, ``Florence is Adam's fourth (I think) child, she is about four years old and some of this code is even older.''
The flo
system is highly object-oriented, using several layers of inheritance to implement its functionality. All components inherit their functionality from the flo::Component
base-class.
Every Component Needs an Editor
When you create a new MKDoc Document you'll eventually end up at the component editor screen. Here you'll see an interface listing all the component types available:
This is actually a list of files in the flo/editor
directory, reformatted to be easier to read:
Discussion.pm File.pm Headlines.pm Html.pm Image.pm Link.pm Photo.pm Poll.pm Price.pm RSS.pm Text.pm TimeRange.pm
Each of these .pm
files implements a sub-class of flo::Component
(not flo::Editor
as you might expect, that class does something else). These classes are responsible for managing both the editing of data and the output of the data for visitors to the site.
To get started with the POD component I'll create flo/editor/POD.pm
. The easiest way to create a new editor is to copy an existing editor and use that code as a base. In this case I copied flo/editor/Text.pm
since the POD component will be most like Text:
$ cp flo/editor/Text.pm flo/editor/POD.pm
After editing the package
line to read:
package flo::editor::POD;
and restarting Apache, the POD component is available for adding to documents. However, actually attempting to add it to a document results in an error. That's because every editor requires a template.
Templates MK the Doc Go Round
When you add a component to a document in MKDoc the next thing you see is an interface to edit that component. In the case of Text that's an HTML textarea
and some buttons. This comes from a Petal template stored in templates/editor
.
Just like before I'll start by copying the template for the Text component:
$ cp -a templates/editor/text templates/editor/pod
I used cp -a
because templates/editor/text
is actually a directory containing a single file, en.html
. If the text component is ever translated into other languages then those files will sit alongside en.html
.
To get this template ready for use I did a search-and-replace on the copied file, changing occurrences of 'text' into 'pod'. Of course I was careful not to translate textarea
into podarea
!
After this work the POD component is basically functional:
You can enter POD into the textarea and save to the database. There are two obvious problems at this stage. First, the editing interface doesn't have any color. That's easily remedied by adding a class in skins/admin.css
:
.pod-component { color: #000; background-color: #9C6; }
Second, nothing is displaying outside the editing interface. Users visiting the documents aren't seeing the POD entered in the editor. To fix this we'll need
Another Day, Another Template
Display of documents to visitors is controlled by templates/document/default/en.html
. It contains a list of component types to loop through which will show up on the page. To add the POD component to this list I changed this line:
Body_Loop self/components_list --text --html --image --photo --file --poll --discussion --headlines --rss;
To read:
Body_Loop self/components_list --text --html --image --photo --file --poll --discussion --headlines --rss --pod;
Now the POD text shows up on rendered pages, just like text. For example, here's the test document I created earlier with the POD contents ``=head1 Hello World!'' showing:
Finally, Time to Code
Now that we've got the component working in the editor it's time to get the output right. Instead of just showing the raw POD entered by the editor I'd rather show the rendered output. I'll use Pod::Simple::HTML from the Pod::Simple distribution ( http://search.cpan.org/~sburke/Pod-Simple/ ) to render the POD as HTML. Thus, the first thing to do is add a use
line to flo/editor/POD.pm
:
use Pod::Simple::HTML;
Then all that's needed is a new html()
method in flo::editor::POD which uses the Pod::Simple API to create HTML from POD:
sub html { my $self = shift; my $data = $self->{'data'};
# translate POD to HTML my $parser = Pod::Simple::HTML->new(); my $output; $parser->output_string(\$output); $parser->parse_string_document($data); return $output; }
After these changes, and a quick Apache restart, the component is full functional, turning POD formatting instructions into HTML:
Further Development
That's all it takes to get a new component up and running. However, there's a lot more work that can be done to make components work better. Here are a few ideas to give you an idea of what's possible:
- The POD component should detect invalid POD and explain the problem to the editor. The way to do this is via the
MKDoc::Ouch
API. You can find lots of samples ofMKDoc::Ouch
usage in the more complicated components like Headlines and TimeRange. - The help text in the POD editor interface needs work and should point to a full introduction to POD.
- Translating POD to HTML is a time-consuming process. The flo::editor::POD object should cache the translation internally so it can be called multiple times with no additional cost.
Of course, the possibilities don't end there. MKDoc's component system is quite flexible. For more ideas check out the code for the other components and their super-class, flo::Component.
MKDoc Ltd., 31 Psalter Lane, Sheffield, S11 8YL, UK.
Copyright © 2001-2005 MKDoc Ltd.