Linux3月7日-shell脚本进阶函数

文章目录

  • 脚本函数三种写法
  • 信号捕捉trap
  • 创建临时文件mktemp
  • 安装复制文件install
  • 交互式转化批处理工具expect
  • shell脚本数组

函数function是由若干条shell命令组成的语句块,实现代码重用和模块化编程,它与shell程序形式上相似,不同的是它不是一个单独的进程,不能独立运行,而是shell程序的一部分。

脚本函数三种写法

[root@rocky8 ~]# help function
function: function name { COMMANDS ; } or name () { COMMANDS ; }
    Define shell function.
    
    Create a shell function named NAME.  When invoked as a simple command,
    NAME runs COMMANDs in the calling shell's context.  When NAME is invoked,
    the arguments are passed to the function as $1...$n, and the function's
    name is in $FUNCNAME.
    
    Exit Status:
    Returns success unless NAME is readonly.
#语法一:
function (){
   ...函数体...
}

#语法二:
function func_name{
   ...函数体...
}

#语法三:
function func_name(){
   ...函数体...
}

Linux3月7日-shell脚本进阶函数_第1张图片

信号捕捉trap

trap命令可以捕捉信号,修改信号原来的功能,实现自定义功能。

为什么我们按下ctrl+c键就能结束linux当前正在运行的进程,比如ping命令默认是一直进行ping,当你按下ctrl+c时就结束了ping,为什么会这样?其实是ctrl+c向ping发送了一个停止的信号,可以使用“trap -l”查看所有的信号
Linux3月7日-shell脚本进阶函数_第2张图片
Linux3月7日-shell脚本进阶函数_第3张图片

#列出所有信号
trap -l

#进程收到系统发出的指定信号后,将执行自定义指令,而不会执行原操作。
trap '触发指令' 信号

#列出自定义信号操作
trap -p

#当脚本退出时,执行finish函数
trap finish EXIT

信号捕捉的应用:将来在程序执行时,不希望被ctrl+c这样的异常突然终止掉程序。信号捕捉工具就是trap,trap是内部命令,内部命令通过help查看帮助。外部命令则可以通过man查看。
Linux3月7日-shell脚本进阶函数_第4张图片

#! /bin/bash
# 捕获2信号 2信号是: 2) SIGINT 
trap 'echo 删除跟系统,不能中断' 2
while true; do
        echo "正在删除系统中,请稍后!"
        sleep 1
done

Linux3月7日-shell脚本进阶函数_第5张图片
安全退出

#! /bin/bash
  
finish(){
    echo "Finish at `date +%F_%T`" | tee -a /root/finish.log
}

trap finish exit

while true ;do
     echo running
     sleep 1
done

Linux3月7日-shell脚本进阶函数_第6张图片
Linux3月7日-shell脚本进阶函数_第7张图片

创建临时文件mktemp

mktemp命令用于创建显示临时文件,可避免冲突。


mktemp [option]...[TEMPLATE]
#说明:template: filenameXXXX x至少要出现三个

Linux3月7日-shell脚本进阶函数_第8张图片
Linux3月7日-shell脚本进阶函数_第9张图片
编写"rm.sh"脚本实现手工制作垃圾箱

#! /bin/bash
DIR=`mktemp -d /tmp/trash-$(date +%F_%H-%M-%S)xxxxxx`
mv $* $DIR
echo $* is move to $DIR

定义一个rm的别名,将’'rm.sh"脚本赋值给rm这个别名。
在这里插入图片描述Linux3月7日-shell脚本进阶函数_第10张图片

安装复制文件install

install 功能相当于cp,chmod,chown,chgrp,mkdir等相关命令的集合
在这里插入图片描述
在这里插入图片描述

交互式转化批处理工具expect

expect是由Don Libes基于Tcl(Tool Command Language)语言开发的,主要应用于自动化交互式操作的场景,借助expect处理交互的命令,可以将交互过程如:ssh登录,ftp登录写在一个脚本上,使之自动化完成,尤其适用于需要多台服务器执行相同操作的环境中,可以大大提高系统管理人员的工作效率。expect需要安装 yum -y install except

交互式命令:需要你输入yes/no才能执行下一步的操作。

expect中相关命令
·spawn         启动新的进程
·expect        从进程接收字符串
·send          用于向进程发送字符串
·interact      运行用户交互
·exp_continue  匹配多个字符串在执行动作后加次命令

Linux3月7日-shell脚本进阶函数_第11张图片
可以认为expect就是一种独立的脚本编程语言,则它的首行机制就是“/usr/bin/expect”

#!/usr/bin/expect
spawn scp /etc/redhat-release 10.0.0.201:/data
expect {
     "yes/no" { send "yes\n";exp_continue }
     "password" { send "123456\n"}
}
expect eof

#此脚本是将当前机器上的linux版本信息远程拷贝到10.0.0.201机器上,并在需要交互yes时,自动输入yes,并在需要输入201机器上的密码时,自动输入密码

因为不是/bin/bash了,所以expect1的执行就只能是赋予执行权限之后执行了。
在这里插入图片描述
回到交互式(interact)

#!/usr/bin/expect
spawn ssh 10.0.0.210
expect {
        "yes/no" { send "yes\n";exp_continue }
        "password" { send "123456\n" }
}
interact

Linux3月7日-shell脚本进阶函数_第12张图片
expect 通过set赋值变量

#!/usr/bin/expect
set ip 10.0.0.201
set user root
set password 123456
set timeout 10
spawn ssh $user@$ip
expect {
       "yes/no" { send "yes\n";exp_continue }
       "password" { send "$password\n"}
}
interact

expect 位置参数,(执行脚本实,后面的参数的位置得和脚本里定义的参数的位置保持一直)

#!/usr/bin/expect
set ip [lindex $argv 0]
set user [lindex $argv 1]
set password [lindex $argv 2]
spawn ssh $user@$ip
expect {
		"yes/no" { send "yes\n";exp_contiune }
		"password" { send "$password\n"}
}
interact

Linux3月7日-shell脚本进阶函数_第13张图片
shell脚本调用expect

#!/bin/bash
ip=$1
user=$2
password=$3
expect <<EOF
set timeout 20
spawn ssh $user@$ip
expect {
      "yes/no" { send "yes\n";exp_continue }
      "password" { send "$password\n" }
}
expect "]#" { send "useradd hehe\n" }
expect "]#" { send "echo 123456 | passwd --stdin hehe\n" }
expect "]#" { send "exit\n" }
expect eof
EOF

#一定记得expect和{之间有空格啊,不然就报invalid
#invalid command name "expect{"
#    while executing
#"expect{"

Linux3月7日-shell脚本进阶函数_第14张图片
Linux3月7日-shell脚本进阶函数_第15张图片
在多个机器201,216,217上,批量创建test账号

#!/bin/bash
NET=10.0.0
user=root
password=123456
IPLIST="
201
216
217
"
for ID in $IPLIST;do
ip=$NET.$ID

expect <<EOF
set timeout 20
spawn ssh $user@$ip
expect {
      "yes/no" { send "yes\n";exp_continue }
      "password" { send "$password\n" }
}
expect "]#" { send "useradd test\n" }
expect "]#" { send "exit\n" }
#关闭selinux
#expect "]#" { send "sed -i ‘s/^SELINUX=enforcing/SELINUX=disabled/’ /etc/selinux/config\n" }
#expect "]#" { send "setenforce 0\n" }
expect eof
EOF
done
#批量创建test账号成功
[root@rocky8 scripts]# bash expect6.sh 
spawn ssh [email protected]
[email protected]'s password: 
Activate the web console with: systemctl enable --now cockpit.socket

Last login: Tue Mar 14 14:39:27 2023 from 10.0.0.210
[root@centos8 ~]# useradd test
[root@centos8 ~]# exit
logout
Connection to 10.0.0.201 closed.
spawn ssh [email protected]
The authenticity of host '10.0.0.216 (10.0.0.216)' can't be established.
ECDSA key fingerprint is SHA256:mZPxf2BlCHWGFGOySe3SIqZz4cKNlqJZyBsl63kbGEg.
Are you sure you want to continue connecting (yes/no/[fingerprint])? yes
Warning: Permanently added '10.0.0.216' (ECDSA) to the list of known hosts.
[email protected]'s password: 
Last login: Tue Mar 14 15:01:17 2023 from 10.0.0.1
[root@centos7 ~]# useradd test
[root@centos7 ~]# exit
logout
Connection to 10.0.0.216 closed.
spawn ssh [email protected]
The authenticity of host '10.0.0.217 (10.0.0.217)' can't be established.
ECDSA key fingerprint is SHA256:o4LXS6D+DywH8JOjcem8/f4wcRXkOMQ7TCUipw+9aeM.
Are you sure you want to continue connecting (yes/no/[fingerprint])? yes
Warning: Permanently added '10.0.0.217' (ECDSA) to the list of known hosts.
[email protected]'s password: 
Last login: Tue Mar 14 15:01:28 2023 from 10.0.0.1
[root@rocky8 ~]# useradd test
[root@rocky8 ~]# exit
logout
Connection to 10.0.0.217 closed.
[root@rocky8 scripts]# 

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

shell脚本数组

declare 声明和查看数组变量, unset:删除数组
Linux3月7日-shell脚本进阶函数_第16张图片
Linux3月7日-shell脚本进阶函数_第17张图片
Linux3月7日-shell脚本进阶函数_第18张图片
范例:生产10个随机数保存于数组中,并找出其最大只和最小值

#!/bin/bash
declare -i min max
declare -a nums
for ((i=0;i<10;i++));do
        nums[$i]=$RANDOM
        [ $i -eq 0 ] && min=${nums[0]} && max=${nums[0]} && continue
        [ ${nums[$i]} -gt $max ] && max=${nums[$i]} && continue
        [ ${nums[$i]} -lt $min ] && min=${nums[$i]}
done
echo "All number are ${nums[*]}"
echo "Max is $max"
echo "Min is $min"

Linux3月7日-shell脚本进阶函数_第19张图片

你可能感兴趣的:(马哥Sre探险之旅,bash,linux,开发语言)