--- loncom/lonencurl.pm 2007/10/02 01:10:16 1.4 +++ loncom/lonencurl.pm 2011/10/01 03:18:57 1.5 @@ -2,7 +2,7 @@ # The LearningOnline Network # URL translation for encrypted filenames # -# $Id: lonencurl.pm,v 1.4 2007/10/02 01:10:16 albertel Exp $ +# $Id: lonencurl.pm,v 1.5 2011/10/01 03:18:57 raeburn Exp $ # # Copyright Michigan State University Board of Trustees # @@ -33,6 +33,7 @@ use strict; use Apache::Constants qw(:common :remotehost); use Apache::lonnet; use Apache::lonenc; +use GDBM_File; sub handler { my $r = shift; @@ -44,8 +45,40 @@ sub handler { # Initialize Environment my $lonidsdir=$r->dir_config('lonIDsDir'); &Apache::lonnet::transfer_profile_to_env($lonidsdir,$handle); -# Decrypt URL and redirect - my $redirect=&Apache::lonenc::unencrypted($r->uri); +# Decrypt URL, if appropriate, and redirect + my $redirect; + my ($decrypted,$encnum,$remainder) = &checkdecryption($r->uri); + if (($encnum ne '') && ($remainder ne '')) { + my $referrer = $r->headers_in->{'Referer'} || ''; + my $host = $r->headers_in->{'Host'}; + my $decryptreferrer; + if ($referrer =~ m{^https?://\Q$host\E(/enc/\Q$encnum\E/[^?]+)}) { + ($decryptreferrer) = &checkdecryption($1); + } + if ($decryptreferrer eq '') { + if ($env{'request.course.fn'} ne '') { + my %symbhash; + if (tie(%symbhash,'GDBM_File',$env{'request.course.fn'}.'_symb.db', + &GDBM_READER(),0640)) { + my $lastsymb=$symbhash{'last_known'}; + untie(%symbhash); + (undef,undef,$decryptreferrer)=&Apache::lonnet::decode_symb($lastsymb); + $decryptreferrer = &Apache::lonnet::clutter($decryptreferrer); + } + } + } + if ($decryptreferrer ne '') { + my ($referrerpath) = ($decryptreferrer =~ m{^(.+/)[^/]+$}); + if (($env{'httpref.'.$referrerpath.$remainder} eq $decryptreferrer) || + ($env{'httpref.'.$referrerpath.'*'} eq $decryptreferrer) || + ($env{'httpref.'.$referrerpath} eq $decryptreferrer)) { + $redirect=$referrerpath.$remainder; + } + } + } + if ($redirect eq '') { + $redirect=&Apache::lonenc::unencrypted($r->uri); + } if ($r->args) { $redirect.='?'.$r->args; } $r->internal_redirect($redirect); return OK; @@ -53,5 +86,17 @@ sub handler { return FORBIDDEN; } +sub checkdecryption { + my ($uri) = @_; + my ($encnum,$encname,$rest) = ($uri =~ m{^/enc/(\d+)/([^.]+)(.*)$}); + my $enclength = length($encname); + my $rem = $enclength%16; + if (($encname =~ /[^a-f0-9]/) || ($rem != 0) || ($enclength < 16)) { + return ('',$encnum,$encname.$rest); + } else { + return (&Apache::lonenc::unencrypted($uri)); + } +} + 1; __END__