sh脚本笔记2

test条件测试

语法

条件测试语法 说明
语法1:test <测试表达式> 这是利用test命令进行条件测试表达式的方法。test命令和"<测试表达式>"之间至少有一个空格
语法2:[ <测试表达式> ] 这是通过[](单中括号)进行条件测试表达式的方法,和test命令的用法相同,这是老男孩推荐的方法。[]的边界和内容之间至少有一个空格
语法3:[[ <测试表达式> ]] 这是通过[[]](双中括号)进行条件测试表达式的方法,是比test和[]更新的语法格式。[[]]的边界和内容之间至少有一个空格。(支持正则处理)
语法4:((<测试表达式>)) 这是通过(())(双小括号)进行条件测试表达式的方法,一般用于if语句里。(())(双小括号)两端不需要有空格

参数

sh 复制代码
1. 关于某个文件名的类型侦测(存在与否),如:test -e filename
-e 该【文件名】是否存在?(常用)(不区分目录和文件)
-f 该【文件名】是否为文件(file)?(常用)
-d 该【文件名】是否为目录(directory)?(常用)
-b 该【文件名】是否为一个block device装置?
-c 该【文件名】是否为一个character device装置?
-S 该【文件名】是否为一个Socket文件?
-p 该【文件名】是否为一个FIFO(pipe)文件?
-L 该【文件名】是否为一个连结档?

2.关于文件的权限侦测,如:test -r filename
-r 侦测该文件名是否具有【可读】的属性?
-w 侦测该文件名是否具有【可写】的属性?
-x 侦测该文件名是否具有【可执行】的属性?
-u 侦测该文件名是否具有【SUID】的属性?
-g 侦测该文件名是否具有【SGID】的属性?
-k 侦测该文件名是否具有【Sticky bit】的属性?
-s 侦测该文件名是否具有【非空白文件】?

3.两个文件之间的比较,如:test file1 -nt file2
-nt (newer than)判断file1是否比file2新
-ot (older than)判断file1是否比file2旧
-ef 判断file1与file2是否为同一文件,可用在判断hand link的判定上。主要意义在判定,两个文件是否均指向同一个inode哩!

4.关于两个整数之间的判定,例如:test n1 -eq n2
-eq 两数值相等(equal)
-ne 两数值不等(not equal)
-gt n1大于n2(greater than)
-lt n1小于n2(less than)
-ge n1大于等于n2(greater than or equal)
-le n1小于等于n2(less than or equal)

5.判定字符串的数据
test -z string 判定字符串是否为0?若string为空字符串,则为true
test -n string 判定字符串是否非为0?若string为空字符串,则为false
注:-n 亦可省略
test str1 = str2 判定str1是否等于str2,若相等,则回传true
test str1 != str2 判定str1是否不等于str2,若相等,则回传false

6.多重条件判定,例如:test -r filename -a -x filename
-a (and)两状况同时成立!例如:test -r file -a -x file,则file同时具有r与x权限时,才回传true
-o (or)两状况任何一个成立!例如:test -r file -o -x file,则file具有r或x权限时,就可回传true
! 反相状态,如test ! -x file,当file不具有x时,回传true

注意:
在条件测试中使用变量,必须添加双引号

字符串比较

常用字符串测试操作符 说明
-n "字符串" 若字符串的长度不为0,则为真,即测试表达式成立,n可以理解为no zero
-z "字符串" 若字符串的长度为0,则为真,即测试表达式成立,z可以理解为zero的缩写
"串1" = "串2" 若字符串1等于字符串2,则为真,即测试表达式成立,可使用"=="代替"=",=号两边有空格
"串1" != "串2" 若字符串1不等于字符串2,则为真,即测试表达式成立,但不能用"!=="代替"!=" ,!=号两边有空格

注意:
对于字符串变量的比较,一定要记住给变量添加双引号。使用等于号的值判断,左右两边也必须有空格

数值比较

在[]以及test中使用的比较符号(使用右边的需要转义) 在(())和[[]]中使用的比较符号(左边的也可以用) 说明
-eq ==或= 相等,全拼为equal
-ne != 不相等,全拼为not equal
-gt > 大于,全拼为greater than
-ge >= 大于等于,全拼为greater equal
-lt < 小于,全拼为less then
-le <= 小于等于,全拼为less equal

逻辑操作符

在[]以及test中使用的操作符(右边不能使用) 在(())和[[]]中使用的操作符 说明
-a && and,与,两端都为真,则结果为真
-o || or,或,两端有一个为真,则结果为真
! ! not,非,两端相反,则结果为真

测试表达式符号总结

测试表达式符号 [] test [[]] (())
边界为是否需要空格 需要 需要 需要 不需要
逻辑操作符 ! -a -o ! -a -o ! && || ! && ||
整数比较操作符 -eq -ne -gt -lt -ge -le -eq -ne -gt -lt -ge -le -eq -ne -gt -lt -ge -le或= != > >= < <= = != > >= < <=
字符串比较操作符 = == != = == != = == != = == !=
是否支持通配符匹配 不支持 不支持 支持 不支持

注意:
最常用的就是,中括号,搭配-gt -lt如此用法即可

if

单if

sh 复制代码
if <条件表达式>
then
    代码。。。
fi

sh 复制代码
if <条件表达式>;then
    代码。。。
fi

if-else

sh 复制代码
if <条件表达式>
then
    代码。。。
else
    代码。。。
fi

sh 复制代码
if <条件表达式>;then
    代码。。。
else
    代码。。。
fi

if-elseif

sh 复制代码
if <条件表达式>
then
    代码。。。
elif <条件表达式>
then
    代码。。。
else
    代码。。。
fi

sh 复制代码
if <条件表达式>;then
    代码。。。
elif <条件表达式>;then
    代码。。。
else
    代码。。。
fi

开发MySQL监控脚本

端口监控 1)在服务器本地监控服务端口的常见命令有netstat、ss、lsof 2)从远端监控服务器本地端口的命令有telnet、nmap、nc
监控服务进程或进程数 此方法适合本地服务器,注意,过滤的是进程的名字。命令为: ps -ef | grep nginx | wc -l ps -ef | grep mysql | wc -l
在客户端模拟用户访问 使用wget或curl命令进行测试(如果检测数据库,则需要转为通过Web服务器去访问数据库),并对测试结果做三种判断: 1)利用返回值(echo $?)进行判断 2)获取特殊字符串以进行判断(需要事先开发好程序) 3)根据HTTP响应header的情况进行判断
登录MySQL数据库判断 通过MySQL客户端连接数据库,根据返回值或返回内容判断。例如: mysql -uroot -poldboy123 -e "select version();" &>/dev/null;echo $?

shell函数

函数定义

sh 复制代码
# 标准函数定义
function 函数名(){
	函数体
	# return可写可不写
	return 返回值
}
# 偷懒写法
# 当使用function关键字时,可以省略括号
function 函数名{
	函数体
	# return可写可不写
	return 返回值
}
# 超级懒人写法
# 必须有括号
函数名(){
	函数体
	# return可写可不写
	return 返回值
}

函数执行

有关函数执行的基础概念

  • 执行shell函数,直接写函数名字即可,无需添加其他内容
  • 函数体内定义的变量,称之为局部变量
  • 函数体内需要添加return语句,作用是退出函数,且赋予返回值给调用该函数的程序,也就是shell脚本
  • return语句和exit不同
    • return是结束函数的执行,返回一个(退出值、返回值)
    • exit是结束shell环境,返回一个(退出值、返回值)给当前的shell
  • 函数如果单独写入一个文件里,需要用source读取(调用函数的脚本如果用source执行,该函数会添加在环境变量里。如果用bash执行,会在子shell中执行,在当前shell中该函数就不会添加在环境变量里)
  • 函数内,使用local关键字,定义局部变量
  • 函数名字后面都不需要带括号
  • 和其它编程语言不同的是,Shell 函数在定义时不能指明参数,但是在调用时却可以传递参数,并且给它传递什么参数它就接收什么参数。
  • Shell 也不限制定义和调用的顺序,你可以将定义放在调用的前面,也可以反过来,将定义放在调用的后面。

函数参数

函数体内可以使用参数变量,获取函数参数。函数的参数变量,与脚本参数变量是一致的。

  • $1~$9:函数的第1个到第9个的参数。
  • $0:函数所在的脚本名,以及脚本路径。
  • $#:函数的参数总数。
  • $@:函数的全部参数,参数之间使用空格分隔。
  • \*:函数的全部参数,参数之间使用变量IFS值的第一个字符分隔,默认为空格,但是可以自定义。

如果函数的参数多于9个,那么第10个参数可以用${10}的形式引用,以此类推。

相关推荐
1900439 分钟前
linux6:常见命令介绍
linux·运维·服务器
Camellia-Echo16 分钟前
【Linux从青铜到王者】Linux进程间通信(一)——待完善
linux·运维·服务器
Linux运维日记27 分钟前
k8s1.31版本最新版本集群使用容器镜像仓库Harbor
linux·docker·云原生·容器·kubernetes
我是唐青枫36 分钟前
Linux dnf 包管理工具使用教程
linux·运维·服务器
编程修仙2 小时前
Collections工具类
linux·windows·python
芝麻团坚果2 小时前
对subprocess启动的子进程使用VSCode python debugger
linux·ide·python·subprocess·vscode debugger
写点什么啦2 小时前
[debug]不同的window连接ubuntu的vscode后无法正常加载kernel
linux·vscode·ubuntu·debug
wellnw2 小时前
[ubuntu]编译共享内存读取出现read.c:(.text+0x1a): undefined reference to `shm_open‘问题解决方案
linux·ubuntu
不爱学习的YY酱2 小时前
【操作系统不挂科】<CPU调度(13)>选择题(带答案与解析)
java·linux·前端·算法·操作系统
DC_BLOG2 小时前
Linux-Nginx虚拟主机
linux·运维·nginx