+Copy the templates found in F<templates/factory> into the F<beer/factory>
+directory off the web root. When the designers get back to you with custom
+templates, they are to go in F<beer/custom>. If you need to override templates
+on a database-table-by-table basis, put the new template in F<beer/I<table>>.
+
+This will automatically give you C<add>, C<edit>, C<list>, C<view> and C<delete>
+commands; for instance, to see a list of breweries, go to
+
+ http://your.site/beer/brewery/list
+
+For more information about how the system works and how to extend it,
+see L<Maypole>.
+
+=head1 Implementation
+
+This class overrides a set of methods in the base Maypole class to provide its
+functionality. See L<Maypole> for these:
+
+=over
+
+=item get_request
+
+=cut
+
+sub get_request {
+ my ($self, $r) = @_;
+ my $request_options = $self->config->request_options || {};
+ my $ar;
+ if ($MODPERL2) {
+ $ar = eval {require Apache2::Request} ? Apache2::Request->new($r,%{$request_options}) : $r;
+ }
+ else { $ar = Apache::Request->instance($r,%{$request_options}); }
+ $self->ar($ar);
+}
+
+=item warn
+
+=cut
+
+sub warn {
+ my ($self,@args) = @_;
+ my ($package, $line) = (caller)[0,2];
+ my $ar = $self->parent ? $self->parent->{ar} : $self->{ar};
+ if ( $args[0] and ref $self ) {
+ $ar->warn("[$package line $line] ", @args) ;
+ } else {
+ print "warn called by ", caller, " with ", @_, "\n";
+ }
+ return;
+}
+
+
+=item parse_location
+
+=cut
+
+sub parse_location {
+ my $self = shift;
+
+ # Reconstruct the request headers
+ $self->headers_in(Maypole::Headers->new);
+
+ my %headers;
+ if ($MODPERL2) { %headers = %{$self->ar->headers_in};
+ } else { %headers = $self->ar->headers_in; }
+ for (keys %headers) {
+ $self->headers_in->set($_, $headers{$_});
+ }
+
+ $self->preprocess_location();
+
+ my $path = $self->ar->uri;
+ my $base = URI->new($self->config->uri_base);
+ my $loc = $base->path;
+
+ {
+ no warnings 'uninitialized';
+ $path .= '/' if $path eq $loc;
+ if ($loc =~ /\/$/) {
+ $path =~ s/^($loc)?//;
+ } else {
+ $path =~ s/^($loc)?\///;
+ }
+ }
+
+ $self->path($path);
+ $self->parse_path;
+ $self->parse_args;
+}
+
+=item parse_args
+
+=cut
+
+sub parse_args {
+ my $self = shift;
+ $self->params( { $self->_mod_perl_args( $self->ar ) } );
+ $self->query( $self->params );
+}
+
+=item redirect_request
+
+Sets output headers to redirect based on the arguments provided
+
+Accepts either a single argument of the full url to redirect to, or a hash of
+named parameters :
+
+$r->redirect_request('http://www.example.com/path');
+
+or
+
+$r->redirect_request(protocol=>'https', domain=>'www.example.com', path=>'/path/file?arguments', status=>'302', url=>'..');
+
+The named parameters are protocol, domain, path, status and url
+
+Only 1 named parameter is required but other than url, they can be combined as
+required and current values (from the request) will be used in place of any
+missing arguments. The url argument must be a full url including protocol and
+can only be combined with status.
+
+=cut