summaryrefslogtreecommitdiff
path: root/IkiWiki
diff options
context:
space:
mode:
Diffstat (limited to 'IkiWiki')
-rw-r--r--IkiWiki/Plugin/brokenlinks.pm2
-rw-r--r--IkiWiki/Plugin/comments.pm11
-rw-r--r--IkiWiki/Plugin/editpage.pm3
-rw-r--r--IkiWiki/Plugin/format.pm28
-rw-r--r--IkiWiki/Plugin/goto.pm6
-rw-r--r--IkiWiki/Plugin/highlight.pm143
-rw-r--r--IkiWiki/Plugin/inline.pm2
-rw-r--r--IkiWiki/Plugin/listdirectives.pm2
-rw-r--r--IkiWiki/Plugin/opendiscussion.pm2
-rw-r--r--IkiWiki/Plugin/orphans.pm2
-rw-r--r--IkiWiki/Plugin/pagecount.pm9
-rw-r--r--IkiWiki/Plugin/rename.pm8
-rw-r--r--IkiWiki/Render.pm4
-rw-r--r--IkiWiki/Setup/Automator.pm23
14 files changed, 222 insertions, 23 deletions
diff --git a/IkiWiki/Plugin/brokenlinks.pm b/IkiWiki/Plugin/brokenlinks.pm
index da97dbc28..cf8f25281 100644
--- a/IkiWiki/Plugin/brokenlinks.pm
+++ b/IkiWiki/Plugin/brokenlinks.pm
@@ -30,7 +30,7 @@ sub preprocess (@) {
my %broken;
foreach my $page (pagespec_match_list([keys %links],
$params{pages}, location => $params{page})) {
- my $discussion=gettext("discussion");
+ my $discussion=gettext("Discussion");
my %seen;
foreach my $link (@{$links{$page}}) {
next if $seen{$link};
diff --git a/IkiWiki/Plugin/comments.pm b/IkiWiki/Plugin/comments.pm
index e618d1a90..517e16f9f 100644
--- a/IkiWiki/Plugin/comments.pm
+++ b/IkiWiki/Plugin/comments.pm
@@ -21,6 +21,8 @@ my %commentstate;
sub import {
hook(type => "checkconfig", id => 'comments', call => \&checkconfig);
hook(type => "getsetup", id => 'comments', call => \&getsetup);
+ hook(type => "preprocess", id => 'comment', call => \&preprocess);
+ # here for backwards compatability with old comments
hook(type => "preprocess", id => '_comment', call => \&preprocess);
hook(type => "sessioncgi", id => 'comment', call => \&sessioncgi);
hook(type => "htmlize", id => "_comment", call => \&htmlize);
@@ -287,10 +289,15 @@ sub editcomment ($$) {
else {
$type = $config{default_pageext};
}
+
+
my @page_types;
if (exists $IkiWiki::hooks{htmlize}) {
- @page_types = grep { ! /^_/ } keys %{$IkiWiki::hooks{htmlize}};
+ foreach my $key (grep { !/^_/ } keys %{$IkiWiki::hooks{htmlize}}) {
+ push @page_types, [$key, $IkiWiki::hooks{htmlize}{$key}{longname} || $key];
+ }
}
+ @page_types=sort @page_types;
$form->field(name => 'do', type => 'hidden');
$form->field(name => 'sid', type => 'hidden', value => $session->id,
@@ -372,7 +379,7 @@ sub editcomment ($$) {
my $location=unique_comment_location($page, $config{srcdir});
- my $content = "[[!_comment format=$type\n";
+ my $content = "[[!comment format=$type\n";
# FIXME: handling of double quotes probably wrong?
if (defined $session->param('name')) {
diff --git a/IkiWiki/Plugin/editpage.pm b/IkiWiki/Plugin/editpage.pm
index af42097ba..467cd9ed5 100644
--- a/IkiWiki/Plugin/editpage.pm
+++ b/IkiWiki/Plugin/editpage.pm
@@ -230,7 +230,7 @@ sub cgi_editpage ($$) {
$dir=~s![^/]+/+$!!;
if ((defined $form->field('subpage') && length $form->field('subpage')) ||
- $page eq gettext('discussion')) {
+ $page eq lc(gettext('Discussion'))) {
$best_loc="$from/$page";
}
else {
@@ -280,6 +280,7 @@ sub cgi_editpage ($$) {
push @page_types, [$key, $hooks{htmlize}{$key}{longname} || $key];
}
}
+ @page_types=sort @page_types;
$form->tmpl_param("page_select", 1);
$form->field(name => "page", type => 'select',
diff --git a/IkiWiki/Plugin/format.pm b/IkiWiki/Plugin/format.pm
index bbe3aa9fe..1513cbed7 100644
--- a/IkiWiki/Plugin/format.pm
+++ b/IkiWiki/Plugin/format.pm
@@ -10,21 +10,33 @@ sub import {
}
sub preprocess (@) {
- my $format=$_[0];
- shift; shift;
- my $text=$_[0];
- shift; shift;
my %params=@_;
+ my $format=shift;
+ shift;
+ my $text=IkiWiki::preprocess($params{page}, $params{destpage}, shift);
+ shift;
if (! defined $format || ! defined $text) {
error(gettext("must specify format and text"));
}
- elsif (! exists $IkiWiki::hooks{htmlize}{$format}) {
- error(sprintf(gettext("unsupported page format %s"), $format));
+ elsif (exists $IkiWiki::hooks{htmlize}{$format}) {
+ return IkiWiki::htmlize($params{page}, $params{destpage},
+ $format, $text);
}
+ else {
+ # Other plugins can register htmlizefallback
+ # hooks to add support for page types
+ # not suitable for htmlize. Try them until
+ # one succeeds.
+ my $ret;
+ IkiWiki::run_hooks(htmlizefallback => sub {
+ $ret=shift->($format, $text)
+ unless defined $ret;
+ });
+ return $ret if defined $ret;
- return IkiWiki::htmlize($params{page}, $params{destpage}, $format,
- IkiWiki::preprocess($params{page}, $params{destpage}, $text));
+ error(sprintf(gettext("unsupported page format %s"), $format));
+ }
}
1
diff --git a/IkiWiki/Plugin/goto.pm b/IkiWiki/Plugin/goto.pm
index 3f40c5859..2e2dc04a1 100644
--- a/IkiWiki/Plugin/goto.pm
+++ b/IkiWiki/Plugin/goto.pm
@@ -32,6 +32,12 @@ sub cgi_goto ($;$) {
}
}
+ # It's possible that $page is not a valid page name;
+ # if so attempt to turn it into one.
+ if ($page !~ /$config{wiki_file_regexp}/) {
+ $page=titlepage($page);
+ }
+
IkiWiki::loadindex();
# If the page is internal (like a comment), see if it has a
diff --git a/IkiWiki/Plugin/highlight.pm b/IkiWiki/Plugin/highlight.pm
new file mode 100644
index 000000000..20f79ef57
--- /dev/null
+++ b/IkiWiki/Plugin/highlight.pm
@@ -0,0 +1,143 @@
+#!/usr/bin/perl
+package IkiWiki::Plugin::highlight;
+
+use warnings;
+use strict;
+use IkiWiki 3.00;
+
+# locations of highlight's files
+my $filetypes="/etc/highlight/filetypes.conf";
+my $langdefdir="/usr/share/highlight/langDefs";
+
+sub import {
+ hook(type => "getsetup", id => "highlight", call => \&getsetup);
+ hook(type => "checkconfig", id => "highlight", call => \&checkconfig);
+ # this hook is used by the format plugin
+ hook(type => "htmlizefallback", id => "highlight", call =>
+ \&htmlizefallback);
+}
+
+sub getsetup () {
+ return
+ plugin => {
+ safe => 1,
+ rebuild => 1, # format plugin
+ },
+ tohighlight => {
+ type => "string",
+ example => ".c .h .cpp .pl .py Makefile:make",
+ description => "types of source files to syntax highlight",
+ safe => 1,
+ rebuild => 1,
+ },
+}
+
+sub checkconfig () {
+ if (exists $config{tohighlight}) {
+ foreach my $file (split ' ', $config{tohighlight}) {
+ my @opts = $file=~s/^\.// ?
+ (keepextension => 1) :
+ (noextension => 1);
+ my $ext = $file=~s/:(.*)// ? $1 : $file;
+
+ my $langfile=ext2langfile($ext);
+ if (! defined $langfile) {
+ error(sprintf(gettext(
+ "tohighlight contains unknown file type '%s'"),
+ $ext));
+ }
+
+ hook(
+ type => "htmlize",
+ id => $file,
+ call => sub {
+ my %params=@_;
+ highlight($langfile, $params{content});
+ },
+ longname => sprintf(gettext("Source code: %s"), $file),
+ @opts,
+ );
+ }
+ }
+}
+
+sub htmlizefallback {
+ my $format=lc shift;
+ my $langfile=ext2langfile($format);
+
+ if (! defined $langfile) {
+ return;
+ }
+
+ return highlight($langfile, shift);
+}
+
+my %ext2lang;
+my $filetypes_read=0;
+my %highlighters;
+
+# Parse highlight's config file to get extension => language mappings.
+sub read_filetypes () {
+ open (IN, $filetypes);
+ while (<IN>) {
+ chomp;
+ if (/^\$ext\((.*)\)=(.*)$/) {
+ $ext2lang{$_}=$1 foreach $1, split ' ', $2;
+ }
+ }
+ close IN;
+ $filetypes_read=1;
+}
+
+
+# Given a filename extension, determines the language definition to
+# use to highlight it.
+sub ext2langfile ($) {
+ my $ext=shift;
+
+ my $langfile="$langdefdir/$ext.lang";
+ return $langfile if exists $highlighters{$langfile};
+
+ read_filetypes() unless $filetypes_read;
+ if (exists $ext2lang{$ext}) {
+ return "$langdefdir/$ext2lang{$ext}.lang";
+ }
+ # If a language only has one common extension, it will not
+ # be listed in filetypes, so check the langfile.
+ elsif (-e $langfile) {
+ return $langfile;
+ }
+ else {
+ return undef;
+ }
+}
+
+# Interface to the highlight C library.
+sub highlight ($$) {
+ my $langfile=shift;
+ my $input=shift;
+
+ eval q{use highlight};
+ if ($@) {
+ print STDERR gettext("warning: highlight perl module not available; falling back to pass through");
+ return $input;
+ }
+
+ my $gen;
+ if (! exists $highlighters{$langfile}) {
+ $gen = highlightc::CodeGenerator_getInstance($highlightc::XHTML);
+ $gen->setFragmentCode(1); # generate html fragment
+ $gen->setHTMLEnclosePreTag(1); # include stylish <pre>
+ $gen->initTheme("/dev/null"); # theme is not needed because CSS is not emitted
+ $gen->initLanguage($langfile); # must come after initTheme
+ $gen->setEncoding("utf-8");
+ $highlighters{$langfile}=$gen;
+ }
+ else {
+ $gen=$highlighters{$langfile};
+ }
+
+ return $gen->generateString($input);
+}
+
+1
diff --git a/IkiWiki/Plugin/inline.pm b/IkiWiki/Plugin/inline.pm
index 27ea1c4a6..9d5ebc34d 100644
--- a/IkiWiki/Plugin/inline.pm
+++ b/IkiWiki/Plugin/inline.pm
@@ -354,7 +354,7 @@ sub preprocess_inline (@) {
my $file = $pagesources{$page};
my $type = pagetype($file);
if ($config{discussion}) {
- my $discussionlink=gettext("discussion");
+ my $discussionlink=lc(gettext("Discussion"));
if ($page !~ /.*\/\Q$discussionlink\E$/ &&
(length $config{cgiurl} ||
exists $links{$page."/".$discussionlink})) {
diff --git a/IkiWiki/Plugin/listdirectives.pm b/IkiWiki/Plugin/listdirectives.pm
index d2cebca34..bd73f1a04 100644
--- a/IkiWiki/Plugin/listdirectives.pm
+++ b/IkiWiki/Plugin/listdirectives.pm
@@ -45,7 +45,7 @@ sub checkconfig () {
sub needsbuild (@) {
my $needsbuild=shift;
- @fulllist = sort keys %{$IkiWiki::hooks{preprocess}};
+ @fulllist = grep { ! /^_/ } sort keys %{$IkiWiki::hooks{preprocess}};
@shortlist = grep { ! $IkiWiki::hooks{preprocess}{$_}{shortcut} } @fulllist;
$pluginstring = join(' ', @shortlist) . " : " . join(' ', @fulllist);
diff --git a/IkiWiki/Plugin/opendiscussion.pm b/IkiWiki/Plugin/opendiscussion.pm
index 3da01efee..60b193eca 100644
--- a/IkiWiki/Plugin/opendiscussion.pm
+++ b/IkiWiki/Plugin/opendiscussion.pm
@@ -23,7 +23,7 @@ sub canedit ($$) {
my $cgi=shift;
my $session=shift;
- my $discussion=gettext("discussion");
+ my $discussion=lc(gettext("Discussion"));
return "" if $page=~/(\/|^)\Q$discussion\E$/;
return undef;
}
diff --git a/IkiWiki/Plugin/orphans.pm b/IkiWiki/Plugin/orphans.pm
index cf74c9b79..944eba541 100644
--- a/IkiWiki/Plugin/orphans.pm
+++ b/IkiWiki/Plugin/orphans.pm
@@ -34,7 +34,7 @@ sub preprocess (@) {
}
my @orphans;
- my $discussion=gettext("discussion");
+ my $discussion=lc(gettext("Discussion"));
foreach my $page (pagespec_match_list(
[ grep { ! $linkedto{$_} && $_ ne 'index' }
keys %pagesources ],
diff --git a/IkiWiki/Plugin/pagecount.pm b/IkiWiki/Plugin/pagecount.pm
index 1955603b0..5a2301af4 100644
--- a/IkiWiki/Plugin/pagecount.pm
+++ b/IkiWiki/Plugin/pagecount.pm
@@ -26,8 +26,13 @@ sub preprocess (@) {
# register a dependency.
add_depends($params{page}, $params{pages});
- my @pages=pagespec_match_list([keys %pagesources], $params{pages}, location => $params{page})
- if $params{pages} ne "*"; # optimisation;
+ my @pages;
+ if ($params{pages} eq "*") {
+ @pages=keys %pagesources;
+ }
+ else {
+ @pages=pagespec_match_list([keys %pagesources], $params{pages}, location => $params{page});
+ }
return $#pages+1;
}
diff --git a/IkiWiki/Plugin/rename.pm b/IkiWiki/Plugin/rename.pm
index 8dad92be3..d0e5894dc 100644
--- a/IkiWiki/Plugin/rename.pm
+++ b/IkiWiki/Plugin/rename.pm
@@ -137,14 +137,16 @@ sub rename_form ($$$) {
# insert the standard extensions
my @page_types;
if (exists $IkiWiki::hooks{htmlize}) {
- @page_types=grep { !/^_/ }
- keys %{$IkiWiki::hooks{htmlize}};
+ foreach my $key (grep { !/^_/ } keys %{$IkiWiki::hooks{htmlize}}) {
+ push @page_types, [$key, $IkiWiki::hooks{htmlize}{$key}{longname} || $key];
+ }
}
+ @page_types=sort @page_types;
# make sure the current extension is in the list
my ($ext) = $pagesources{$page}=~/\.([^.]+)$/;
if (! $IkiWiki::hooks{htmlize}{$ext}) {
- unshift(@page_types, $ext);
+ unshift(@page_types, [$ext, $ext]);
}
$f->field(name => "type", type => 'select',
diff --git a/IkiWiki/Render.pm b/IkiWiki/Render.pm
index adae9f0d5..f4de19378 100644
--- a/IkiWiki/Render.pm
+++ b/IkiWiki/Render.pm
@@ -76,7 +76,7 @@ sub genpage ($$) {
$actions++;
}
if ($config{discussion}) {
- my $discussionlink=gettext("discussion");
+ my $discussionlink=lc(gettext("Discussion"));
if ($page !~ /.*\/\Q$discussionlink\E$/ &&
(length $config{cgiurl} ||
exists $links{$page."/".$discussionlink})) {
@@ -146,7 +146,7 @@ sub scan ($) {
if ($config{discussion}) {
# Discussion links are a special case since they're
# not in the text of the page, but on its template.
- $links{$page}=[ $page."/".gettext("discussion") ];
+ $links{$page}=[ $page."/".lc(gettext("Discussion")) ];
}
else {
$links{$page}=[];
diff --git a/IkiWiki/Setup/Automator.pm b/IkiWiki/Setup/Automator.pm
index 5111541e4..742d67666 100644
--- a/IkiWiki/Setup/Automator.pm
+++ b/IkiWiki/Setup/Automator.pm
@@ -98,6 +98,29 @@ sub import (@) {
}
}
+ # Make sure that all the listed plugins can load
+ # and checkconfig is ok. If a plugin fails to work,
+ # remove it from the configuration and keep on truckin'.
+ my %bakconfig=%config; # checkconfig can modify %config so back up
+ if (! eval { IkiWiki::loadplugins(); IkiWiki::checkconfig() }) {
+ foreach my $plugin (@{$config{default_plugins}}, @{$bakconfig{add_plugins}}) {
+ eval {
+ # delete all hooks so that only this plugins's
+ # checkconfig will be run
+ %IkiWiki::hooks=();
+ IkiWiki::loadplugin($plugin);
+ IkiWiki::run_hooks(checkconfig => sub { shift->() });
+ };
+ if ($@) {
+ print STDERR sprintf(gettext("** Disabling plugin %s, since it is failing with this message:"),
+ $plugin)."\n";
+ print STDERR "$@\n";
+ push @{$bakconfig{disable_plugins}}, $plugin;
+ }
+ }
+ }
+ %config=%bakconfig;
+
# Generate setup file.
require IkiWiki::Setup;
IkiWiki::Setup::dump($config{dumpsetup});