I was wondering if it was possible to read a text file that was located in a directory called
“/home/user/files”
I wanted to read it from my cgi-bin which is located in /home/user/cgi-bi/
Below is my code,
#!/usr/bin/perl
use strict;
use CGI;
#Virtual Directory
#Steffan Harris
eval
{
use constant PASSWORD => 'perl';
use constant UPLOAD_DIR => '/home/sharris2/files';
sub mapToFile
{
print chdir UPLOAD_DIR;
}
#This function will list all files in a directory.
sub listDirectoryFiles
{
chdir UPLOAD_DIR;
my @files = <*>;
mapToFile;
print<<LIST;
<h2>Current Files</h2>
<ul>
LIST
if(!$files[0])
{
print" </ul>\n<em>No files in directory</em>";
}
foreach(@files)
{
print" <li>$_</li>";
}
print " </ul>\n";
}
#This function generates a 404 Not Found error
sub generate404
{
print<<RESPONSE;
Status: 404 Not Found
Content-Type: text/html
<html>
<head><title>404 Not Found</title></head>
<body>
<p>
<h1>404 - Not Found</h1>
</p>
The requested URL <b>$ENV{"HTTP_HOST"}$ENV{"REQUEST_URI"}</b> was not found on the server.
</body>
</html>
RESPONSE
exit;
}
#This function checks the path info to see if it matches a file in the UPLOAD_DIR directory, If it does not, then it returns a 404 error
sub checkExsistence
{
if($ENV{"PATH_INFO"})
{
chdir UPLOAD_DIR;
my @files = <*>;
if(!$files[0] and $ENV{"PATH_INFO"} eq "/")
{
return;
}
foreach(@files)
{
if($ENV{"PATH_INFO"} eq "/".$_ || $ENV{"PATH_INFO"} eq "/")
{
print "yes";
return;
}
}
generate404;
}
}
sub checkPassword
{
my ($password, $cgi);
$cgi = new CGI;
$password = $cgi->param('passwd');
unless($password eq PASSWORD)
{
print<<RESPONSE;
Status: 200 OK
Content-Type: text/html
<html>
<head>
<title>Incorrect Password</title>
</head>
<body>
<h1>Invalid password entered.</h1>
<h3><a href="/~sharris2/cgi-bin/files/">Go Back</a></h3>
</body>
RESPONSE
exit;
}
}
sub upLoadFile
{
checkPassword;
my ($uploadfile, $cgi);
$cgi = new CGI;
$uploadfile = $cgi->upload('uploadfile');
chdir UPLOAD_DIR;
$uploadfile
or die "Did not receive a file to upload";
open my $FILE, '>', UPLOAD_DIR."/$uploadfile" or
die "$!";
while(<$uploadfile>)
{
print $FILE $_;
}
}
#Start of main part of program
my $cgi = new CGI;
if(!$ENV{"PATH_INFO"})
{
print $cgi->redirect('/~sharris2/cgi-bin/files/');
}
checkExsistence;
if($ENV{"REQUEST_METHOD"} eq "POST")
{
upLoadFile;
}
print <<"HEADERS";
Status: 200 OK
Content-Type: text/html
HEADERS
print <<"HTML";
<html>
<head>
<title>Virtual Directory</title>
</head>
<body>
HTML
listDirectoryFiles;
print<<HTML;
<h2>Upload a new file</h2>
<form method = "POST" enctype = "multipart/form-data" action = "/~sharris2/cgi-bin/files/" />
File:<input type = "file" name="uploadfile"/>
<p>Password:
<input type = "password" name ="passwd"/></p>
<p><input type = "submit" value= "Submit File" /></p>
</form>
</body>
</html>
HTML
};
There’s no need to
chdir, and you probably don’t really want to do that anyway. Just try to open the directory. If you can’t open the directory, log an error message so you know what happened. Remember, anything you try to access, including containing directories, has to have the appropriate permissions to let the web server user do whatever you are trying to do.Also remember that in any subroutine that you create you want to limit its side-effects. Don’t rely on global data, and don’t change global state. You’ll have a much easier time managing your program when you keep control of those things.