I can't see any reason why the code in red is not working. I did notice that my ssh/scp have a lowercase P in password, however this should just cause a timeout delay before sending the password. Can I suggest using expect "?assword:*"
It it possible that the command you actually used is different to what you posted? Did you try doing the same command from the shell prompt to ensure it's working (eg output path is correct).
Perhaps you will find my script easier to work with. I can see now that you want to use ssh not telent. I've commented it some more and updated for ssh. It looks for a server_list file and produces a local config_details output file:
Code:
#!/usr/bin/expect -f
set timeout 2
set u "souvikm"
set p "passw0rd"
set command "multibos -S"
# Open server_list for read (handle hosts) and config_details for write (handle config)
set hosts [open server_list r]
set config [open config_details w]
# This like turns off local echo -
# for debugging leave it commented and all output will be echoed
#log_user 0
# Loop through each host in the $hosts file
while {[gets $hosts host] >= 0} {
spawn -noecho ssh -t $u@$host
expect "?assword:*"
send -- "$p\r"
# Change server side prompt to make matching more reliable
send "PS1='PROMPT# '\r"
# Wait for new prompt
expect -re "PROMPT# '(.*)PROMPT# "
# Execute command
send "$command\r"
# Match command output and prompt
expect -re "\r\n(.*)\r\n(.*)PROMPT# "
# Load command output into variable output
set output $expect_out(1,string)
# Append output into (and host name) to local logfile
puts $config "$host: $output\r"
# Send exit to host and wait for connection to close
send "exit\r"
expect eof
}
close $hosts
close $config
I tried your provided code(pasted as it is from the server) below:
Code:
#!/usr/bin/expect -f
set timeout 2
set u "souvikm"
set p "pass^123"
set command "oslevel -s"
# Open server_list for read (handle hosts) and config_details for write (handle config)
set hosts [open server_list r]
set config [open config_details w]
# This like turns off local echo -
# for debugging leave it commented and all output will be echoed
#log_user 0
# Loop through each host in the $hosts file
while {[gets $hosts host] >= 0} {
spawn -noecho ssh -t $u@$host
expect "?assword:*"
send -- "$p\r"
# Change server side prompt to make matching more reliable
send "PS1='PROMPT# '\r"
# Wait for new prompt
expect -re "PROMPT# '(.*)PROMPT# "
# Execute command
send "$command\r"
# Match command output and prompt
expect -re "\r\n(.*)\r\n(.*)PROMPT# "
# Load command output into variable output
set output $expect_out(1,string)
# Append output into (and host name) to local logfile
puts $config "$host: $output\r"
# Send exit to host and wait for connection to close
send "exit\r"
expect eof
}
close $hosts
close $config
And this is the error I get:
Code:
My_NIM_Server:msouvik:/export/home/msouvik>./expect_script_new.sh
msouvik@My_Target_Server password:
Last unsuccessful login: Thu Nov 14 12:13:52 GMT 2013 on ssh from My_NIM_Server
Last login: Fri Nov 15 13:33:34 GMT 2013 on /dev/pts/1 from 10.220.48.25
*******************************************************************************
* *
* *
* Welcome to AIX Version 7.1! *
* *
* *
* Please see the README file in /usr/lpp/bos for information pertinent to *
* this release of the AIX Operating System. *
* *
* *
*******************************************************************************
oslevel -s
My_Target_Server:msouvik:/export/home/msouvik>oslevel -s
7100-02-02-1316
can't read "expect_out(1,string)": no such element in array
while executing
"set output $expect_out(1,string)"
("while" body line 19)
invoked from within
"while {[gets $hosts host] >= 0} {
spawn -noecho ssh -t $u@$host
expect "?assword:*"
send -- "$p\r"
# Change server side prompt to mak..."
(file "./expect_script_new.sh" line 17)
My_NIM_Server:msouvik:/export/home/msouvik>
Is there anything I missed here? Excuse me if I could not understand the logic of your provided script
send -- "$p\r"
# Wait for original server side prompt
expect -re "(%|#|>|\$) *$"
# Change server side prompt to make matching more reliable
send "PS1='PROMPT# '\r"
My_NIM_Server:msouvik:/export/home/msouvik>./expect_script_3.sh
msouvik@My_NIM_Client_1's password:
Last unsuccessful login: Thu Nov 14 12:13:52 GMT 2013 on ssh from My_NIM_Server
Last login: Mon Nov 18 12:18:57 GMT 2013 on /dev/pts/2 from x.x.x.x
oslevel -s
*******************************************************************************
* *
* *
* Welcome to AIX Version 7.1! *
* *
* *
* Please see the README file in /usr/lpp/bos for information pertinent to *
* this release of the AIX Operating System. *
* *
* *
*******************************************************************************
exit
My_NIM_Client_1:msouvik:/export/home/msouvik>oslevel -s
7100-02-02-1316
My_NIM_Client_1:msouvik:/export/home/msouvik>exit
Connection to My_NIM_Client_1 closed.
SECURITY NOTICE
Use of this system, its equipment, and resources is monitored at all
times. All programs and information held on this system are private and
confidential to XXX Corporation, and are only lawfully available to
authorised users for authorised purposes only.
It is a criminal offence to obtain unauthorised access to any program
or information within this system and/or to make any unauthorised
modifications whatsoever to the contents of this computer system.
If you are not an authorised user you are violating the regulations of
this system and can, and will be prosecuted to the full extent of the
law. Please disconnect immediately.
msouvik@My_NIM_Client_2's password:
Last unsuccessful login: Thu Nov 14 12:13:52 GMT 2013 on ssh from My_NIM_Server
Last login: Mon Nov 18 13:03:43 GMT 2013 on /dev/pts/4 from My_NIM_Server
*******************************************************************************
* *
* *
* Welcome to AIX Version 7.1! *
* *
* *
* Please see the README file in /usr/lpp/bos for information pertinent to *
* this release of the AIX Operating System. *
* *
* *
*******************************************************************************
oslevel -s
My_NIM_Client_2:msouvik:/export/home/msouvik>oslevel -s
exit
7100-02-02-1316
My_NIM_Client_2:msouvik:/export/home/msouvik>exit
Connection to My_NIM_Client_2 closed.
So the script ran well, but didn't fetch me the expected o/p in the "config_details" file on the source server(My_NIM_Server), contents of this file below:
So essentially, what I understood is - the below portion of the script fails due to some reason:
Code:
# Load command output into variable output
set output $expect_out(1,string)
# Append output into (and host name) to local logfile
puts $config "$host: $output\r"
The $host variable is captured but not the $output. Leads again pls..
As I mentioned, not a big fan of parsing files within Expect, but this may work for you. It will also capture the output to a local log file:
Code:
#!/usr/bin/expect -f
#
#
# slurp in file containing hostnames
set hostfile [open "hosts" r]
set hostdata [read $hostfile]
close $hostfile
# loop through hosts, connect, and run command
foreach h [split $hostdata "\n"] {
log_file myLog.log # log output to a local log file
if {$h eq {}} continue # skip any blank lines encountered in the server file
set u "<username>"
set p "<password>"
set cmd "<command>"
spawn ssh -t $u@$h $cmd
expect "?assword:*"
send -- "$p\r"
send -- "exit\r"
send -- "\r"
expect eof
}
I looks like you have a large delay between entering the password and the unix prompt appearing. Do you experience this delay when logging in normally?
I know AIX can experience large login delays if /etc/resolv.conf is pointing to a non-existent nameserver, basically the reverse DNS lookup of the incoming IP address stalls waiting for a response.
If you are seeing these delays you may need to extend the timeout defined at the top of the script. It might be a good debugging tool anyway, extend timeout to say 10 seconds and watch where you see pauses in the output.
You may have to tweak this command to properly match the prompts you use on each of your servers:
Code:
# Wait for original server side prompt
expect -re "(%|#|>|\$) *$"
Currently the above looks for any line ending in one of % # > or $ followed by zero or more spaces. This could match text in your login messages or message of the day and is why I usually change PS1 to a unique string ASAP in these type of expect scripts.
Your target is to get output like this:
Code:
My_NIM_Server:msouvik:/export/home/msouvik>./expect_script_3.sh
msouvik@My_NIM_Client_1's password:
Last unsuccessful login: Thu Nov 14 12:13:52 GMT 2013 on ssh from My_NIM_Server
Last login: Mon Nov 18 12:18:57 GMT 2013 on /dev/pts/2 from x.x.x.x
*******************************************************************************
* *
* *
* Welcome to AIX Version 7.1! *
* *
* *
* Please see the README file in /usr/lpp/bos for information pertinent to *
* this release of the AIX Operating System. *
* *
* *
*******************************************************************************
My_NIM_Client_1:msouvik:/export/home/msouvik>PS1='PROMPT# '
PROMPT #oslevel -s
7100-02-02-1316
PROMPT #exit
Connection to My_NIM_Client_1 closed.
Notice how the commands are not output during the message of the day/ login banner. The PS1= command executes first and changes the system prompt, this is very important because the output capture from oslevel needs to match on the prompt to properly capture the command output.
I would have to do some more trial & error method to make your suggested technique of this script to work -- I'll update this discussion as soon as I could get it work. FYI, the highlighted portion(in red) below doesn't work:
Code:
My_NIM_Server:msouvik:/export/home/msouvik>./expect_script_3.sh
msouvik@My_NIM_Client_1's password:
Last unsuccessful login: Thu Nov 14 12:13:52 GMT 2013 on ssh from My_NIM_Server
Last login: Mon Nov 18 12:18:57 GMT 2013 on /dev/pts/2 from x.x.x.x
*******************************************************************************
* *
* *
* Welcome to AIX Version 7.1! *
* *
* *
* Please see the README file in /usr/lpp/bos for information pertinent to *
* this release of the AIX Operating System. *
* *
* *
*******************************************************************************
My_NIM_Client_1:msouvik:/export/home/msouvik>PS1='PROMPT#'
PROMPT #oslevel -s
7100-02-02-1316
PROMPT #exit
Connection to My_NIM_Client_1 closed.
The script is not able to set the PS1 shell parameter, it does it without being able to set it as below(already shared before):
Code:
My_NIM_Server:msouvik:/export/home/msouvik>./expect_script_3.sh
msouvik@My_NIM_Client_1's password:
Last unsuccessful login: Thu Nov 14 12:13:52 GMT 2013 on ssh from My_NIM_Server
Last login: Mon Nov 18 12:18:57 GMT 2013 on /dev/pts/2 from x.x.x.x
*******************************************************************************
* *
* *
* Welcome to AIX Version 7.1! *
* *
* *
* Please see the README file in /usr/lpp/bos for information pertinent to *
* this release of the AIX Operating System. *
* *
* *
*******************************************************************************
My_NIM_Client_1:msouvik:/export/home/msouvik>oslevel -s
7100-02-02-1316
My_NIM_Client_1:msouvik:/export/home/msouvik>exit
Connection to My_NIM_Client_1 closed.
msouvik@My_NIM_Client_2's password:
Last unsuccessful login: Thu Nov 14 12:13:52 GMT 2013 on ssh from My_NIM_Server
Last login: Mon Nov 18 12:18:57 GMT 2013 on /dev/pts/2 from x.x.x.x
*******************************************************************************
* *
* *
* Welcome to AIX Version 7.1! *
* *
* *
* Please see the README file in /usr/lpp/bos for information pertinent to *
* this release of the AIX Operating System. *
* *
* *
*******************************************************************************
My_NIM_Client_2:msouvik:/export/home/msouvik>oslevel -s
7100-02-02-1316
My_NIM_Client_2:msouvik:/export/home/msouvik>exit
Connection to My_NIM_Client_2 closed.
in2nix4life,
Your recent suggestion gave me error too, modified code pasted below:
Code:
+1 #!/usr/bin/expect -f
+2 #
+3 #
+4
+5 # slurp in file containing hostnames
+6 set hostfile [open "server_list" r]
+7 set hostdata [read $hostfile]
+8 close $hostfile
+9
+10 # loop through hosts, connect, and run command
+11 foreach h [split $hostdata "\n"] {
+12 log_file myLog.log # log output to a local log file
+13 if {$h eq {}} continue # skip any blank lines encountered in the server file
+14 set u "msouvik"
+15 set p "pass^123"
+16 set cmd "oslevel -s"
+17 spawn ssh -t $u@$h $cmd
+18 expect "?assword:*"
+19 send -- "$p\r"
+20 send -- "exit\r"
+21 send -- "\r"
+22 expect eof
+23 }
Error:
Code:
My_NIM_Server:msouvik:/export/home/msouvik>./expect_script.sh
wrong # args: extra words after "else" clause in "if" command
while compiling
"if {$h eq {}} continue # skip any blank lines encountered in the server file"
("foreach" body line 3)
invoked from within
"foreach h [split $hostdata "\n"] {
log_file myLog.log # log output to a local log file
if {$h eq {}} continue # skip any blank lines ..."
(file "./expect_script_4.sh" line 11)
Good news is, I could get my job done with pieces of code taken from each of your suggestions.
So, my expect code to run the desired cmd on target servers looks like this:
Code:
#!/usr/bin/expect -f
#
#
# set credentials
set u "msouvik"
set p "pass^123"
# get host name from command-line
set h [lindex $argv 0]
# set the command to run
set cmd "oslevel -s >> /export/home/msouvik/expect.out; multibos -S >> /export/home/msouvik/expect.out"
# spawn a connection to the host and run the given command
spawn -noecho ssh -t $u@$h $cmd
# handle the password prompt
expect "?assword:*"
send -- "$p\r"
send -- "\r"
And the code to scp the above run cmd o/p's is as below:
Code:
#!/usr/bin/expect -f
#
# set credentials
set u "msouvik"
set p "pass^123"
# get host name from command-line
set h [lindex $argv 0]
# scp the data onto NIM server
spawn -noecho scp $u@$h:/export/home/msouvik/expect.out /export/home/msouvik/expect/expect.out.$h
# handle the password prompt for scp
expect "?assword:*"
send -- "$p\r"
send -- "\r"
# done
expect eof
The scp is successfully able to get me the cmd o/p's to my NIM server suffixing with the relevant hostname as in "expect.out.$h"
You may ask, why did I choose to have 2 separate scripts for this purpose - thats coz when I club these to scripts into one - it fails to do the job(reason not known to me at the moment!)
The discussion doesn't end here until I'm able to fix both of your recent suggestions.
Hi All,
i am trying to ssh to a remote machine and execute certain command to remote machine through script.
i am able to ssh but after its getting hung at the promt and after pressing ctrl +d i am gettin the out put as
expect: spawn id exp5 not open
while executing
"expect "$" {... (3 Replies)
Ladies & Gents,
Can one of you gurus please show me a very simple "expect" script to change the password in Solaris in a script, please? Nothing fancy, no error checking, no nothing. Just to change the password of a new user, it's all.
Many thanks in advance. U guys have honestly earned my... (1 Reply)
Hi,
I need to run a test script to check all test accounts, is it possible to pass the password to su in following command? I've got following error:
$ echo "${password}" | su ${test_account} -c "check_account.sh"
standard in must be a tty
Thank you.
- j (3 Replies)
Friends,
Need someone's help in helping me with the below requirement for a script:
> For a list of servers(over 100+), I need to login into each of them(cannot configure password-less ssh) & grab few configuration details <
I know, this is possible through expect programming in a simple... (2 Replies)
I need a shell script using expect to login to couple of remote servers and read "crontab -l -u <username>" & "cat /etc/rc.local" & "df -h" and able to create output into a file saved locally with hostname.crontab & hostname.rc.local & disk.status. I can supply a file as list of hostname or IP... (4 Replies)
Hi
I'm trying to run a script " abc.sh" which triggers "use.sh" .
abc.sh is nothing but a "expect" script which provides username and password automatically to the use.sh script.
Please find below the scripts:
#abc.sh
#!/usr/bin/expect -f
exec /root/use.sh
expect "*name*"
send... (1 Reply)
Hi,
I am trying to use "Expect" in shell script to ssh and do some work in remote server but I am unable to connect. Here is the code I am using.
#save as test.sh
set ip "10.10.10.10"
set username "uname"
set password "upass"
spawn ssh $username@$ip
expect "Password:"
send... (8 Replies)
Hello All,
I am a newbie in Shell script programming, and maybe you can help me with my query.
I need to write a shell script (mntServer.ksh) that will start a background process and also to be able to run another script.
The mntServer.ksh script contains:
#!/bin/ksh... (1 Reply)
hi friends,
i m tryin to load data from one set of table to other i have sql procedure al ready for it..!
i m going to load the procedure only if data in one of my table for example
table "landing " have 10 records each attribute of this table is
file_name status date ... (2 Replies)