Interaction-free shell programming (EOF, Expect use)

One, Here Document free interaction concept

Use I/O redirection to provide the command list to interactive programs or commands. For example, ftp, cat, or read commands
are a substitute for standard input, which helps script developers not to use temporary files to construct input information, but to directly generate a "file" on the spot and use it as standard input for "commands". Here Document can also be used with non-interactive programs and commands.

1. Structure

语法格式:
命令 <<标记  #标记这里不能有空格
...
内容    #标记直接是传入内容
...
标记         #标记这里不能有空格

Matters needing attention :

The mark can use any legal character (usually EOF). The
ending mark must be written in the top
box, and there can be no characters
before the ending mark. There can be no characters after the ending mark (including spaces) . The spaces before and after the beginning mark will be omitted.

The EOF here is just a mark that the first one indicates the beginning, and the last one indicates the end. EOF is usually used to indicate the mark

Pass the content of the mark into the dd.txt file, you can see that when you write it again, all the original content is overwritten.
Insert picture description here

2. EOF example:

1. Interaction-free way to realize the statistics of the number of rows, put the content to be counted between the mark "EOF", and directly pass the content to wc -l for statistics

wc -l <<EOF
>Line1
>Line2
>EOF

Insert picture description here

2. Receive input and print it through the read command. The input value is the part between the two EOF tags as the value of the variable i

read i <<EOF
> good night     #将good night 赋值给i
> rain drop      #再赋值一个发现输出时只能显示一个
> EOF

Insert picture description here

3. Set a password for the user through passwd

passwd list <<EOF
>123           
>123
EOF

Insert picture description here

4. Support variable substitution

When writing the file, it will first replace the variable with the actual value, and then complete the writing with the cat command


#!/bin/bash
file="ss.txt"
i="play"
cat > $file <<EOF
I want to $i
EOF

Insert picture description here
You can see that the ss.txt file is automatically created and written
Insert picture description here

5. Assign the value to the variable as a whole, and then print the value of the variable through the echo command


#!/bin/bash
var="hello! I want to sleep"
myvar=$(cat <<EOF
6666
Today is a good day.
$var
EOF
)
echo $myvar

Execution result You
Insert picture description here
can see that there is no blank line here,
Insert picture description here
execution result
Insert picture description here

6. Turn off the variable replacement function, and output the characters as they are, without any modification or replacement


#!/bin/bash
var="hello! I want to sleep"
myvar=$(cat <<'EOF'
6666
Today is a good day.
$var
EOF
)
echo "$myvar"

Insert picture description here

7. Remove the TAB character before each line

Insert picture description here


#!/bin/bash
var="hello! I want to sleep"
myvar=$(cat <<-'EOF'
	6666
	Today is a good day.
	$var
EOF
)
echo "$myvar"

Insert picture description here

8. Multi-line comments

The default comment of Bash is "#". This comment method only supports single-line comments: The introduction of Here Document solves the problem of multi-line comments.
":" represents an empty command that does nothing. The content of the middle mark area will not be executed and will be ignored by bash, so the effect of batch comments can be achieved.


#!/bin/bash
var="hello! I want to sleep"
: <<-'EOF'
        6666
        Today is a good day.
        $var
EOF

echo "$myvar"
echo "666"

Insert picture description here

Two, Expect no interaction

Expect

  • It is a tool based on the tcl language. It is often used for automated control and testing to solve interactive problems in shell scripts.

1. Installation

rpm -q expect
rpm -q tcl
yum install -y expect

Insert picture description here
Insert picture description here

2. Basic commands

(1) Script interpreter

  • The file is first introduced in the expect script to indicate which shell to use

#!/usr/bin/expect

(2) spawn

  • Spawn is usually followed by a command to open a session, start a process, and track subsequent interaction information.
例:spawn passwd root

(3) expect

  • Judge whether the last output result contains the specified string, if there is, return immediately, otherwise, wait for the timeout period and return;
  • Can only capture the output of the process started by spawn;
  • Used to receive the output after the command is executed, and then match the expected string

(4) send

  • Send a character string to the process to simulate the user's input; this command cannot automatically enter and line feed, usually add \r (carriage return) or \n

例如:发送密码
方式一:
expect "密码" {
    
    send "123123\r"}		#同一行send部分要有{}
方式二:
expect "密码"	
send "123123\r"							#换行send部分不需要有{}
方式三:
expect					#只要匹配了其中一个情况,执行相应的send语句后退出该expect语句
{
    
    
"密码1" {
    
    send "123123\r"}
"密码2" {
    
    send "123133\r"}
"密码3" {
    
    send "abc123\r"}
}

(5) The terminator expect eof and interact

expect eof:

  • Indicates the end of the interaction, waiting for the execution to end, returning to the original user, corresponding to spawn
  • For example, when switching to the root user, the expect script waits for 10s by default. When the command is executed, it stays for 10s by default and automatically switches back to the original user.
expect eof

interact:

  • After the execution is completed, the interactive state is maintained, and the control is transferred to the console. It will stay at the target terminal instead of returning to the original terminal. At this time, you can manually operate it. The command after interact does not work, such as adding exit after interact. It will not exit the root user. If there is no interaction, it will log out after logging in, instead of staying on the remote terminal.

  • If you use interact, you will stay in the terminal instead of returning to the original terminal. For example, when you switch to the root user, you will always be in the root user state; for example, when you ssh to another server, you will always be in the target server terminal instead of switching back to the original server. .

interact .

(6) set

  • The default timeout period of expect is 10 seconds. The session timeout period can be set through the set command. If the timeout period is not limited, it should be set to -1.

(7) exp_continue

  • exp_continue is appended to a certain expect judgment item, so that after the item is matched, it can continue to match other items in the expect judgment sentence. exp_continue is similar to the continue statement in the control statement.
  • For example: The following example will determine whether there is yes/no or *password in the interactive output. If it matches yes/no, output yes and execute the judgment again; if it matches *password, output abc123 and end the expect statement.
expect {
    
    
    "(yes/no)" {
    
    send "yes\r"; exp_continue;}
    "*password" {
    
    set timeout 300; send "abc123\r";}
}

#注意:使用exp_continue时,如果跟踪像 passwd 这样的输入密码后就结束进程的命令,expect{}外不要再加上expect eof
#因为spawn进程结束后会向expect发送eof,会导致后面的 expect eof 执行报错

(8) send_user

  • Represents an echo command, equivalent to echo
send_user

(9) Receive parameters

  • The expect script can accept parameters passed from the bash command line and get it using [lindex $argv n]. Among them, n starts from 0 and represents the first, second, third...parameters respectively.
例:
set hostname [lindex $argv 0]   	相当于 hostname=$1
set password [lindex $argv 1]		相当于 password=$2

Three, use example:

1.expect

  • Execution cannot be executed in the previous way, expect is executed directly, you need to use the expect command to execute the script

Example: Switch users without interactive su


#!/usr/bin/expect
#设置超时时间
set timeout 3
#设置输入用户和密码
set username [lindex $argv 0]
set password [lindex $argv 1]

spawn su $username
expect "密码" {
    
    send "$password\r"}
interact       #会停留在目标终端而不会退回到原终端
  #或者expect eof  当执行完命令后,默认停留10s后,自动切回了原用户

Insert picture description here

Example: Free interactive link ssh


#!/usr/bin/expect
set timeout 3      #超时时间为3秒,不设置得话 默认为10秒

set hostname [lindex $argv 0]
set password [lindex $argv 1]

spawn ssh $hostname

expect {
    
    

  "(yes/no)" {
    
    send "yes\r"; exp_continue }
  "*password:" {
    
    send "${password}\r"}
}

expect eof    #这里执行后跳回
#interact     这里是保持执行后得控制台位置,不跳回。

Insert picture description here

2. Embedded execution mode, integrate the expect process into Shell to facilitate execution and processing

Example: Create a user and set a password

#!/bin/bash

usrname=$1
passwd=$2

useradd $usrname        #非交互得命令放在外面得脚本里

/usr/bin/expect <<EOF   #嵌入expect
  spawn passwd $usrname #开启spawn跟踪passwd命令
    #匹配字符,并且发送字符串
    expect "新的*" {
    
    send "${passwd}\r"}
    expect "重新*" {
    
    send "${passwd}\r"}
    expect eof  #结束符
EOF  

Insert picture description here

![

After awk query keywords, you can see how many users I have created.
Insert picture description here

Example: Embedded interactive ssh login


#!/bin/bash

hostname=$1
password=$2

/usr/bin/expect<<EOF
spawn ssh $hostname 
  expect {
    
    
  "(yes/no)" {
    
    send "yes\r";exp_continue}
  "*password" {
    
    send "$password\r"}

}
expect "*]#" {
    
    send "ifconfig\r"}
expect eof

Insert picture description here

Automatically jump back after execution
Insert picture description here

Example: Create a disk without interaction


#!/bin/bash
disk=$1

/usr/bin/expect<<EOF

spawn fdisk $disk
 expect "命令"  {send "n\r"}
 expect "Select" {send "\r"}
 expect "分区" {send "\r" }
 expect "起始" {send "\r"}
 expect "Last" {send "\r"} 
 expect "命令(输入 m 获取帮助):" { send "w\r"}
expect eof
EOF
partprobe
mkfs.xfs $disk -f &> /dev/null
if [ $? -eq 0 ]
then
echo -e " 磁盘格式化完成 "
mkdir $disk.1
mount $disk $disk.1
df -h
else
echo "格式化shibai"
fi

Insert picture description here

Insert picture description here

Guess you like

Origin blog.csdn.net/weixin_44324367/article/details/111714823