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

G'day your holiness,
I am a babe in Perl but have a pretty good feel for it but very new to objects. I am attempting to use the Expect.pm to automate some daily reports but am having trouble understanding how to get my StdOut from the command being ran by Expect...any and all help is greatly appreciated. Here is the code that I have and the resulting DEBUG below it. My Expect functions are matching and sending the correct responses to the username and password but immediately hard_close() without returning the output from the command...just not clear in my mind how to send it to an array for processing.
As always THANKS,
Danny
#!/usr/bin/perl -w $ENV{'RTSERVERS'} = 'tcp:dspmon03.tdc.cingular.net:2059,tcp:dspmon01.t +dc.cingular.net:2059'; use Expect; use strict; $Expect::Log_Stdout=1; $Expect::Debug=3; $Expect::Exp_Internal=1; my $cmd = "/opt/app/bmcprod/common/bmc/bin/solaris-2-10-sparc/pslv -a +"-id DSPMON03" ./cs_get_agent_info.asm"; new Expect(); (my $rtcloud = Expect->spawn("$cmd")) || die "Couldn't spawn $cmd, $!" +; unless ($rtcloud->expect(30,"Enter a user name for the service 'PATROL +_CSERVER_DSPMON03' :")) { die "Never got username prompt from $cmd, ".$rtcloud->exp_error()."\ +n"; } print $rtcloud "b1patrol\r"; unless ($rtcloud->expect(30,"Password: ")) { die "Never got Password prompt from $cmd, ".$rtcloud->exp_error()."\ +n"; } print $rtcloud "xxxxxxxx\r";

DEBUG
Use of uninitialized value in concatenation (.) or string at /usr/loca +l/lib/perl5/site_perl/5.8.8/Expect.pm line 1431. Closing . at /usr/local/lib/perl5/site_perl/5.8.8/Expect.pm line 1431 Expect::hard_close('Expect=GLOB(0x1005dcad0)') called at /usr/ +local/lib/perl5/site_perl/5.8.8/Expect.pm line 1621 Expect::DESTROY('Expect=GLOB(0x1005dcad0)') called at ./get_RT +cloud.pl line 14 eval {...} called at ./get_RTcloud.pl line 14 Expect::new('Expect') called at ./get_RTcloud.pl line 14 Use of uninitialized value in concatenation (.) or string at /usr/loca +l/lib/perl5/site_perl/5.8.8/Expect.pm line 1434. closed. Spawned '/opt/app/bmcprod/common/bmc/bin/solaris-2-10-sparc/pslv -a "- +id DSPMON03" ./cs_get_agent_info.asm' spawn id(3) Pid: 7293 Tty: /dev/pts/6 at /usr/local/lib/perl5/site_perl/5.8.8/Expect.pm line 181 Expect::spawn('Expect', '/opt/app/bmcprod/common/bmc/bin/solar +is-2-10-sparc/pslv -a "-...') called at ./get_RTcloud.pl line 16 expect(Expect=GLOB(0x1006afec0) 30 Enter a user name for the service ' +PATROL_CSERVER_DSPMON03' :) called... expect(): handling param 'Enter a user name for the service 'PATROL_CS +ERVER_DSPMON03' :'... expect(): exact match 'Enter a user name for the service 'PATROL_CSERV +ER_DSPMON03' :'... Starting EXPECT pattern matching... at /usr/local/lib/perl5/site_perl/5.8.8/Expect.pm line 561 Expect::expect('Expect=GLOB(0x1006afec0)', 30, 'Enter a user n +ame for the service \'PATROL_CSERVER_DSPMON03\' :') called at ./get_R +Tcloud.pl line 18 spawn id(3): beginning expect. Timeout: 30 seconds. Current time: Tue Aug 14 15:40:11 2007 spawn id(3): list of patterns: #1: -ex `Enter a user name for the service \'PATROL_CSERVER_DSPMON03 +\' :' spawn id(3): Does `' match: pattern #1: -ex `Enter a user name for the service \'PATROL_CSERVER_ +DSPMON03\' :'? No. Waiting for new data (30 seconds)... spawn id(3): new data. spawn id(3): read 153 byte(s). INFO: Connecting to Global Namespace using tcp:dspmon03.tdc.cingular.n +et:2059,tcp:dspmon01.tdc.cingular.net:2059... INFO: Setting authentication hooks spawn id(3): Does `INFO: Connecting to Global Namespace using tcp:dspm +on03.tdc.cingular.net:2059,tcp:dspmon01.tdc.cingular.net:2059...\r\nI +NFO: Setting authentication hooks\r\n' match: pattern #1: -ex `Enter a user name for the service \'PATROL_CSERVER_ +DSPMON03\' :'? No. Waiting for new data (29 seconds)... spawn id(3): new data. spawn id(3): read 63 byte(s). Enter a user name for the service 'PATROL_CSERVER_DSPMON03' : spawn id(3): Does `INFO: Connecting to Global Namespace using tcp:dspm +on03.tdc.cingular.net:2059,tcp:dspmon01.tdc.cingular.net:2059...\r\nI +NFO: Setting authentication hooks\r\n\r\nEnter a user name for the se +rvice \'PATROL_CSERVER_DSPMON03\' :' match: pattern #1: -ex `Enter a user name for the service \'PATROL_CSERVER_ +DSPMON03\' :'? YES!! Before match string: `INFO: Connecting to Global Namespace using t +cp:dspmon03.tdc.cingular.net:2059,tcp:dspmon01.tdc.cingular.net:2059. +..\r\nINFO: Setting authentication hooks\r\n\r\n' Match string: `Enter a user name for the service \'PATROL_CSERVER_ +DSPMON03\' :' After match string: `' Matchlist: () Returning from expect successfully. spawn id(3): accumulator: `' expect(Expect=GLOB(0x1006afec0) 30 Password: ) called... expect(): handling param 'Password: '... expect(): exact match 'Password: '... Starting EXPECT pattern matching... at /usr/local/lib/perl5/site_perl/5.8.8/Expect.pm line 561 Expect::expect('Expect=GLOB(0x1006afec0)', 30, 'Password: ') c +alled at ./get_RTcloud.pl line 24 spawn id(3): beginning expect. Timeout: 30 seconds. Current time: Tue Aug 14 15:40:12 2007 spawn id(3): list of patterns: #1: -ex `Password: ' spawn id(3): Does `' match: pattern #1: -ex `Password: '? No. Waiting for new data (30 seconds)... spawn id(3): new data. spawn id(3): read 10 byte(s). b1patrol spawn id(3): Does `b1patrol\r\n' match: pattern #1: -ex `Password: '? No. Waiting for new data (30 seconds)... spawn id(3): new data. spawn id(3): read 58 byte(s). Password required for the user 'b1patrol' on service 'PATR spawn id(3): Does `b1patrol\r\nPassword required for the user \'b1patr +ol\' on service \'PATR' match: pattern #1: -ex `Password: '? No. Waiting for new data (27 seconds)... spawn id(3): new data. spawn id(3): read 23 byte(s). OL_CSERVER_DSPMON03'. spawn id(3): Does `b1patrol\r\nPassword required for the user \'b1patr +ol\' on service \'PATROL_CSERVER_DSPMON03\'.\r\n' match: pattern #1: -ex `Password: '? No. Waiting for new data (27 seconds)... spawn id(3): new data. spawn id(3): read 10 byte(s). Password: spawn id(3): Does `b1patrol\r\nPassword required for the user \'b1patr +ol\' on service \'PATROL_CSERVER_DSPMON03\'.\r\nPassword: ' match: pattern #1: -ex `Password: '? YES!! Before match string: `b1patrol\r\nPassword required for the user \ +'b1patrol\' on service \'PATROL_CSERVER_DSPMON03\'.\r\n' Match string: `Password: ' After match string: `' Matchlist: () Returning from expect successfully. spawn id(3): accumulator: `' Closing spawn id(3). at /usr/local/lib/perl5/site_perl/5.8.8/Expect.pm line 1431 Expect::hard_close('Expect=GLOB(0x1006afec0)') called at /usr/ +local/lib/perl5/site_perl/5.8.8/Expect.pm line 1621 Expect::DESTROY('Expect=GLOB(0x1006afec0)') called at ./get_RT +cloud.pl line 0 eval {...} called at ./get_RTcloud.pl line 0 spawn id(3) closed. Pid 7293 of spawn id(3) terminated, Status: 0x01

Replies are listed 'Best First'.
Re: Expect.pm dealing with STDOUT
by Argel (Prior) on Aug 14, 2007 at 21:39 UTC
    I think you need to save the instance from the "new Expect" or do something like the following:
    my $expect_instance = Expect->spawn( "telnet $router" ); my $cmd = 'terminal length 0'; print $expect_instance "$cmd\r"; my( $which, $why, $match, $before, $after ) = $expect_instance->expect +( $timeout, $prompt ); if( ! $which ) { die "Could not send $cmd to $router. Reason: $why"; }

    You would want to check on $before, $after, and if you had multiple possible matches then $match. In the example above it is matching on $prompt, and thus $before is what came before the match and $after is what followed it. Note that these can be strings with new lines in them.

    It has been a while since I used Expect.pm so I hope this helps.

Re: Expect.pm dealing with STDOUT
by dwm042 (Priest) on Aug 15, 2007 at 01:08 UTC
    The previous respondant was actually correct; you need to create an expect object and then use that object to do things. I don't claim great expertise in it either, but I have been asked to make things work in Perl Expect. What I'll offer is a bit of a code snippet where the script is logging into a router via ssh and then looking at the prompt to help determine the type of the router.

    my $exp = new Expect; $exp->raw_pty(1); $exp->log_stdout(0); # $exp->log_stdout(1); # uncomment for debugging $exp->log_file($logfile); my $host = "$r\.domain\.com"; $exp->spawn("ssh -o StrictHostKeyChecking=no $user{$r}\@$host ") | +| die("Cannot spawn an ssh session within expect.\n"); $exp->expect($delay, [ 'assword:', sub { my $exp = shift; $exp->send("$pass{$r}\r"); exp_continue; } ], [ eof => sub { $exitcode = 1; } ], [ timeout => sub { $exitcode = 2; } ], [ '>', sub { my $exp = shift; $cisco = $false; $prompt = '>'; } ], [ '#', sub { my $exp = shift; } ],);
Re: Expect.pm dealing with STDOUT
by unplugged (Initiate) on Mar 16, 2011 at 11:18 UTC
    This is not a Perl related question. I am curious to know the options available with /opt/app/bmcprod/common/bmc/bin/solaris-2-10-sparc/pslv.