I feel like a real novice with this question, but sometimes huge experience can have a bad day.
I have this CGI script for file upload in file chunks. It is correctly uploading my files just fine, however I can't get a log file to write log data even though it used to work perfectly. The log file is zero bytes.
I added a couple of lines to greatly simplify debug at the start of the script. They are listed below. They open a new log file, write a simple line of text, then close it.
I figured it can't be a flush problem as I'm closing the file. It must be opening the file because the file exists, just zero bytes. It must be running the CGI script, because my file does not upload otherwise. And it has permission to write to /tmp, as the file is created. Also there are no errors in /etc/httpd/logs/errorlog
open(LOGFILE, ">", "/tmp/olss2.log") or die "Can't open log file: $!";
$| = 1;
print LOGFILE "New Log Entry Started";
close LOGFILE;
Related
I am using open to write data into an Excel file. This is working fine with .txt files, but with .xls files it always fails.
This is the code I am writing
$filename = "abc.xls";
$fhandle = "ABC";
open( $fhandle, ">$filename" ) || die "cannot open file $filename";
The same code executes fine in another environment which has an older Perl version.
I need help on how can I fix this.
Found the problem to the issue. The environment I was trying to create these files in already had the files with the same name but did not have permissions for me to edit those files. I deleted the old files and it worked like a charm.
Thanks a lot for your help guys.!!
Shivam
A file handle is a file handle. Not a string.
Also, you are typing the filename in the open call. Why don't you use the $filename variable you so neatly created two lines earlier?
I would try something like this:
$filename = "abc.xls";
open($fhandle, ">$filename") || die "cannot open file $filename";
Also, this xls file: Is it open in excel when you try to run the script? Excel will stop you from opening it in another application or script if you do.
Furthermore : Please use strict and warnings. They will make your life much better.
I am working on a cgi script where I get an uploaded an audio file, downsample it to 8000Hz and then get it recognised later.
I am facing an error while downsampling the file. The code for downsampling goes like:
1) Code for File Upload:
use CGI;
use strict;
use File::Copy qw(copy);
use CGI::Carp 'fatalsToBrowser';
my $PROGNAME = "file_upload.cgi";
my $cgi = new CGI();
print "Content-type: text/html\n\n";
my $upfile = $cgi->param('upfile');
# Get the basename in case we want to use it.
my $basename = GetBasename($upfile);
no strict 'refs';
if (! open(OUTFILE, ">../cgi-bin/upload/".$basename) ) {
print "Can't open for writing - $!";
exit(-1);
}
2)Code for downsample:
my $source_file="/var/www/cgi-bin/upload/$upfile";
system("sox $source_file -r 8000 /var/www/cgi-bin/upload/temp.wav".";"."mv /var/www/cgi-bin/upload/temp.wav $source_file");
where:
source_file is the path for uploaded audio file
$upfile is the name of the uploaded wav file
temp.wav is the temporary downsampled file which is overwritten on the original file using mv command
Error
sox FAIL formats: can't open input file `/var/www/cgi-bin/upload/file1.wav': WAVE: RIFF header not found
file1.wav is the file I uploaded
Please help me understand why the sox command is not executing despite it being correctly written?
This isn't really an answer to your question as we don't have enough information yet.
Have you tried running the command from your Unix command line? I'd assume you get the same error. What do you get if you run file on the file that you have saved? How big is the file before and after you upload it?
You don't show the code that writes the uploaded file. I suspect there's a bug in that. If you add that to your question, we could help you find it.
Where is GetBasename() defined? Can we see the code?
Your sox command seems strange. You're running sox on a file called temp.wav and then copying that file over your uploaded file. Perhaps there are a couple of steps that you aren't telling us.
Some other suggestions for improvement:
Use cgi->new, not new CGI. The latter has some strange corner cases that you will have real problems debugging if you ever come across them.
If you're loading the CGI module, then why not use its header method instead of writing your own (technically incorrect) header.
no strict 'refs' is a really bad idea (and, as far as I can see, isn't needed here).
Please use the three-arg version of open() and lexical filehandles
open my $out_fh, '>', "../cgi-bin/upload/$basename"
Include the file path in your error message
my $file = "../cgi-bin/upload/$basename";
if (!open my $out_fh, '>', $file) {
print "Can't open file '$file' for writing - $!";
exit(-1);
}
You are loading the File::Copy module, but then moving your file using a shell command.
Allowing random users to upload files into a directory under your cgi-bin directory is a massive potential security hole. You should find another directory to store the uploaded files.
Oh, and then there's the whole - why on Earth would you be writing CGI programs in 2017!
The issue is resolved. The reason why I was having problem executing the sox and copy commands was because of where I was placing the two commands in code. Basically a beginners error. So I was opening the file as mentioned in the problem statement. I put the copy and sox commands for execution before I closed the filehandler and hence they were not getting executed successfully.
I need to write a script that opens a file then closes it then opens it again. For example:
#!/usr/bin/perl
open(File,">>test.csv");
print File "1234\n";
close(File);
open(File,">>test.csv");
print File "5678\n";
close(File);
when this code runs on eclipse , it works fine but when I try running the script from the cmd; the file is opened for the first time only and the csv file contains 1234 only.
Probably you keep open the file somewhere.
To know this kind of error, you have to use "die" command with "open" as follows,
open(File,">>test.csv") || die $!;
This will throw you error if any (like Permission denied at line 1.).
Also it is recommended to use 'use strict;' and 'use warnings;' at top of the program to notify any error.
I am fetching some log files (which are in txt format) from another server and trying to parse them using my Perl script. The logs are being fetched correctly after which I set permissions to 777 for the log directory.
After this I attempt to open the log files, one by one for parsing, via my Perl script. Now, the strange thing and the problem which happens is, my script is sometimes able to open the file and sometimes NOT. To put it simply, it's unable to open the log files for parsing at times.
Also, I have cronned this perl script and the chances of file open failing are greater when it runs via cron rather than manually, although they have run successfully in both cases previously. I don't understand where the issue lies.
Here is the code which I use for opening the files,
$inputDir = "/path/to/dir";
#inputFiles = <$inputDir/*>;
# inputFiles array is list of files in the log directory
foreach my $logFile(#inputFiles)
{
# just to ensure file name is text
$logFile = $logFile."";
# process file only if filename contains "NOK"
if(index($logFile,"NOK") > -1)
{
# opens the file
open($ifile, '<', $logFile) or die "Error: Unable to open file for processing.";
# file parsing takes place
}
}
close($ifile);
I want to re-iterate that this code HAS run successfully and I haven't changed any part of it. Yet, it does not run every time without fail, because its unable to open the log file at times. Any ideas?
You should include the error message $! and the file name $logFile in your die string to see why the open failed, and for which file.
open($ifile, '<', $logFile) or die "Error: Unable to open $logFile: $!";
Also, this line:
$logFile = $logFile."";
...is quite redundant. If a conversion is necessary, perl will handle it.
Just as an example, this is what you code should look like. You may like to try this version
use strict;
use warnings;
my $inputDir = '/path/to/dir';
my #inputFiles = <$inputDir/*>;
foreach my $logFile (grep /NOK/, #inputFiles) {
open my $ifile, '<', $logFile or die qq(Unable to open "$logFile": $!);
# Process data from <$ifile>;
}
Maybe opening some files fails, because your program has too many open files. Your program opens all files in $inputDir and processes them in the loop. After that it closes the last file opened.
EDIT: after reading TLP's comment and reading perldoc -f close and perldoc -f open I see that TLP is right and the filehandle in $ifile is closed by a subsequent open($ifile,'<',$logFile) . However, if the file parsing code not shown by the topic creator creates another reference to $ifile the file handle would stay open.
Moving the call to close into the if block should solve your problem:
$inputDir = "/path/to/dir";
#inputFiles = <$inputDir/*>;
# inputFiles array is list of files in the log directory
foreach my $logFile(#inputFiles)
{
# process file only if filename contains "NOK"
if(index($logFile,"NOK") > -1)
{
# opens the file
# added my to $ifile to keep local to this scope
open(my $ifile, '<', $logFile) or die "Error: Unable to open file for processing.";
# file parsing takes place
# close current file
close($ifile);
}
}
I've written a page in PHP that takes user input and then I do a shell_exec to a Perl file after passing those parameters in.
My Perl file basically generates a GD::Graph. When I run the script for the first time, there seems to be no issue and I get a valid image.gif file. However, running it a second time, doesn't change any data on the image.gif file. It remains the same, as though it can't be over-written.
I then executed the Perl script via shell and passed the paramters manually. Here is the error message I get:
Failed to save graph to file: uploads/image.gif. Permission denied at image.pl line 178.
The relevant code in Perl is:
my $bar_file = $filepath . '/image.gif';
if (-e $bar_file) {
#If file exists, delete
unlink($bar_file);
}
else {
print "File does not exist.";
}
open(IMG, ">$bar_file")
|| die ("\nFailed to save graph to file: $bar_file. $!");
binmode IMG;
print IMG $plot->gif();
close IMG;
And the problematic line 178 is:
open(IMG, ">$bar_file")
I tried changing the file to CHMOD 777, but since its been generated by Apache, I do not have the sufficient permissions to CHMOD it.
Can you check if unlink failed?
On success, it returns the number of files it successfully deleted. On failure, it returns false and sets $! (errno).
Surely you want to use the GD hooks in PHP itself?
http://php.net/manual/en/book.image.php