use File::Temp qw( tempfile );
sub capture_output {
my $target_fh = shift;
my $temp_fh = tempfile();
my $temp_fd = fileno $temp_fh;
local *SAVED;
local *TARGET = $target_fh;
open SAVED, ">&TARGET" or die "can't remember target";
open TARGET, ">&=$temp_fd" or die "can't redirect target";
my $saved_fh = *SAVED;
return sub {
seek $temp_fh, 0, 0 or die "can't seek"; # rewind
my $captured_output = do { local $/; <$temp_fh> };
close $temp_fh or die "can't close temp file handle";
local (*SAVED, *TARGET) = ($saved_fh, $target_fh);
open TARGET, ">&SAVED" or die "can't restore target";
close SAVED or die "can't close SAVED";
return $captured_output;
}
}
####
print STDERR "before redirection\n";
my $recorder = capture_output(*STDERR); # start
print STDERR "during redirection\n";
my $saved_output = $recorder->(); # stop
print STDERR "after redirection\n";
print "Saved output = $saved_output";
####
before redirection
after redirection
Saved output = during redirection