jcpunk has asked for the wisdom of the Perl Monks concerning the following question:

Greetings monks,

I have got a script here using the Expect module and I need to get data out of it. normally I would just let it dump all over the screen, but it has to be formated nicely, so normally I would just throw together a reg-ex and use before() or after(), but I need to do some rather strange matching and do not think that solution is viable... so does anyone have any thoughts as to how to get STDout into a scalar from expect with log_stdout(0) enabled. Also keeping in mind that I am unable to dump output to a log and then open that up as that is "a security risk"...sigh

If anyone has any thoughts as to how this should be done they would be greatly apprecated.


The code that I have so far is here, if that helps explain my question better
$exp->send("/bin/sh\n"); #do lots of random shiznat here #that i dont want to see like a telnet login my $junk=$exp->send("/bin/cat /etc/passwd\n"); #do formating to skip things that arnt worth looking at #and probably make some tables so that it outputs nicely print "Output:<b>$junk</b>\n";
It doesn't work, but I hope this helps explain what I mean

Replies are listed 'Best First'.
Re: Expect, STDout, and formating
by cbro (Pilgrim) on Jun 12, 2003 at 21:03 UTC
    Here's an example that you can port to your code:
    use Expect; $exp = new Expect; $exp->log_stdout(0); $exp->log_file(\&formatoutput); $exp->spawn("/bin/sh"); $exp->send("/bin/cat /etc/passwd\n"); $exp->soft_close(); sub formatoutput { my $input = shift; # format however you'd like # e.g. $input =~ s/\$//g; # That will get rid of the $ output and leave you with # only data. You will also need to get rid of the # commands as they too will be passed to this function. # By that I mean /bin/cat /etc/passwd # You can do all types of good stuff for additional # formatting such as formline or format STDOUT_TOP = print STDOUT "\n\n$input\n\n"; # or if you used formline print STDOUT "$^A", etc. # but I'll leave the particulars to you. return; }
    HTH,
    Chris

    Update:changed $output to $input in the print STDOUT statement...
Re: Expect, STDout, and formating
by BrowserUk (Patriarch) on Jun 12, 2003 at 21:19 UTC

    If you are using 5.8, then you could try reopening STDOUT to an 'in memory' file as described in perlfunc:open (Search for "in memory").

    File handles can be opened to ``in memory'' files held in Perl scalars + via: open($fh, '>', \$variable) || .. Though if you try to re-open STDOUT or STDERR as an ``in memory'' file +, you have to close it first: close STDOUT; open STDOUT, '>', \$variable or die "Can't open STDOUT: $!";

    I'm not certain that the Expect module would cooperate with this, but it seems likely that it would. In the above examples the output would be stored in $variable.

    Remember to close/reopen STDOUT to 'con' or 'tty' depending on your OS before outputing stuff you want the user to see:)


    Examine what is said, not who speaks.
    "Efficiency is intelligent laziness." -David Dunham
    "When I'm working on a problem, I never think about beauty. I think only how to solve the problem. But when I have finished, if the solution is not beautiful, I know it is wrong." -Richard Buckminster Fuller


Re: Expect, STDout, and formating
by aquarium (Curate) on Jun 12, 2003 at 22:27 UTC
    if you want to capture stdout of the spawned process, then your expect object (I believe) is a filehandle. therefore @array=<$exp_object> should work, as should $scalar=<$exp_object> Sorry, but I can't test this for you as this machine is not allowed to have additional modules installed. what does work for sure, and if you really don't need any of the expect module functionality, is to open the program as a pipe, eg
    open(MYPROG,"| /bin/sh") or die;
    $scalar=<MYPROG>;