if ($config{sslcookie}) {
print $session->header(-charset => 'utf-8',
-cookie => $session->cookie(-httponly => 1, -secure => 1));
- } else {
+ }
+ else {
print $session->header(-charset => 'utf-8',
-cookie => $session->cookie(-httponly => 1));
}
sub redirect ($$) {
my $q=shift;
- my $url=shift;
+ eval q{use URI};
+ my $url=URI->new(shift);
if (! $config{w3mmode}) {
print $q->redirect($url);
}
}
sub decode_cgi_utf8 ($) {
- # decode_form_utf8 method is needed for 5.10
+ # decode_form_utf8 method is needed for 5.01
if ($] < 5.01) {
my $cgi = shift;
foreach my $f ($cgi->param) {
if ($] >= 5.01) {
my $form = shift;
foreach my $f ($form->field) {
+ my @value=map { decode_utf8($_) } $form->field($f);
$form->field(name => $f,
- value => decode_utf8($form->field($f)),
+ value => \@value,
force => 1,
);
}
template => {type => 'div'},
stylesheet => baseurl()."style.css",
);
- my $buttons=["Login"];
-
+ # MITLOGIN: These should be restored when logins are allowed again.
+ #my $buttons=["Login"];
+ my $buttons=[];
+
if ($q->param("do") ne "signin" && !$form->submitted) {
- $form->text(gettext("You need to log in first."));
+ #$form->text(gettext("You need to log in first."));
+ $form->text(
+ "You must have an MIT personal certificate to edit");
}
$form->field(name => "do", type => "hidden", value => "signin",
force => 1);
force => 1);
$form->field(name => "sid", type => "hidden", value => $session->id,
force => 1);
- $form->field(name => "email", size => 50, fieldset => "preferences");
+ #$form->field(name => "email", size => 50, fieldset => "preferences");
+ $form->field(name => "realname", size => 50, fieldset => "preferences");
my $user_name=$session->param("name");
if (! $form->submitted) {
- $form->field(name => "email", force => 1,
- value => userinfo_get($user_name, "email"));
+ #$form->field(name => "email", force => 1,
+ #value => userinfo_get($user_name, "email"));
+ $form->field(name => "realname", force => 1,
+ value => userinfo_get($user_name, "realname"));
}
if ($form->submitted eq 'Logout') {
userinfo_set($user_name, 'email', $form->field('email')) ||
error("failed to set email");
}
-
+ if (defined $form->field('realname')) {
+ userinfo_set($user_name, 'realname', $form->field('realname')) ||
+ error("failed to set realname");
+ }
$form->text(gettext("Preferences saved."));
}
showform($form, $buttons, $session, $q);
}
- sub cgi_custom_failure ($$) {
- my $header=shift;
+ sub cgi_custom_failure ($$$) {
+ my $q=shift;
+ my $httpstatus=shift;
my $message=shift;
- print $header;
+ print $q->header(
+ -status => $httpstatus,
+ -charset => 'utf-8',
+ );
print $message;
# Internet Explod^Hrer won't show custom 404 responses
$session->delete();
cgi_savesession($session);
cgi_custom_failure(
- $q->header(-status => "403 Forbidden"),
+ $q, "403 Forbidden",
gettext("You are banned."));
}
}
use warnings;
use strict;
use IkiWiki;
+use IkiWiki::UserInfo;
use Encode;
use open qw{:utf8 :std};
wrappermode => (defined $config{git_wrappermode} ? $config{git_wrappermode} : "06755"),
};
}
+
+ # Avoid notes, parser does not handle and they only slow things down.
+ $ENV{GIT_NOTES_REF}="";
# Run receive test only if being called by the wrapper, and not
# when generating same.
plugin => {
safe => 0, # rcs plugin
rebuild => undef,
+ section => "rcs",
},
git_wrapper => {
type => "string",
'--', $file);
if ($sha1) {
($sha1) = $sha1 =~ m/($sha1_pattern)/; # sha1 is untainted now
- } else { debug("Empty sha1sum for '$file'.") }
+ }
+ else {
+ debug("Empty sha1sum for '$file'.");
+ }
return defined $sha1 ? $sha1 : q{};
}
my %env=%ENV;
if (defined $user || defined $ipaddr) {
my $u=encode_utf8(defined $user ? $user : $ipaddr);
- $ENV{GIT_AUTHOR_NAME}=$u;
- $ENV{GIT_AUTHOR_EMAIL}="$u\@web";
+ # MITLOGIN This algorithm could be improved
+ $ENV{GIT_AUTHOR_NAME}=IkiWiki::userinfo_get($u, "realname");
+ $ENV{GIT_AUTHOR_EMAIL}="$u\@mit.edu";
}
$message = IkiWiki::possibly_foolish_untaint($message);
# Remove srcdir prefix
$file =~ s/^\Q$config{srcdir}\E\/?//;
- my @sha1s = run_or_non('git', 'rev-list', 'HEAD', '--', $file);
- my $ci = git_commit_info($sha1s[$#sha1s], 1);
- my $ctime = $ci->{'author_epoch'};
+ my @raw_lines = run_or_die('git', 'log',
+ '--follow', '--no-merges',
+ '--pretty=raw', '--raw', '--abbrev=40', '--always', '-c',
+ '-r', '--', $file);
+ my @ci;
+ while (my $parsed = parse_diff_tree("", \@raw_lines)) {
+ push @ci, $parsed;
+ }
+ my $ctime = $ci[$#ci]->{'author_epoch'};
debug("ctime for '$file': ". localtime($ctime));
return $ctime;
use warnings;
use strict;
use IkiWiki 3.00;
+use Data::Dumper;
sub import {
hook(type => "getsetup", id => "httpauth", call => \&getsetup);
hook(type => "auth", id => "httpauth", call => \&auth);
+ hook(type => "formbuilder_setup", id => "httpauth",
+ call => \&formbuilder_setup);
+ hook(type => "canedit", id => "httpauth", call => \&canedit,
+ first => 1);
}
sub getsetup () {
plugin => {
safe => 1,
rebuild => 0,
+ section => "auth",
+ },
+ cgiauthurl => {
+ type => "string",
+ example => "http://example.com/wiki/auth/ikiwiki.cgi",
+ description => "url to redirect to when authentication is needed",
+ safe => 1,
+ rebuild => 0,
+ },
+ httpauth_pagespec => {
+ type => "pagespec",
+ example => "!*/Discussion",
+ description => "PageSpec of pages where only httpauth will be used for authentication",
+ safe => 0,
+ rebuild => 0,
},
}
+
+ sub redir_cgiauthurl ($;@) {
+ my $cgi=shift;
+
+ IkiWiki::redirect($cgi,
+ @_ > 1 ? IkiWiki::cgiurl(cgiurl => $config{cgiauthurl}, @_)
+ : $config{cgiauthurl}."?@_"
+ );
+ exit;
+ }
sub auth ($$) {
my $cgi=shift;
my $session=shift;
if (defined $cgi->remote_user()) {
- $session->param("name", $cgi->remote_user());
+ my $user = $cgi->remote_user();
+ $session->param("name", $user);
+ eval IkiWiki::possibly_foolish_untaint($ENV{SSL_CLIENT_S_DN_CN});
+ my $realname = IkiWiki::userinfo_get($user, "realname");
+ if ((!defined $realname || $realname eq "") &&
+ defined $ENV{SSL_CLIENT_S_DN_CN}) {
+ IkiWiki::userinfo_set($user, "realname", $ENV{SSL_CLIENT_S_DN_CN});
+ }
}
}
+ sub formbuilder_setup (@) {
+ my %params=@_;
+
+ my $form=$params{form};
+ my $session=$params{session};
+ my $cgi=$params{cgi};
+ my $buttons=$params{buttons};
+
+ if ($form->title eq "signin" &&
+ ! defined $cgi->remote_user() && defined $config{cgiauthurl}) {
+ my $button_text="Login with HTTP auth";
+ push @$buttons, $button_text;
+
+ if ($form->submitted && $form->submitted eq $button_text) {
+ # bounce thru cgiauthurl and then back to
+ # the stored postsignin action
+ redir_cgiauthurl($cgi, do => "postsignin");
+ }
+ }
+ }
+
+ sub test_httpauth_pagespec ($) {
+ my $page=shift;
+
+ return (
+ );
+ }
+
+ sub canedit ($$$) {
+ my $page=shift;
+ my $cgi=shift;
+ my $session=shift;
+
+ if (! defined $cgi->remote_user() &&
+ defined $config{httpauth_pagespec} &&
+ length $config{httpauth_pagespec} &&
+ defined $config{cgiauthurl} &&
+ pagespec_match($page, $config{httpauth_pagespec})) {
+ return sub {
+ # bounce thru cgiauthurl and back to edit action
+ redir_cgiauthurl($cgi, $cgi->query_string());
+ };
+ }
+ else {
+ return undef;
+ }
+ }
+
1
plugin => {
safe => 1,
rebuild => 1, # format plugin
+ section => "format",
},
multimarkdown => {
type => "boolean",
if ($@) {
debug(gettext("multimarkdown is enabled, but Text::MultiMarkdown is not installed"));
}
- $markdown_sub=sub {
- Text::MultiMarkdown::markdown(shift, {use_metadata => 0});
+ else {
+ $markdown_sub=sub {
+ Text::MultiMarkdown::markdown(shift, {use_metadata => 0});
+ }
}
}
if (! defined $markdown_sub) {
eval q{use Text::Markdown};
- if (! $@) {
+ if (1) {#! $@) { # Text::Markdown throws this but works. Shrug.
if (Text::Markdown->can('markdown')) {
$markdown_sub=\&Text::Markdown::markdown;
}
plugin => {
safe => 1,
rebuild => 1,
+ section => "core",
},
}
my @pagepath=(split("/", $page));
my $pagedepth=@pagepath;
+
+ # The last element in @pagepath is the page itself, so punt that
+ # (These are /parent/ links, after all.)
+ pop @pagepath;
+
foreach my $dir (@pagepath) {
next if $dir eq 'index';
$depth=$i;
$height=($pagedepth - $depth);
+ $path.="/".$dir;
+ $title=pagetitle($dir);
push @ret, {
url => urlto(bestlink($page, $path), $page),
page => $title,
"depth_$depth" => 1,
"height_$height" => 1,
};
- $path.="/".$dir;
- $title=pagetitle($dir);
$i++;
}
return @ret;
my $page=$params{page};
my $template=$params{template};
- if ($template->query(name => "parentlinks")) {
- $template->param(parentlinks => [parentlinks($page)]);
+ if ($template->query(name => "parentlinks") ||
+ $template->query(name => "has_parentlinks")) {
+ my @links=parentlinks($page);
+ $template->param(parentlinks => \@links);
+ $template->param(has_parentlinks => (@links > 0));
}
}
my @envsave;
push @envsave, qw{REMOTE_ADDR QUERY_STRING REQUEST_METHOD REQUEST_URI
CONTENT_TYPE CONTENT_LENGTH GATEWAY_INTERFACE
- HTTP_COOKIE REMOTE_USER HTTPS REDIRECT_STATUS
+ HTTP_COOKIE REMOTE_USER HTTPS SSL_CLIENT_S_DN_CN REDIRECT_STATUS
REDIRECT_URL} if $config{cgi};
my $envsave="";
foreach my $var (@envsave) {
}
EOF
- my $cc=exists $ENV{CC} ? possibly_foolish_untaint($ENV{CC}) : 'cc';
- if (system($cc, "$wrapper.c", "-o", "$wrapper.new") != 0) {
+ my @cc=exists $ENV{CC} ? possibly_foolish_untaint($ENV{CC}) : 'cc';
+ push @cc, possibly_foolish_untaint($ENV{CFLAGS}) if exists $ENV{CFLAGS};
+ if (system(@cc, "$wrapper.c", "-o", "$wrapper.new") != 0) {
#translators: The parameter is a C filename.
error(sprintf(gettext("failed to compile %s"), "$wrapper.c"));
}
- unlink("$wrapper.c");
if (defined $config{wrappergroup}) {
my $gid=(getgrnam($config{wrappergroup}))[2];
if (! defined $gid) {