LinuxQuestions.org

LinuxQuestions.org (/questions/)
-   Programming (https://www.linuxquestions.org/questions/programming-9/)
-   -   Span error is coming in Expect script. (https://www.linuxquestions.org/questions/programming-9/span-error-is-coming-in-expect-script-4175633891/)

cj_cheema 07-12-2018 09:51 PM

Span error is coming in Expect script.
 
Hi

I have created an expect script which used for running health check shell script(UX_health_monitor.sh) saved in remote Linux servers. This expect script is able to run remotely saved health check shell script from my jump Linux server and this same expect script is able to do scp of remotely generated health report to my jump server.
But this expect script is not able to send me email.

But at the end of execution of this expect script I am getting below error message:

spawn ssh -o StrictHostKeychecking=no batman@
ssh: Could not resolve hostname : Name or service not known
spawn 'echo "Find the Attached Daily Health Check Report of Backup Servers" | mail -s "Backup Servers Daily Health Check Report `date +%d%b%Y`" cj@delta.com -A /tmp/health_mon/Daily_Health_Report*_`date +%d%b%Y`.txt'
couldn't execute "'echo "Find the Attached Daily Health Check Report of Backup Servers" | mail -s "Backup Servers Daily Health Check Report `date +%d%b%Y`" cj@delta.com -A /tmp/health_mon/Daily_Health_Report*_`date +%d%b%Y`.txt'": no such file or directory
while executing
"spawn '$MAIL'"
(file "./expect_health_report" line 78)
[root@abc]#


Below is the code of my expect script:
Code:

#!/usr/bin/expect -f

# Set timout for script

set timeout 5

# Defining Login user and password
set user "batman"
set password "robin"

# Get the list of hosts, one per line
set fh [open "hosts.txt"]
set hosts [split [read $fh] "\n"]
close $fh

# commands to run, one per line
set HCR {/root/health_mon/UX_health_monitor.sh 1> /tmp/Daily_Health_Report_`hostname`_`date +%d%b%Y`.txt 2> /dev/null}
set MAIL {echo "Find the Attached Daily Health Check Report of Backup Servers" | mail -s "Backup Servers Daily Health Check Report `date +%d%b%Y`" cj@delta.com -A /tmp/health_mon/Daily_Health_Report*_`date +%d%b%Y`.txt}

# Generated health report file path and Jump server path is defined for scp.
set SCP_FILE "/tmp/Daily_Health_Report_`hostname`_`date +%d%b%Y`.txt"
set SCP_REMOTE "$user@abc:/tmp/health_mon"


# Let the script play..

# Login to the remote Linux hosts

foreach host $hosts {
    spawn ssh -o StrictHostKeychecking=no $user@$host
    expect {
      timeout { continue; }
      eof { continue; }
      "password:"
    }

    send "$password\r"

    # Become sudo
    expect "$"
    send "sudo su -\r"
    expect "password:"
    send "$password\r"


  # Run the health Check command
    expect "# " { send "$HCR\r" }


# Gather the generated Health Check report from Remote Linux hosts and send it to central jump Linux Server.
  expect "#"
  send "scp -o StrictHostKeyChecking=no $SCP_FILE $SCP_REMOTE\r"
  expect "password:"
  send "$password\r"
  expect "100%"
  sleep 1

  # Exit from Remote Linux hosts
    expect "# "
    send "exit\r"
    expect "$"
    send "exit\r"
    expect eof
}

#  Send Report on email.
    sleep 2 
    spawn '$MAIL'
    expect eof


pan64 07-13-2018 01:03 AM

you have at least two errors:
hostname is invalid and also something wrong with that SCP_FILE

jlinkels 07-13-2018 04:42 AM

The error message is pretty clear. The host cannot be found. You are trying to ssh to batman@. Instead of batman@<hostname>.

Why don't you add some very basic trace or debugging statements to your code so that you know at least what your code is doing?

jlinkels

Turbocapitalist 07-13-2018 05:24 AM

There are also two very deadly bugs with your code. The first one is using passwords instead of keys. By itself it would be dependent on the strength of the password, but when combined with the second bug it guarantees 100% success of any Man-in-the-Middle attacks. The second one is that you have set StrictHostKeychecking to "no". Again, that guarantees 100% success of any Man-in-the-Middle attacks between your machines. Wherever you copied that script from, you should report them for security violations and promulgating unsound practices.

OpenSSH can't protect you if it is configured in an unsafe manner like you have in your current script.

Before progressing, please change StrictHostKeychecking back to "yes" or at least to "accept-new". Then please set up key-based authentication between your client machine and your SSH server so that you can turn off password authentication.

Turbocapitalist 07-13-2018 05:33 AM

There is a third unsafe practice in your script, that is the passing of the root password for the remote machine just to run a single script. Remove the stanza entitled "Become sudo". Instead say:

Code:

...
set HCR {/root/health_mon/UX_health_monitor.sh}

...

    expect "# " { send "sudo $HCR > /tmp/Daily_Health_Report_$(hostname)_$(date +%d%b%Y).txt 2>/dev/null \r" }
...

And in order for that to run on the remote machine, have /etc/sudoers configured correctly there:

Code:

%batman ALL=(root:root) NOPASSWD: /root/health_mon/UX_health_monitor.sh ""
That way you do not need to have the password nor is there a way to escape from the script since no parameters may be passed. In fact, it might be possible then to do away with expect entirely and just SSH with the shell. Less complicated.

cj_cheema 07-16-2018 05:36 PM

Thanks for highlighting security vulnearbilty in my script surely I will resolve this as you suggested. But issue with my script is it is not able to send email I have put this below code for sending email by expect:

Code:

sleep 2 
    spawn '$MAIL'
    expect eof

Let me know if there is alternate way for sending email through expect script my motive is post generating of health check report expect should exit from remote machine and from jump server it send email to me with the attached report which is gathered from scp from remote machine.

As of now I am able to gather health check report from scp that means code is running fine till that below parameters:

Code:

#!/usr/bin/expect -f

# Set timout for script

set timeout 5

# Defining Login user and password
set user "batman"
set password "robin"

# Get the list of hosts, one per line
set fh [open "hosts.txt"]
set hosts [split [read $fh] "\n"]
close $fh

# commands to run, one per line
set HCR {/root/health_mon/UX_health_monitor.sh 1> /tmp/Daily_Health_Report_`hostname`_`date +%d%b%Y`.txt 2> /dev/null}
set MAIL {echo "Find the Attached Daily Health Check Report of Backup Servers" | mail -s "Backup Servers Daily Health Check Report `date +%d%b%Y`" cj@delta.com -A /tmp/health_mon/Daily_Health_Report*_`date +%d%b%Y`.txt}

# Generated health report file path and Jump server path is defined for scp.
set SCP_FILE "/tmp/Daily_Health_Report_`hostname`_`date +%d%b%Y`.txt"
set SCP_REMOTE "$user@abc:/tmp/health_mon"


# Let the script play..

# Login to the remote Linux hosts

foreach host $hosts {
    spawn ssh -o StrictHostKeychecking=no $user@$host
    expect {
      timeout { continue; }
      eof { continue; }
      "password:"
    }

    send "$password\r"

    # Become sudo
    expect "$"
    send "sudo su -\r"
    expect "password:"
    send "$password\r"


  # Run the health Check command
    expect "# " { send "$HCR\r" }


# Gather the generated Health Check report from Remote Linux hosts and send it to central jump Linux Server.
  expect "#"
  send "scp -o StrictHostKeyChecking=no $SCP_FILE $SCP_REMOTE\r"
  expect "password:"
  send "$password\r"
  expect "100%"
  sleep 1

  # Exit from Remote Linux hosts
    expect "# "
    send "exit\r"
    expect "$"
    send "exit\r"
    expect eof
}

But it is failing in below code:

Code:

sleep 2 
    spawn '$MAIL'
    expect eof


jlinkels 07-16-2018 06:31 PM

Did you resolve the first problem then? Any feedback to the forum how you solved it and what error it was?

You say
Quote:

Code:

sleep 2 
    spawn '$MAIL'
    expect eof


How is it failing? Error message?
It did give an error message. Have you read it? What should it mean?

And no, this is not the way to send mail. Use the tcl exec command to execute an external command. Capture the output of exec and perform a check on the result. You don't have to connect, enter passwords, wait for reply etc, so it is no use to use an expect command.

What upsets me is that your first line in your OP is:
Quote:

I have created an expect script which used for running health check shell
You did not create it. You copied it and you don't have a clue what you are doing. Copying as such is not a problem, we all do. But it is annoying if you claim you created it.

jlinkels

Turbocapitalist 07-17-2018 01:31 AM

Quote:

Originally Posted by cj_cheema (Post 5879929)
Thanks for highlighting security vulnearbilty in my script surely I will resolve this as you suggested.

Ok. Great. We await the updated, safer script (minus the multiple severe vulnerabilities) for review and can help you then once once you post it.

What kind of feed back did you get from the author of the script when you reported the security violations it causes?


All times are GMT -5. The time now is 02:11 PM.