Okay, trying to sepparate out stdout and stderr. By all means just tell me there is a better way, but...
I have the following function to pull out the two streams and stick them in sepparate files, while also providing them as a parsable return value to the calling code.
I have pasted 2 code segments, the first is the function including a debug line creating a file of the unprocessed command output. The second was a test for processing the output to see where my error was. Unfortunately the test works, but the function doesn't... I'm stumped:-
#function to take a single command and write the outputs (stdout and stderr) to sepparate files, and the consol
#NOTE: if multiple commands are passed in a single string, only the execution
#of the last will have it's output captured
sub execute
{
my $cmd = shift;
my $retval ="";
my ($output, $line);
#prepend each STDOUT line with "@#STDOUT%:"
$output = `($cmd|perl -e"while(<STDIN>){s/^/\@\#STDOUT\%:/;print;}")2>&1`;
#DEBUG Output to file###########
print PURE $output;
#Split the output to multiple lines and process
foreach $line (split(/\n/,$output))
{
#If the line has the prepend
if ($line =~ s/^\@\#STDOUT\%://)
{
#print to file
print OUT "$line\n";
#print to consol
print "$line\n";
#add to the return value
$line =~ s/^/STDOUT:/;
$retval = $retval."$line\n";
}
else
{
#print to file
print ERR "$line\n";
#print to consol
print "$line\n";
#add to the return value
$line =~ s/^/STDERR:/;
$retval = $retval."$line\n";
}
return $retval;
}
}
As mentioned at the start; the debug line is to allow me to capture and run the same output through a test routine:-
open(PURE, "<./PureOutput.txt");
#declare in a block to prevent the changes in special variables propagating
{
#unset the block sepparator
$/="";
#read in all the file
$output = <PURE>;
}
#Split the output to multiple lines and process
#(this is exactly the same as in the execute function)
foreach $line (split(/\n/,$output))
{
#If the line has the prepend
if ($line =~ s/^\@\#STDOUT\%://)
{
#print to file
print OUT "$line\n";
#print to consol
print "$line\n";
#add to the return value
$line =~ s/^/STDOUT:/;
$retval = $retval."$line\n";
}
else
{
#print to file
print ERR "$line\n";
#print to consol
print "$line\n";
#add to the return value
$line =~ s/^/STDERR:/;
$retval = $retval."$line\n";
}
}
#print $retval;
exit;
Now, running the function against a set of commands yealds rubbish in the consol and the STDOUT (They have what seems to be only the 1st and last lines of each command output) the pure output debug file and the STDERR output file seem fine.
If I then run the pure output debug file through the test script then I get the expected output in all files and the consol. Even the return values are fine.
Cannot understand why one works and the other doesn't... ideas?
Malc
I have the following function to pull out the two streams and stick them in sepparate files, while also providing them as a parsable return value to the calling code.
I have pasted 2 code segments, the first is the function including a debug line creating a file of the unprocessed command output. The second was a test for processing the output to see where my error was. Unfortunately the test works, but the function doesn't... I'm stumped:-
#function to take a single command and write the outputs (stdout and stderr) to sepparate files, and the consol
#NOTE: if multiple commands are passed in a single string, only the execution
#of the last will have it's output captured
sub execute
{
my $cmd = shift;
my $retval ="";
my ($output, $line);
#prepend each STDOUT line with "@#STDOUT%:"
$output = `($cmd|perl -e"while(<STDIN>){s/^/\@\#STDOUT\%:/;print;}")2>&1`;
#DEBUG Output to file###########
print PURE $output;
#Split the output to multiple lines and process
foreach $line (split(/\n/,$output))
{
#If the line has the prepend
if ($line =~ s/^\@\#STDOUT\%://)
{
#print to file
print OUT "$line\n";
#print to consol
print "$line\n";
#add to the return value
$line =~ s/^/STDOUT:/;
$retval = $retval."$line\n";
}
else
{
#print to file
print ERR "$line\n";
#print to consol
print "$line\n";
#add to the return value
$line =~ s/^/STDERR:/;
$retval = $retval."$line\n";
}
return $retval;
}
}
As mentioned at the start; the debug line is to allow me to capture and run the same output through a test routine:-
open(PURE, "<./PureOutput.txt");
#declare in a block to prevent the changes in special variables propagating
{
#unset the block sepparator
$/="";
#read in all the file
$output = <PURE>;
}
#Split the output to multiple lines and process
#(this is exactly the same as in the execute function)
foreach $line (split(/\n/,$output))
{
#If the line has the prepend
if ($line =~ s/^\@\#STDOUT\%://)
{
#print to file
print OUT "$line\n";
#print to consol
print "$line\n";
#add to the return value
$line =~ s/^/STDOUT:/;
$retval = $retval."$line\n";
}
else
{
#print to file
print ERR "$line\n";
#print to consol
print "$line\n";
#add to the return value
$line =~ s/^/STDERR:/;
$retval = $retval."$line\n";
}
}
#print $retval;
exit;
Now, running the function against a set of commands yealds rubbish in the consol and the STDOUT (They have what seems to be only the 1st and last lines of each command output) the pure output debug file and the STDERR output file seem fine.
If I then run the pure output debug file through the test script then I get the expected output in all files and the consol. Even the return values are fine.
Cannot understand why one works and the other doesn't... ideas?
Malc