#!/usr/bin/env plackup # vim:syntax=perl: # This is a wiki that: # - uses flat-files as a storage system # - uses server-side (SSH+vim) page-editing only; there is no web-based editing (it should only be used when there is a limited group of authors) # - provides no page versioning / history / diffing # # Details: # - the markup language is MultiMarkdown # - serves all files in the current directory as static files # - *.mkd files are converted to HTML via Text::MultiMarkdown # - ".mkd" and "index.mkd" will be appended when appropriate. These are all the same page: # http://localhost:5000/ # http://localhost:5000/index # http://localhost:5000/index.mkd # TODO: # - BUG -- when on a "//" index.mkd-bypass page, and you click on the "parent directory" link, it doesn't go to the parent directory use strict; use warnings; use Plack::App::Directory; use Plack::Util; use Plack::MIME; use Text::MultiMarkdown; use Encode; use Data::Dumper; our $head_insert = do {local $/; }; Plack::MIME->add_type(".mkd" => "text/x-markdown"); my $app = sub { my ($env) = @_; ##==== pre-filter # add "index.mkd" if a directory was requested, and there's an index.mkd inside it # (however, the directory listing can still be retrieved by putting a double-slash on the end of the URL if ($env->{PATH_INFO} =~ /\/$/ && -d "./$env->{PATH_INFO}" && !($env->{PATH_INFO} =~ s/\/\/$/\//) && -e "./$env->{PATH_INFO}/index.mkd") { $env->{PATH_INFO} .= "/index.mkd"; } # add ".mkd" suffix, if that would fix a 404-missing-file, but only when the .mkd'd path actually exists if (! -e "./$env->{PATH_INFO}" && -e "./$env->{PATH_INFO}.mkd") { $env->{PATH_INFO} .= ".mkd"; } ##==== have Plack::App::Directory and Plack::App::File do their thing my $res = Plack::App::Directory->new(root => ".")->to_app->($env); ##==== post-filter Plack::Util::response_cb($res, sub { my $res = shift; my $ct = Plack::Util::header_get( $res->[1], 'Content-Type' ); if ($ct =~ m#^text/x-markdown(?:;.*)?#) { # do markup=>HTML conversion my $markup = join '', $res->[2]->getlines(); my $html = Text::MultiMarkdown::markdown($markup, { use_wikilinks => 1, document_format => 'complete', }); $html =~ s/(]*>)/$1\n$head_insert/s; $res->[2] = [ $html ]; Plack::Util::header_set( $res->[1], 'Content-Type' => 'text/html; charset=utf-8' ); Plack::Util::header_set( $res->[1], 'Content-Length' => length(Encode::encode_utf8($html)) ); } return; }); }; #### vv this will be inserted just after in every .mkd => .html conversion vv #### __DATA__