X-Git-Url: http://git.freeside.biz/gitweb/?p=freeside.git;a=blobdiff_plain;f=rt%2Fhtml%2Fautohandler;h=b2a407add470b7209e01a4478a7fe21e47ec44b7;hp=ce8b7569e1ffffdbd8972bd7727e8e59a3a99952;hb=289340780927b5bac2c7604d7317c3063c6dd8cc;hpb=945721f48f74d5cfffef7c7cf3a3d6bc2521f5dd diff --git a/rt/html/autohandler b/rt/html/autohandler index ce8b7569e..b2a407add 100644 --- a/rt/html/autohandler +++ b/rt/html/autohandler @@ -27,18 +27,24 @@ $RT::Handle->ForceRollback() if $RT::Handle->TransactionDepth; -local *session; +local *session unless $m->is_subrequest; # avoid reentrancy, as suggested by masonbook + +# Disable AutoFlush using an attribute +if ($m->request_comp->attr_exists('AutoFlush')) { + $m->autoflush($m->request_comp->attr('AutoFlush')); +} + %ARGS = map { - # if they've passed multiple values, they'll be an array. if they've passed just one, a scalar - # whatever they are, mark them as utf8 + # if they've passed multiple values, they'll be an array. if they've + # passed just one, a scalar whatever they are, mark them as utf8 my $type = ref($_); (!$type) ? Encode::decode(utf8 => $_, Encode::FB_PERLQQ) : - ($type eq 'ARRAY') + ($type eq 'ARRAY') ? [ map { ref($_) ? $_ : Encode::decode(utf8 => $_, Encode::FB_PERLQQ) } @$_ ] : - ($type eq 'HASH') + ($type eq 'HASH') ? { map { ref($_) ? $_ : Encode::decode(utf8 => $_, Encode::FB_PERLQQ) } %$_ } : $_ -} %ARGS; + } %ARGS; if ($ARGS{'Debug'}) { require Time::HiRes; @@ -65,69 +71,95 @@ if ($m->base_comp->path =~ '^/+NoAuth/' || $m->abort(); } -# If RT is configured for external auth, let's get REMOTE_USER -elsif ($RT::WebExternalAuth and length($ENV{'REMOTE_USER'})) { - my $orig_user = $user; - - $user = $ENV{'REMOTE_USER'}; - $session{'CurrentUser'} = RT::CurrentUser->new(); - my $load_method = $RT::WebExternalGecos ? 'LoadByGecos' : 'Load'; - - if ($^O eq 'MSWin32' and $RT::WebExternalGecos) { - my $NodeName = Win32::NodeName(); - $user =~ s/^\Q$NodeName\E\\//i; - } - - $session{'CurrentUser'}->$load_method($user); - - if ($RT::WebExternalAuto and !$session{'CurrentUser'}->Id() ) { - # Create users on-the-fly with default attributes - - my $UserObj = RT::User->new(RT::CurrentUser->new('root')); - - my ($val, $msg) = $UserObj->Create( - %{ref($RT::AutoCreate) ? $RT::AutoCreate : {}}, - Name => $user, - Gecos => $user, - ); - - if ($val) { - $UserObj->SetPrivileged(1); - - if ($^O !~ /^(?:riscos|MacOS|MSWin32|dos|os2)$/) { - # Populate fields with information from Unix /etc/passwd - - my ($comments, $realname) = (getpwnam($user))[5, 6]; - $UserObj->SetComments($comments) if defined $comments; - $UserObj->SetRealName($realname) if defined $realname; +# If RT is configured for external auth, let's go through and get REMOTE_USER +elsif ( $RT::WebExternalAuth ) { + + # do we actually have a REMOTE_USER equivlent? + if ( RT::Interface::Web::WebCanonicalizeInfo() ) { + + my $orig_user = $user; + + $user = RT::Interface::Web::WebCanonicalizeInfo(); + $session{'CurrentUser'} = RT::CurrentUser->new(); + my $load_method = $RT::WebExternalGecos ? 'LoadByGecos' : 'Load'; + + if ($^O eq 'MSWin32' and $RT::WebExternalGecos) { + my $NodeName = Win32::NodeName(); + $user =~ s/^\Q$NodeName\E\\//i; + } + + $session{'CurrentUser'}->$load_method($user); + + if ($RT::WebExternalAuto and !$session{'CurrentUser'}->Id() ) { + # Create users on-the-fly + + my $UserObj = RT::User->new(RT::CurrentUser->new('root')); + + my ($val, $msg) = $UserObj->Create( + %{ref($RT::AutoCreate) ? $RT::AutoCreate : {}}, + Name => $user, + Gecos => $user, + ); + + if ($val) { + + # now get user specific information, to better create our user. + my $new_user_info = RT::Interface::Web::WebExternalAutoInfo($user); + + # set the attributes that have been defined. + # FIXME: this is a horrible kludge. I'm sure there's something cleaner + foreach my $attribute ('Name', 'Comments', 'Signature', 'EmailAddress', + 'PagerEmailAddress', 'FreeformContactInfo', + 'Organization', 'Disabled', 'Privileged', + 'RealName', 'NickName', 'Lang', 'EmailEncoding', + 'WebEncoding', 'ExternalContactInfoId', + 'ContactInfoSystem', 'ExternalAuthId', 'Gecos', + 'HomePhone', 'WorkPhone', 'MobilePhone', + 'PagerPhone', 'Address1', 'Address2', 'City', + 'State', 'Zip', 'Country') { + + my $method = "Set$attribute"; + $UserObj->$method($new_user_info->{$attribute}) + if( defined $new_user_info->{$attribute} ); + } + $session{'CurrentUser'}->Load($user); } - elsif ($^O eq 'MSWin32' and eval 'use Net::AdminMisc; 1') { - # Populate fields with information from NT domain controller + else { + # we failed to successfully create the user. abort abort abort. + delete $session{'CurrentUser'}; + $m->abort() unless $RT::WebFallbackToInternalAuth; + $m->comp('/Elements/Login', %ARGS, + Error=> loc('Cannot create user: [_1]', $msg)); } - - $session{'CurrentUser'}->Load($user); } - else { + + unless ( $session{'CurrentUser'}->Id() ) { delete $session{'CurrentUser'}; - $m->abort() unless $RT::WebFallbackToInternalAuth; - $m->comp('/Elements/Login', %ARGS, Error=> loc('Cannot create user: [_1]', $msg)); + $user = $orig_user; + + if ( $RT::WebExternalOnly ) { + $m->comp('/Elements/Login', %ARGS, + Error=> loc('You are not an authorized user')); + $m->abort(); + } } } - - unless ( $session{'CurrentUser'}->Id() ) { - delete $session{'CurrentUser'}; - $user = $orig_user; - - if ( $RT::WebExternalOnly ) { - $m->comp('/Elements/Login', %ARGS, Error=> loc('You are not an authorized user')); - $m->abort(); + elsif ($RT::WebFallbackToInternalAuth) { + unless (defined($session{'CurrentUser'})) { + $m->comp('/Elements/Login', %ARGS, + Error=> loc('XXX CHANGEME You are not an authorized user')); + $m->abort(); } + } else { + # WebExternalAuth is set, but we don't have a REMOTE_USER. abort + delete $session{'CurrentUser'} if defined $session{'CurrentUser'}; } } delete $session{'CurrentUser'} unless $session{'CurrentUser'} and defined $session{'CurrentUser'}->Id; + # Process per-page authentication callbacks $m->comp('/Elements/Callback', %ARGS, _CallbackName => 'Auth');