so I have the following code and cant figure out how to only display one send command. I only need the result from the df -h send command.
#!/usr/bin/env bash
echo "Updating Source..."
/usr/bin/expect << EXPECT
log_user 0;
spawn -noecho ssh -p 7742 user#location
expect "username:"
send "username\r"
expect "password:"
send "password\r"
send "shell\r"
send "df -h\r"
send "exit\r"
sleep .5
send "exit\r"
interact
EXPECT
Try the following:
#!/usr/bin/env bash
echo "Updating Source..."
/usr/bin/expect << EXPECT
log_user 0;
spawn -noecho ssh -p 7742 user#location
expect "username:"
send "username\r"
expect "password:"
send "password\r"
send "shell\r"
log_user 1;
send "df -h\r"
log_user 0;
send "exit\r"
sleep .5
send "exit\r"
interact
EXPECT
Related
I have the following expect script within a bash script and I'm unsure as to why the interact command is not working.
expect <<-EOS
#!/usr/bin/expect
set timeout $EXP_TIMEOUT
send_user "\n The timeout being used is $EXP_TIMEOUT \n"
send_user "\nLogging into remote host via SSH:\n"
spawn ssh -q -o ConnectTimeout=$SSH_TIMEOUT -o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null ${hostname}
expect "*assword*"
send -- "$secret\r"
expect {
"*assword*" {
send \x03
puts "\nIncorrect Password\n"
}
"$prompt" {
send -- "/usr/seos/bin/sesu - $user\r"
expect "*assword*"
send -- "$secret\r"
expect "$prompt"
send -- "id\r"
expect "$prompt"
send -- "hostname -s\r"
interact
}
}
expect eof
EOS
Thank you all for your help!
interact can't let the user enter data via stdin because you are already redirecting stdin for the here document.
Instead, you can save your here document with all expansions to a variable, and then pass that to -c. Here's a simplified example:
script=$(cat << EOF
spawn vi
send "iHello $(hostname)"
interact
EOF
)
expect -c "$script"
I need some help on below code. I just need to achieve some simpliest task. bakcup and replace some ssl certificate files. but it doesn't seem to work. what is wrong with below code:
import_esx() {
local username=root
local backuptimestamp=$(date +"%m-%d-%y-%I:%M:%S_%p")
/usr/bin/expect << EOF
set timeout 30
spawn ssh -l $username $Ip_Address
expect {
"(yes/no)?" { send "yes\r"; exp_continue }
"*?assword: " { send "$CommonPassword\r"; exp_continue}
}
send_user "Backing up current certificates\r"
send "mv /etc/vmware/ssl/rui.key /etc/vmware/ssl/rui.key.$backuptimestamp\r"
send "mv /etc/vmware/ssl/rui.crt /etc/vmware/ssl/rui.crt.$backuptimestamp\r"
send "mv /etc/vmware/ssl/castore.pem /etc/vmware/ssl/castore.pem.$backuptimestamp\r"
EOF
}
thanks
Jerry
expect {
"(yes/no)?" { send "yes\r"; exp_continue }
"*?assword: " { send "$CommonPassword\r"; exp_continue}
}
you exp_continue on each branch: You have to expect something else so you can stop looping.
Before each send, you should expect something, typically the shell prompt. Also, after the last mv command, you need to send "exit\r" and then expect eof
Assuming your shell prompt ends with "dollar space", you can put it all together:
set prompt {[$] $}
expect {
"(yes/no)?" { send "yes\r"; exp_continue }
"*?assword: " { send "$CommonPassword\r"; exp_continue}
-re $prompt
}
send_user "Backing up current certificates\r"
send "mv /etc/vmware/ssl/rui.key /etc/vmware/ssl/rui.key.$backuptimestamp\r"
expect -re $prompt
send "mv /etc/vmware/ssl/rui.crt /etc/vmware/ssl/rui.crt.$backuptimestamp\r"
expect -re $prompt
send "mv /etc/vmware/ssl/castore.pem /etc/vmware/ssl/castore.pem.$backuptimestamp\r"
expect -re $prompt
send "exit\r"
expect eof
Im trying to compile a script that establishes an ssh connecting with a remote machine and searches multiple log files for error messages, my current code is the following:
#!/bin/bash
expect <<-EOF > /home/file
set timeout 3
spawn ssh -oPort=port ip zgrep "error" /dir/dir/file.gz.\[54321\]
expect "Are you sure you want to continue connecting (yes/no)?" { send "yes\r" }
expect "*password: " { send "password\r" }
expect "*#" { send "exit\r" }
EOF
expect <<-EOF >> /home/file
set timeout 3
spawn ssh -oPort=port ip zgrep "error" /dir/dir/file1.gz.\[54321\]
expect "Are you sure you want to continue connecting (yes/no)?" { send "yes\r" }
expect "*password: " { send "password\r" }
expect "*#" { send "exit\r" }
EOF
expect <<-EOF >> /home/file
set timeout 3 ip
spawn ssh -oPort=port ip grep error /dir/dir/file
expect "Are you sure you want to continue connecting (yes/no)?" { send "yes\r" }
expect "*password: " { send "password\r" }
expect "*#" { send "exit\r" }
EOF
expect <<-EOF >> /home/file
set timeout 3
spawn ssh -oPort=port ip grep error /dir/dir/file1
expect "Are you sure you want to continue connecting (yes/no)?" { send "yes\r" }
expect "*password: " { send "password\r" }
expect "*#" { send "exit\r" }
EOF
Now have you may have noticed i connect to the machine 4 times, which feels so inefficient, i have tried to put all of this log searches into 1 ssh connection, like the following:
expect <<-EOF > /home/file
set timeout 3
spawn ssh -oPort=port ip zgrep "error" /dir/dir/file.gz.\[54321\]
expect "Are you sure you want to continue connecting (yes/no)?" { send "yes\r" }
expect "*password: " { send "password\r" }
expect "*#" { send "grep error /dir/dir/file1\r" }
expect "*#" { send "exit\r" }
EOF
but when i try this i get the error
spawn id exp4 not open
while executing
"expect "*#" { send "grep error /dir/dir/file1\r" }"
What is wrong with this code that make it output this error,
All help appreciated
You can use a single command to do all the work required in one expect session:
expect <<-EOF > /home/file
set timeout 3
spawn ssh -oPort=port ip "zgrep error /dir/dir/file.gz.[54321] ; zgrep error /dir/dir/file1.gz.[54321] ; grep error /dir/dir/file ; grep error /dir/dir/file1"
expect "Are you sure you want to continue connecting (yes/no)?" { send "yes\r" }
expect "*password: " { send "password\r" }
expect "*#" { send "exit\r" }
EOF
You will need to modify your quotation " marks and escape characters \ so that the remote shell does not to interpret them. There is no need to wrap the string error in quotation marks.
Here is my script
#!/bin/ksh
RemoteFile=`grep "${File}" ${TempLog}` --> the value of the variable is Site Information_2013-07-04-00-01-26.CSV
/usr/bin/expect << EOF
spawn sftp user#server
expect "password:"
send "123fakepassword\n"
expect "sftp>"
send "cd /home/user/pickup_dir\n"
expect "sftp>"
send "lcd /home/user/Scripts/mart/wmt/RAMDISK0\n"
expect "sftp>"
send "get $RemoteFile\n" ---> I'm trying to pass it here so I can download the file.
expect "sftp>"
send "exit\r"
EOF
But no luck!, How can I pass a filename with double quote so the it will execute as (get "Site Information_2013-07-04-00-01-26.CSV\n") I'm placing it in variable cause the filename change on date. Or A'm I doing it wrong? I know not good to hard code the password but we can't use ssh-key to have a passwordless sftp. Thanks!
You just need to send some quotes. Pick one of
send "get '$RemoteFile'\n"
send "get \"$RemoteFile\"\n"
#!/bin/bash
while true
do
/usr/bin/expect <<EOF
set timeout 300
spawn sftp $remoteUser#$remoteIp
expect "yes/no" {
send "yes\r"
expect "*?assword" { send "$remotePass\r" }
} "*?assword" { send "$remotePass\r" }
expect "sftp> " { send "cd $RemoteFolderPath\r" }
expect "sftp> " { send "mget $remoteFileName\r" }
expect "sftp> " { send "quit\r" }
interact
EOF
done
exit
I'm trying to use expect in an bash script to provide the SFTP password and put other commands.
I'am try to get the return code of binary SFTP .
My test script :
#!/bin/bash
USER=$1
HOST=$2
PASSWD=$3
PORT=$4
FILEIN=$5
FILEOUT=$6
ACTION=$7
CR_FTP=`/usr/bin/expect <<EOF | tee -a log.log
spawn sftp -v -oPort=$PORT $USER#$HOST
expect "password:"
send "$PASSWD\r"
expect "sftp>"
send "ls\r"
expect "sftp>"
send "$ACTION $FILEIN $FILEOUT\r"
expect "sftp>"
send "bye\r"
EOF`
echo " -------------------- $CR_FTP --------------------------"
...
send "bye\r"
expect eof
set details [wait]
puts "sftp exit status=[lindex $details 3]"
EOF`
See http://www.tcl.tk/man/expect5.31/expect.1.html