Tarquin's rough stab at turning
UseMod into OO code...
#!/usr/bin/perl
###############################################################################
# UseMOO
# a sort of perl disaster by Tarquin
# based on UseModWiki by Clifford A. Adams
#
###############################################################################
# OO code begins
###############################################################################
#
# class Page
#
# Base class for pages.
# should:
# open an HTML scaffold file or build the UseModWiki
# default HTML page scaffold
# determine what sort of page has been requested
{
package Page;
###########################################################
# Static
our @registered;
sub propNested { @registered }
###########################################################
# Class conditions
sub propConditions { }
# just for inheritance
###########################################################
# Configuration
our %configuration = (
ConfigFile => 'config.pl',
SiteName => 'Moo Wiki',
HomePage => 'HomePage',
RecentChanges => 'RecentChanges',
);
# at this point we should read in a configuration file if:
# a) this script's config asks for it
# b) it exists
# this will change the values of the %configuration hash
# we also need to read in user preferences.
# These will probably also go into %configuration to make retrieval simpler
sub getConfiguration {
# consider changing this to accept a list of keynames and
# return a list of values
my $class = shift; $class = (ref $class or $class);
my $wantedkey = shift;
return $configuration{$wantedkey};
}
###########################################################
# Register
sub register {
my $class = shift; $class = (ref $class or $class);
push @registered, $class
if $class->isa(Page)
and not grep /^\Q$class\E$/, @registered;
}
###########################################################
# New
sub new {
my $class = shift; $class = (ref $class or $class);
my %browseParameters = @_;
my $self = {} ;
my $text;
my $childClass;
# consider calling this $object instead; "self" is misleading
# this is part of an earlier approach that involved
# storing HTML output in the created instance.
$self->{outputText} = {};
# not sure what this is here for
return if $class ne Page;
# test child classes to see if they want to handle this page
foreach my $childclass (@registered) {
if( eval $childclass->propConditions ) {
return $childclass->new(%browseParameters);
}
}
# return this class; if we get here then we've not properly handled the cases
return bless $self, $class;
# notes
# the new sub should return an instance that actually holds some data
# for example the page name
# this might also allow recursive calling for preview, diffs, histories etc.
# for these, I imagine faking a browseParameters entry called something like 'embed'
# that would prevent the HTML wrapping etc
# consider also using a sub name other than "new" for child classes
# -- this would allow a default version of it here for inheritance.
# what to call it though?
}
###########################################################
# Browsing
sub browsePage {
my $self = shift;
#$self->{outputText} .= "fish";
# dont yet see any point in using a class variable to build output
my $text;
$text .= "Content-Type: text/html\n\n" ;
$text .= $self->makePageHeader() ;
$text .= $self->makePageContent();
$text .= $self->makePageFooter();
return $text;
}
sub makePageHeader {
my $class = shift; $class = (ref $class or $class);
my $text ;
$text .= "<!DOCTYPE HTML>\n" ;
$text .= '<html><head><title>', $class->getConfiguration('SiteName'), "</title>\n" ;
# Help! why didn't that work? How are the commas confusing the result of the sub call?
$text .= $class->getConfiguration('SiteName');
$text .= "</title>\n";
$text .= "<body>\n" ;
return $text;
}
sub makePageContent {
my $class = shift; $class = (ref $class or $class);
return "Default Page object\n";
}
sub makePageFooter {
my $class = shift; $class = (ref $class or $class);
my $text ;
$text .= "</body></html>\n" ;
return $text;
}
}
###############################################################################
#
# class WikiPage
#
# Base class for wiki pages.
# should:
# load and parse wiki text
# determine if extra elements are needed: preview, diff, etc
{
package WikiPage;
our @ISA = Page;
WikiPage->register();
###########################################################
# Class conditions
#
# wiki pages have wiki.cgi?pagename
# this works out as {keywords}=pagename
# if it's just wiki.cgi we want the home page.
sub propConditions { q[$browseParameters{keywords} or %browseParameters == undef] }
our $pageName;
sub new {
my $class = shift; $class = (ref $class or $class);
my %browseParameters = @_;
my $self = {};
$pageName = $browseParameters{keywords};
# putting data into the returned instance would make a lot more sense
# we'd lose this hacky class variable $pageName
return bless $self, $class;
}
sub makePageContent {
my $class = shift; $class = (ref $class or $class);
my $text;
if ($pageName eq '') {
$pageName = $class->getConfiguration('HomePage');
}
$text .= "WikiPage class<BR>\n";
$text .= "The name of this page is: '$pageName'<BR>";
return $text;
}
}
###############################################################################
#
# class WikiVersion
#
{
package WikiVersion;
our @ISA = Page;
WikiVersion->register();
###########################################################
# Class conditions
sub propConditions { q[$browseParameters{action} eq 'version'] }
###########################################################
# New
sub new {
my $class = shift; $class = (ref $class or $class);
my $self = {};
return bless $self, $class;
}
###########################################################
# Content
sub makePageContent {
my $class = shift; $class = (ref $class or $class);
return "UseMOO version number\n";
}
}
###############################################################################
{
package UseMooWiki ;
use strict;
use CGI;
use CGI::Carp qw(fatalsToBrowser);
use vars qw( $q $MaxPost $ThisPage );
$q = new CGI;
our $log = '';
{
my %PageVariables = $q->Vars;
# later handle Content-Length etc
print Page->new( %PageVariables )->browsePage();
}
}