Home > Archive > PERL Miscellaneous > July 2004 > capture/supress stdout from perl module called from cgi
You are viewing an archived Text-only version of the thread.
To view this thread in it's original format and/or if you want to reply to
this thread please [click here]
| Author |
capture/supress stdout from perl module called from cgi
|
|
| project2501 2004-07-23, 3:56 pm |
|
i have a problem. i'm using apache with perl cgi and the cgi calls
functions from the VCS::CVS module. this is fine... but the
CVS::commit($message) sends items to stdout.
sterr is fine as the webserver redirects that to the apache error logs,
but stdout appears before html stream headers "content type etc" ... and
so the server logs a "malformed header from script. Bad header=..." error
as expected.
i wonder if i can block stdout around that block of code... i've
investigated the use iof eval{} but there don't appear to be options to do
this. the CVS::CVS module itself cannot be set to not output stdout.
any help appreciated.
t
| |
| Eric Bohlman 2004-07-23, 3:56 pm |
| project2501 <project2501@project2501.cor> wrote in
news:pan.2004.07.23.16.28.11.594000@project2501.cor:
>
> i have a problem. i'm using apache with perl cgi and the cgi calls
> functions from the VCS::CVS module. this is fine... but the
> CVS::commit($message) sends items to stdout.
>
> sterr is fine as the webserver redirects that to the apache error
> logs, but stdout appears before html stream headers "content type etc"
> ... and so the server logs a "malformed header from script. Bad
> header=..." error as expected.
>
> i wonder if i can block stdout around that block of code... i've
> investigated the use iof eval{} but there don't appear to be options
> to do this. the CVS::CVS module itself cannot be set to not output
> stdout.
Would IO::Scalar be any help?
| |
| Anno Siegel 2004-07-23, 3:56 pm |
| project2501 <project2501@project2501.cor> wrote in comp.lang.perl.misc:
>
> i have a problem. i'm using apache with perl cgi and the cgi calls
> functions from the VCS::CVS module. this is fine... but the
> CVS::commit($message) sends items to stdout.
Well, it shouldn't. No module should print to stdout unless that is
its express purpose.
> sterr is fine as the webserver redirects that to the apache error logs,
I wouldn't call that "fine", but yes, error logs have a big belly.
> but stdout appears before html stream headers "content type etc" ... and
> so the server logs a "malformed header from script. Bad header=..." error
> as expected.
>
> i wonder if i can block stdout around that block of code... i've
> investigated the use iof eval{} but there don't appear to be options to do
> this. the CVS::CVS module itself cannot be set to not output stdout.
Eval is for very different purposes. That it can be used to suppress
unwanted error output bears only a superficial resemblance to your
situation.
The solution depends a bit on what the module actually does. If it
just print()s without a filehandle argument (most likely), select()
is the solution. You need a filehandle to redirect the unwanted
output to (you *could* use STDERR for that, but opening /dev/null may
be a better idea, if available). So (untested):
my $devnull;
open $devnull, ">", $_ or die "Can't write to $_" for '/dev/null';
my $oldfh = select( $devnull);
# code that *prints* *things*
select( $oldfh);
# code that is entitled to print
If the module explicitly prints to STDOUT, stronger medicine is indicated
(and available), but that won't be necessary.
Anno
| |
| Ilmari Karonen 2004-07-23, 8:56 pm |
| On 2004-07-23, project2501 <project2501@project2501.cor> wrote:
>
> i wonder if i can block stdout around that block of code... i've
> investigated the use iof eval{} but there don't appear to be options to do
> this. the CVS::CVS module itself cannot be set to not output stdout.
You don't mention if the output comes from VCS::CVS itself or from
some external program it calls. In any case, you can capture the
output by reopening STDOUT to a temporary file:
use File::Temp qw(tempfile);
my $tempfile = tempfile() or die "Can't create temp file: $!\n";
open TMPOUT, '>&', \*STDOUT or die "Can't dup stdout: $!\n";
open STDOUT, '>&', $tempfile or die "Can't redirect stdout: $!\n";
# ... do something ...
open STDOUT, '>&', \*TMPOUT or die "Can't restore stdout: $!\n";
s $tempfile, 0, 0 or die "Can't rewind temp file: $!\n";
my @lines = <$tempfile>;
If you just want to send any output to the bit bucket, that's even
easier:
open TMPOUT, '>&', \*STDOUT or die "Can't dup stdout: $!\n";
open STDOUT, '>/dev/null' or die "Can't redirect stdout: $!\n";
# ... do something ...
open STDOUT, '>&', \*TMPOUT or die "Can't restore stdout: $!\n";
--
Ilmari Karonen
If replying by e-mail, please replace ".invalid" with ".net" in address.
|
|
|
|
|