]> sipb.mit.edu Git - ikiwiki.git/blobdiff - IkiWiki.pm
parameterized indent
[ikiwiki.git] / IkiWiki.pm
index cd93fe969de8a38b4356ad041ba7c1cf6de3b801..241fb45b7f09cfdbab4cf285fd63f78406ee5b4e 100644 (file)
@@ -7,7 +7,7 @@ use strict;
 use Encode;
 use HTML::Entities;
 use URI::Escape q{uri_escape_utf8};
-use POSIX;
+use POSIX ();
 use Storable;
 use open qw{:utf8 :std};
 
@@ -20,7 +20,7 @@ use Exporter q{import};
 our @EXPORT = qw(hook debug error template htmlpage deptype
                  add_depends pagespec_match pagespec_match_list bestlink
                 htmllink readfile writefile pagetype srcfile pagename
-                displaytime will_render gettext urlto targetpage
+                displaytime will_render gettext ngettext urlto targetpage
                 add_underlay pagetitle titlepage linkpage newpagefile
                 inject add_link
                  %config %links %pagestate %wikistate %renderedfiles
@@ -334,11 +334,20 @@ sub getsetup () {
                safe => 0, # paranoia
                rebuild => 0,
        },
+       include => {
+               type => "string",
+               default => undef,
+               example => '^\.htaccess$',
+               description => "regexp of normally excluded files to include",
+               advanced => 1,
+               safe => 0, # regexp
+               rebuild => 1,
+       },
        exclude => {
                type => "string",
                default => undef,
-               example => '\.wav$',
-               description => "regexp of source files to ignore",
+               example => '^(*\.private|Makefile)$',
+               description => "regexp of files that should be skipped",
                advanced => 1,
                safe => 0, # regexp
                rebuild => 1,
@@ -409,6 +418,13 @@ sub getsetup () {
                safe => 0,
                rebuild => 0,
        },
+       clean => {
+               type => "internal",
+               default => 0,
+               description => "running in clean mode",
+               safe => 0,
+               rebuild => 0,
+       },
        refresh => {
                type => "internal",
                default => 0,
@@ -451,6 +467,13 @@ sub getsetup () {
                safe => 0,
                rebuild => 0,
        },
+       setuptype => {
+               type => "internal",
+               default => "IkiWiki::Setup::Standard",
+               description => "perl class to use to dump setup file",
+               safe => 0,
+               rebuild => 0,
+       },
        allow_symlinks_before_srcdir => {
                type => "boolean",
                default => 0,
@@ -881,7 +904,7 @@ sub bestlink ($$) {
                $l.="/" if length $l;
                $l.=$link;
 
-               if (exists $links{$l}) {
+               if (exists $pagesources{$l}) {
                        return $l;
                }
                elsif (exists $pagecase{lc $l}) {
@@ -891,7 +914,7 @@ sub bestlink ($$) {
 
        if (length $config{userdir}) {
                my $l = "$config{userdir}/".lc($link);
-               if (exists $links{$l}) {
+               if (exists $pagesources{$l}) {
                        return $l;
                }
                elsif (exists $pagecase{lc $l}) {
@@ -941,7 +964,12 @@ sub linkpage ($) {
 sub cgiurl (@) {
        my %params=@_;
 
-       return $config{cgiurl}."?".
+       my $cgiurl=$config{cgiurl};
+       if (exists $params{cgiurl}) {
+               $cgiurl=$params{cgiurl};
+               delete $params{cgiurl};
+       }
+       return $cgiurl."?".
                join("&", map $_."=".uri_escape_utf8($params{$_}), keys %params);
 }
 
@@ -1081,16 +1109,20 @@ sub htmllink ($$$;@) {
        }
 
        my @attrs;
-       if (defined $opts{rel}) {
-               push @attrs, ' rel="'.$opts{rel}.'"';
-       }
-       if (defined $opts{class}) {
-               push @attrs, ' class="'.$opts{class}.'"';
+       foreach my $attr (qw{rel class title}) {
+               if (defined $opts{$attr}) {
+                       push @attrs, " $attr=\"$opts{$attr}\"";
+               }
        }
 
        return "<a href=\"$bestlink\"@attrs>$linktext</a>";
 }
 
+sub userpage ($) {
+       my $user=shift;
+       return length $config{userdir} ? "$config{userdir}/$user" : $user;
+}
+
 sub openiduser ($) {
        my $user=shift;
 
@@ -1099,11 +1131,10 @@ sub openiduser ($) {
                my $display;
 
                if (Net::OpenID::VerifiedIdentity->can("DisplayOfURL")) {
-                       # this works in at least 2.x
                        $display = Net::OpenID::VerifiedIdentity::DisplayOfURL($user);
                }
                else {
-                       # this only works in 1.x
+                       # backcompat with old version
                        my $oid=Net::OpenID::VerifiedIdentity->new(identity => $user);
                        $display=$oid->display;
                }
@@ -1116,7 +1147,7 @@ sub openiduser ($) {
                # Convert "http://somehost.com/user" to "user [somehost.com]".
                # (also "https://somehost.com/user/")
                if ($display !~ /\[/) {
-                       $display=~s/^https?:\/\/(.+)\/([^\/]+)\/?$/$2 [$1]/;
+                       $display=~s/^https?:\/\/(.+)\/([^\/#?]+)\/?(?:[#?].*)?$/$2 [$1]/;
                }
                $display=~s!^https?://!!; # make sure this is removed
                eval q{use CGI 'escapeHTML'};
@@ -1126,23 +1157,6 @@ sub openiduser ($) {
        return;
 }
 
-sub userlink ($) {
-       my $user=shift;
-
-       my $oiduser=eval { openiduser($user) };
-       if (defined $oiduser) {
-               return "<a href=\"$user\">$oiduser</a>";
-       }
-       else {
-               eval q{use CGI 'escapeHTML'};
-               error($@) if $@;
-
-               return htmllink("", "", escapeHTML(
-                       length $config{userdir} ? $config{userdir}."/".$user : $user
-               ), noimageinline => 1);
-       }
-}
-
 sub htmlize ($$$$) {
        my $page=shift;
        my $destpage=shift;
@@ -1229,7 +1243,7 @@ sub preprocess ($$$;$$) {
                                (?:
                                        """(.*?)"""     # 2: triple-quoted value
                                |
-                                       "([^"]+)"       # 3: single-quoted value
+                                       "([^"]*?)"      # 3: single-quoted value
                                |
                                        (\S+)           # 4: unquoted value
                                )
@@ -1315,7 +1329,7 @@ sub preprocess ($$$;$$) {
                                        (?:
                                                """.*?"""       # triple-quoted value
                                                |
-                                               "[^"]+"         # single-quoted value
+                                               "[^"]*?"        # single-quoted value
                                                |
                                                [^"\s\]]+       # unquoted value
                                        )
@@ -1338,7 +1352,7 @@ sub preprocess ($$$;$$) {
                                        (?:
                                                """.*?"""       # triple-quoted value
                                                |
-                                               "[^"]+"         # single-quoted value
+                                               "[^"]*?"        # single-quoted value
                                                |
                                                [^"\s\]]+       # unquoted value
                                        )
@@ -1408,7 +1422,7 @@ sub check_content (@) {
                my %old=map { $_ => 1 }
                        split("\n", readfile(srcfile($pagesources{$params{page}})));
                foreach my $line (split("\n", $params{content})) {
-                       push @diff, $line if ! exists $old{$_};
+                       push @diff, $line if ! exists $old{$line};
                }
                $params{diff}=join("\n", @diff);
        }
@@ -1812,6 +1826,7 @@ sub deptype (@) {
        return $deptype;
 }
 
+my $file_prune_regexp;
 sub file_pruned ($;$) {
        my $file=shift;
        if (@_) {
@@ -1822,34 +1837,52 @@ sub file_pruned ($;$) {
                $file =~ s#^\Q$base\E/+##;
        }
 
-       my $regexp='('.join('|', @{$config{wiki_file_prune_regexps}}).')';
-       return $file =~ m/$regexp/;
+       if (defined $config{include} && length $config{include}) {
+               return 0 if $file =~ m/$config{include}/;
+       }
+
+       if (! defined $file_prune_regexp) {
+               $file_prune_regexp='('.join('|', @{$config{wiki_file_prune_regexps}}).')';
+               $file_prune_regexp=qr/$file_prune_regexp/;
+       }
+       return $file =~ m/$file_prune_regexp/;
 }
 
 sub define_gettext () {
        # If translation is needed, redefine the gettext function to do it.
        # Otherwise, it becomes a quick no-op.
-       no warnings 'redefine';
+       my $gettext_obj;
+       my $getobj;
        if ((exists $ENV{LANG} && length $ENV{LANG}) ||
            (exists $ENV{LC_ALL} && length $ENV{LC_ALL}) ||
            (exists $ENV{LC_MESSAGES} && length $ENV{LC_MESSAGES})) {
-               *gettext=sub {
-                       my $gettext_obj=eval q{
+               $getobj=sub {
+                       $gettext_obj=eval q{
                                use Locale::gettext q{textdomain};
                                Locale::gettext->domain('ikiwiki')
                        };
-
-                       if ($gettext_obj) {
-                               $gettext_obj->get(shift);
-                       }
-                       else {
-                               return shift;
-                       }
                };
        }
-       else {
-               *gettext=sub { return shift };
-       }
+
+       no warnings 'redefine';
+       *gettext=sub {
+               $getobj->() if $getobj;
+               if ($gettext_obj) {
+                       $gettext_obj->get(shift);
+               }
+               else {
+                       return shift;
+               }
+       };
+       *ngettext=sub {
+               $getobj->() if $getobj;
+               if ($gettext_obj) {
+                       $gettext_obj->nget(@_);
+               }
+               else {
+                       return ($_[2] == 1 ? $_[0] : $_[1])
+               }
+       };
 }
 
 sub gettext {
@@ -1857,6 +1890,11 @@ sub gettext {
        gettext(@_);
 }
 
+sub ngettext {
+       define_gettext();
+       ngettext(@_);
+}
+
 sub yesno ($) {
        my $val=shift;
 
@@ -2071,7 +2109,7 @@ use overload (
        '""'    => sub { $_[0][0] },
        '0+'    => sub { 0 },
        '!'     => sub { bless $_[0], 'IkiWiki::SuccessReason'},
-       '&'     => sub { $_[0]->merge_influences($_[1]); $_[0] },
+       '&'     => sub { $_[0]->merge_influences($_[1], 1); $_[0] },
        '|'     => sub { $_[1]->merge_influences($_[0]); $_[1] },
        fallback => 1,
 );
@@ -2084,7 +2122,7 @@ use overload (
        '""'    => sub { $_[0][0] },
        '0+'    => sub { 1 },
        '!'     => sub { bless $_[0], 'IkiWiki::FailReason'},
-       '&'     => sub { $_[1]->merge_influences($_[0]); $_[1] },
+       '&'     => sub { $_[1]->merge_influences($_[0], 1); $_[1] },
        '|'     => sub { $_[0]->merge_influences($_[1]); $_[0] },
        fallback => 1,
 );
@@ -2110,8 +2148,17 @@ sub influences_static {
 sub merge_influences {
        my $this=shift;
        my $other=shift;
-       foreach my $influence (keys %{$other->[1]}) {
-               $this->[1]{$influence} |= $other->[1]{$influence};
+       my $anded=shift;
+
+       if (! $anded || (($this || %{$this->[1]}) &&
+                       ($other || %{$other->[1]}))) {
+               foreach my $influence (keys %{$other->[1]}) {
+                       $this->[1]{$influence} |= $other->[1]{$influence};
+               }
+       }
+       else {
+               # influence blocker
+               $this->[1]={};
        }
 }
 
@@ -2168,7 +2215,7 @@ sub match_link ($$;@) {
        my $from=exists $params{location} ? $params{location} : '';
 
        my $links = $IkiWiki::links{$page};
-       return IkiWiki::FailReason->new("$page has no links")
+       return IkiWiki::FailReason->new("$page has no links", "" => 1)
                unless $links && @{$links};
        my $bestlink = IkiWiki::bestlink($from, $link);
        foreach my $p (@{$links}) {
@@ -2266,11 +2313,13 @@ sub match_user ($$;@) {
        my $user=shift;
        my %params=@_;
        
+       my $regexp=IkiWiki::glob2re($user);
+       
        if (! exists $params{user}) {
                return IkiWiki::ErrorReason->new("no user specified");
        }
 
-       if (defined $params{user} && lc $params{user} eq lc $user) {
+       if (defined $params{user} && $params{user}=~/^$regexp$/i) {
                return IkiWiki::SuccessReason->new("user is $user");
        }
        elsif (! defined $params{user}) {