shell 脚本
作者:互联网
shell 脚本
介绍
shell 是一个命令行解释器,它接收应用程序/用户命令,然后调用操作系统内核。shell 还是一个功能强大的编程语言,易编写、易调试、灵活性强。
第一行的作用
#!/bin/bash
Shebang 在计算机程序中,shebang 指的是出现在文本文件的第一行前两个字符 #!
-
以 #!/bin/sh 开头的文件,程序在执行的时候会调用 /bin/sh,也就是 bash 解释器
-
以 #!/usr/bin/python 开头的文件,代表指定 Python 解释器去执行
-
以 #!/usr/bin/env 解释器名称,是一种在不同平台上都能正确找到解释器的办法。
注意事项
-
如果脚本未指定 shebang ,脚本执行的时候,默认用当前 shell 去解释脚本,即 $SHELL
-
如果 shebang 指定了可执行解释器,比如 /bin/bash /user/bin/python ,脚本在执行时,文件名会作为参数传递给解释器
-
如果 #!指定的解释查询没有执行权限,则会报错
-
如果 #!指定的解释程序不是一个可执行文件,那么指定的解释程序会被被忽略,转交个当前的 SHELL 去执行这个脚本
-
如果你使用 bash text.sh 这样的命令去执行脚本,那么 #!这一行就会被忽略掉,解释器当然是用命令行中显示指定的 bash
脚本注释
可以让别人快速的读懂你写的脚本,还有利于自己后期去更改基本。使用英文注释,也可以用中文但是有可能会报错。
shell执行方法
-
bash script.sh 或 sh scripte.sh,文件本身没有执行权限,则使用的方法,或者脚本未指定 sheban
-
使用 绝对/相对 路径来来执行脚本
-
source script.sh 或者 ./script.sh,代表执行含义,source 等于 .
-
sh < script.sh 很少人用的一种方法
shell和运维
shell主要是来处理系统文本类型数据的,比如日志配置文件。shell 属于弱类型的脚本语言,无需声名变量类型,直接定义使用。
history 历史记录
history //查看历史记录 history -c //清除历史记录 history -r //恢复历史记录
!+ 历史记录ID 快速使用历史命令
!! 使用是一次命令
echo命令
-n 不换行输出 -e 解释字符串中的特殊符号 \n 换行 \r 回车 \b 退格 \t 制表符(四个空格) #eval 执行多个命令 eval ls;cd /temp
变量
pstree 检查进程树
变量定义与赋值,注意变量与值之间不得有空格
[root@shell ~]# name="花花" [root@shell ~]# echo $name 花花 bash变量为弱类型,无需事先声明类型,是将声明和复制同时进行的
变量替换/引用
[root@shell ~]# music="花花" [root@shell ~]# echo ${music} 花花 [root@shell ~]# echo $music 花花 [root@shell ~]# echo name name
变量名规则
-
名称定义要做到简明知意,切按照规则来,切别的应用保留关键字
-
只能包含数字、字母、下划线
-
不能以数字开头
-
不能用标点符号
-
变量名严格区分大小写
#有效字符 [root@shell ~]# age=15 [root@shell ~]# name = "花花" [root@shell ~]# _da=daf [root@shell ~]# echo $_da daf #无效字符 [root@shell ~]# 2age=15 -bash: 2age=15: 未找到命令 [root@shell ~]# .age=55 -bash: .age=55: 未找到命令
变量作用域
父子关系:也就是说在父亲里的变量只能搜索到父亲的变量,搜索不到儿子的。相反儿子的也是。
[root@shell ttt]# cat make_var.sh age='18' [root@shell ttt]# age='20' [root@shell ttt]# echo $age 20 [root@shell ttt]# bash make_var.sh [root@shell ttt]# echo $age 20 [root@shell ttt]# source make_var.sh [root@shell ttt]# echo $age 18
环境变量
环境变量也成为全局变量,针对当前 shell 以及其进程任意子进程,环境变量也分自定义变量、内置变量两种
局部变量
针对在 shell 中的函数或是 shell 脚本中定义
位置参数变量
用于 shell 脚本中传递的参数
特殊变量
shell 内置的特殊功效变量
-
$?
-
0: 成功
-
1-255:报错
-
自定义变量
-
变量赋值:varName=value
-
变量引用:${varName}、$varName
单引号双引号
单引号变量,不识别特殊语法 双引号变量,能识别特殊符号
[root@shell ~]# name="小明" [root@shell ~]# echo ${name} 小明 [root@shell ~]# name2='${name}' [root@shell ~]#
变量特殊
shell 的变量,用在如脚本,函数传递参数使用
$0 获取 shell 脚本文件名,以及脚本路径 $n 获取 shell 脚本的第 n 个参数,n 在1~9之间 $# 获取执行的 shell 脚本后面的参数总个数 $* 获取 shell 脚本所有参数,不加引号等同于$@作用。加上引号"$*"作用是,接受所有参数为单位字符串。"$1 $2..." $@ 不加引号,效果同上,加引号接收到所有参数为独立字符串,如"$1" "$2" "$3"。如果用于for循环的话 $@ 收到的参数就会一个一个竖向的列出来
实例:
1 [root@shell ttt]# cat make_var.sh 2 echo '特殊变量 $0' 3 echo '结果' $0 4 echo '-------------------' 5 echo '特殊变量 $n' 6 echo '结果' $1 $2 $3 7 echo '-------------------' 8 echo '特殊变量 $#' 9 echo '结果' $# 10 echo '-------------------' 11 echo '特殊变量 $*' 12 echo '结果' $* 13 echo '-------------------' 14 echo '特殊变量 $@' 15 echo '结果' $@ 16 echo '-------------------' 17 [root@shell ttt]# bash make_var.sh gm 111 222 333 444 mmm //make_var.sh 后面跟着的都是参数 18 特殊变量 $0 19 结果 make_var.sh 20 ------------------- 21 特殊变量 $n 22 结果 gm 111 222 23 ------------------- 24 特殊变量 $# 25 结果 6 26 ------------------- 27 特殊变量 $* 28 结果 gm 111 222 333 444 mmm 29 ------------------- 30 特殊变量 $@ 31 结果 gm 111 222 333 444 mmm 32 -------------------View Code
特殊状态变量
$? 上一次命令执行状态返回值,0为正确,非0为失败 $$ 当前 shell 脚本的进程号 $! 上一次后台进程号 $_ 再次之前执行的命令,最后一个参数
修改变量设置
环境变量,能找出你的 linux 服务器上的各种变量
-
每个用户都有自己的环境变量配置文件,~/.bash_profile ~/.bashrc,且以个人配置文件,优先加在变量,读取,以个人的优先生效
-
当你需要给所有用户都使用某个变量,写入全局即可 /etc/profile
检查系统环境变量命令
-
set:输出所有变量,包括全局变量、局部变量
-
env:只显示全局变量
-
declare:输出所有的变量,如同set
-
export:显示和设置环境变量值
[root@shell ~]# set BASH=/usr/bin/bash .... [root@shell ~]# set |wc -l //显示的行数 55 [root@shell ~]# env XDG_SESSION_ID=13 .... [root@shell ~]# env | wc -l 21
设置只读变量
readonly,只有 shell 结束,只读变量实效
[root@shell ~]# readonly password="123" [root@shell ~]# echo $password 123 [root@shell ~]# password="123456" bash: password: 只读变量
系统保留环境变量关键字
bash 内嵌了诸多环境变量,用于定义 bash 的工作环境
# 去除空格冒号等于号 第三列的值 [root@shell ~]# export |awk -F '[ :=]' '{print $3}' HISTCONTROL ......
bash 命令执行
开启一个子进程单独来执行脚本
[root@shell etc]# ls /opt/ ; ls /proc/ ; cd /etc/ [root@shell etc]# bash SEHELL.sh
字符串截取
# 从开头删除匹配最短 ## 从开头删除匹配最长 % 从结尾删除匹配最短 %% 从结尾删除匹配最长 //指定字符内容截取 a*c 匹配开头为a,中间任意个字符,结尾为c的字符串 //语法 name="huahua" #该变量的值,有所索引,分别是从 0,1,2,3,4开始 $(变量) 返回变量值 $(#name) 返回变量长度,字符长度 $(变量:start) 返回变量start数值之后的字符,且包含start的数字 $(变量:start:start) 提取start之后的length限制的字符,例如:${name:4:1} $(变量#word) 从变量开头删最短word字符串,例如:${name:hua} $(变量##word) 从变量开头删最长word字符串 $(变量%word) 从变量结尾删除最短word $(变量%%word) 从变量结尾删除最长匹配word 替换 ${变量/patter/string} 用string代替第一个匹配的pattern ${变量//patter/string} 用string替代所有pattern
shell 运算符
运算命令
特殊符号运算
++ 加一 -- 减一 ++a 先计算+1,然后再赋值给a a++ 先对变量a操作,在进行+1 实例 [root@shell ttt]# a=4 [root@shell ttt]# echo $((++a)) 5 [root@shell ttt]# echo $((a++)) 5 [root@shell ttt]# echo $a 6
函数
函数作用,就是把你写的功能代码,进行打包,封装成一个函数名,然后进行调用数名,函数就会执行
注意
函数定义完一定要调用、执行要不使用不了。
脚本开发
脚本开发思路:
-
想好该脚本的功能
-
先写伪代码
实例1:用户输入值来计算
开发一个,接受用户输入的数字,且对运算符号判断,最终得出一个计算脚本
-
接受用户输入
-
对用户的输入是不是数字进行判断
-
对输入的运算符号进行判断
-
最终进行结打印
[root@shell ttt]# touch calculation.sh [root@shell ttt]# chmod +x calculation.sh [root@shell ttt]# cat calculation.sh #!/bin/bash print_usage(){ print "please enter aninteger\n" exit 1 } read -p "Please input your number: " firstnum if [ -n "`echo $firstnum | sed 's/[0-9]//g'`" ] then print_usgae fi read -p "Please input your: " operator if [ "${operator}" != "+" ] && [ "${operator}" != "-" ] && [ "${operator}" != "*" ] && [ "${operator}" != "/" ] then echo "只允许输入 +|-|*|/" exit 2 fi read -p "please input number: " secondnum if [ -n "`echo $secondnum | sed 's/[0-9]//g'`" ] then print_usage fi echo "${firstnum}${operator}${secondnum}结果:$((${firstnum}${operator}${secondnum}))"
1 #!/bin/bash 2 3 #定义函数 函数名为 print_usage 。 exit 1 就是当你输入 echo $? 到时候返回的值 4 print_usage(){ 5 print "please enter aninteger\n" 6 exit 1 7 } 8 9 #接受用户输入命令,-p参数后面写,给用户看的提示信息。read -p "提示信息" 接受用户输入的变量 10 read -p "Please input your number: " firstnum 11 12 #if 判断中括里前后加空格隔开中括号,格式要求。-n 参数是 if 语句,对字符串判断,如果字符串问空,条件就不成立,如果字符串不为空,条件成立。sed 的作用就是讲用户输入的值进行解析,看是不是 0-9 的数字,是就下一步不是就成立就不执行代码。fi 是闭合 if 语句 13 if [ -n "`echo $firstnum | sed 's/[0-9]//g'`" ] 14 then 15 print_usgae 16 fi 17 18 read -p "Please input your: " operator 19 if [ "${operator}" != "+" ] && [ "${operator}" != "-" ] && [ "${operator}" != "*" ] && [ "${operator}" != "/" ] 20 then 21 echo "只允许输入 +|-|*|/" 22 exit 2 23 fi 24 25 read -p "please input number: " secondnum 26 if [ -n "`echo $secondnum | sed 's/[0-9]//g'`" ] 27 then 28 print_usage 29 fi 30 31 #echo 输出三个用户输出的参数在进行运算 32 echo "${firstnum}${operator}${secondnum}结果:$((${firstnum}${operator}${secondnum}))"脚本解释
实例2:Nginx 服务是正常运行
随便一个虚拟机打开安装一个 nginx 开启服务来测试
[root@shell ttt]# touch chare_nginx.sh [root@shell ttt]# chmod +x chare_nginx.sh [root@shell ttt]# cat chare_nginx.sh #!/bin/bash CheckUrl(){ timeout=5 fails=0 success=0 while true do wget --timeout=${timeout} --tries=1 http://192.168.100.20/ -q -O /dev/null if [ $? -ne 0 ] then let fails=fails+1 else let success+=1 fi if [ ${success} -ge 1 ] then echo "health" exit 0 fi if [ ${fails} -ge 2 ] then echo "nixng 出错" exit 2 fi done } CheckUrl [root@shell ttt]# ./chare_nginx.sh #运行成功 health [root@shell ttt]# ./chare_nginx.sh #运行失败输出 nixng 出错
1 [root@shell ttt]# cat chare_nginx.sh 2 #!/bin/bash 3 CheckUrl(){ 4 5 timeout=5 #超时时间 5 秒 6 fails=0 #失败次数。相当于定义了一个计数器 7 success=0 #成功次数。相当于定义了一个计数器 8 9 while true #while 循环 true 为真 10 do 11 #wget 来访问站点、函数timeout传给--timeout、--tries是wget的重连极致、URL、-q是不显示信息、-O是写入 /dev/null 12 wget --timeout=${timeout} --tries=1 http://192.168.100.20/ -q -O /dev/null 13 14 #if 条件判断 -ne:不等于 15 if [ $? -ne 0 ] #当 echo $? 不等于0时 16 then 17 let fails=fails+1 #不等于0失败次数+1 18 else #当 echo $? 等于0时 19 let success+=1 #等于0成功次数+1 20 21 fi 22 23 #if 判断语句 -ge:大于 24 if [ ${success} -ge 1 ] #当成功次数大于一时 25 then 26 echo "health" #就输出 health 27 exit 0 #echo $? 值 28 fi 29 30 #当错误底数大于2是告警,可以发邮箱、短信等。 31 if [ ${fails} -ge 2 ] 32 then 33 echo "nixng 出错" #报错就输出 34 exit 2 35 fi 36 done #结束 37 } 38 39 #注意,函数定义后,一定要调用,执行 40 CheckUrl脚本解释
alias 函数命令
定义 linux 别名函数
[root@shell ttt]# alias hua="cat make_var.sh" [root@shell ttt]# hua #!/bin/bash if expr "$1" ":" ".*\.jpg" &> /dev/null then echo "正确" else echo "失败" fi # 这是 linux 的所以别名 [root@shell ttt]# alias alias cp='cp -i' alias egrep='egrep --color=auto' alias fgrep='fgrep --color=auto' alias grep='grep --color=auto' alias hua='cat make_var.sh' alias l.='ls -d .* --color=auto' alias ll='ls -l --color=auto' alias ls='ls --color=auto' alias mv='mv -i' alias rm='rm -i' alias which='alias | /usr/bin/which --tty-only --read-alias --show-dot --show-tilde'
shell 函数开发脚本
函数特点,类似于 alias 别名一样,能够简化 linux 命令的操作,让整个命令更容易读,更容易用
-
函数,就是你需要执行的 shell 命令,组合起来,组成一个函数体
-
还得给这个函数体,起一个名字,这个名字就是函数名
-
函数名+函数体
-
以后你想执行这个函数,就使用这个函数名即可
1. 先定义函数 2. 调用函数 # 这就是一个一个函数体了,每次调用都会输出 “阿花代码” sayHello(){ echo "阿花代码“ }
函数定义语法
# 标准函数定义 function 函数名(){ 函数体 你想执行的 linux 命令 .... return 返回值 } # shell 老司机 函数名(){ 函数体 代码... return 返回值 }
执行函数
-
执行函数概念
-
执行 shell 函数,直接写函数名即可,无需添加其他内容
-
函数必须先定义,在执行,shell 脚本自上而下加载
-
函数体内需要添加 return 语句,作用是退出函数,且赋予返回值给调用该函数的程序,也就是 shell 脚本
-
return 语句和 exit 不同
-
return 是结束函数的执行,返回值(提出值、返回值)
-
exit 是结束 shell 环境,返回一个(提出值、返回值)给当前的 shell
-
-
函数如果单独写入一个文件里,需要用 source 读取
-
函数内,使用 local 关键字,定义局部变量
函数实战
查询用户输入的网站是否正常运行
[root@shell ttt]# vim url_test.sh usage(){ echo "Usage: $0 URL" exit 1 } check_url(){ # wget 来链接用户输入的网址、--spider 身份信息、-q -o是寂寞输出不想看到任何结果、--trues 链接一次、-T 睡眠5秒、$1 是用户输入的 URL wget --spider -q -o /dev/null --tries=1 -T 5 $1 # if 判断、$? 如果状态码等于零输出....、不等于0输出..... if [ "$?" -eq 0 ] then echo "$1 is runing..." else echo "$1 is down..." fi } #人口函数。也需要调用 main(){ # if 判断用户输入的是不是一个值,不是就返回 usage 函数 if [ "$#" -ne 1 ] then usage else check_url $1 fi } #调用 main 函数、$* 当用户进来的参数当个整体 main $* [root@shell ttt]# ./url_test.sh baidu.com baidu.com is runing...
美化输出
这是 linux 自带的
在输出前面加上 log_success_msg() 和 log_failure_msg() 就可以了
expr命令
expr命令是一个手工命令行计数器,用于在UNIX/LINUX下求表达式变量的值,一般用于整数值,也可用于字符串。
[root@shell ~]# expr --help #查看参数 [root@shell ~]# expr 4 \+ 5 #4+5=9 9
exper匹配模式
exper 命令支持没事匹配功能,且有两个特殊符号:
: 冒号,计算字符串的字符数量
.* 任意的字符串重复0次或者多次
实例:
[root@shell ~]# expr ahkl ":" ".*" 4 [root@shell ~]# expr asn.png ":" ".*\.png" 7
脚本开发
题目:测试用户提交的是否是 .jpg 文件
[root@shell ttt]# cat make_var.sh #!/bin/bash if expr "$1" ":" ".*\.jpg" &> /dev/null #如果 $1 后缀是 .jpg 传入 /dev/null 黑洞文件 then echo "正确" else echo "失败" fi [root@shell ttt]# ./make_var.sh 1.jpg 正确
数值计算
bc命令
是一个计算机命令、支持 awk 数值计算、中括号运算
1.可以直接输入 bc 进入计算机状态进行计算 2.结合管道符来进行计算 [root@shell ~]# echo "5 * 6" 5 * 6 [root@shell ~]# echo "5 * 6" | bc 30
实例:
题目1+100的总和
1 xxxxxxxxxx 方法1:[root@shell ~]# echo {1..100}1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100# tr 是替换命令[root@shell ~]# echo {1..100} | tr " " "+" | bc5050方法2:#seq命令 -s是分隔符[root@shell ~]# seq -s "+" 1001+2+3+4+5+6+7+8+9+10+11+12+13+14+15+16+17+18+19+20+21+22+23+24+25+26+27+28+29+30+31+32+33+34+35+36+37+38+39+40+41+42+43+44+45+46+47+48+49+50+51+52+53+54+55+56+57+58+59+60+61+62+63+64+65+66+67+68+69+70+71+72+73+74+75+76+77+78+79+80+81+82+83+84+85+86+87+88+89+90+91+92+93+94+95+96+97+98+99+100[root@shell ~]# seq -s "+" 100 | bc5050实例 1...100 和
awk运算
AWK 是一种处理文本文件的语言,是一个强大的文本分析工具。
[root@shell ttt]# echo "5 6" 5 6 [root@shell ttt]# echo "5 6" | awk '{print $1+$2}' 11
中括号计算
[root@shell ttt]# num=5 [root@shell ttt]# res=$[num*6] [root@shell ttt]# echo $res 30
read 命令
准输入读取数值
# -t 是时间参数,超过后面的时间就禁止输入了、-p 设置提示信息 [root@shell ttt]# read -t 15 -p "请输入你的名字:" 请输入你的名字:[root@shell ttt]# #后面跟 name 变量就是用户所输入的 [root@shell ttt]# read -t 15 -p "请输入你的名字:" name 请输入你的名字:花花 [root@shell ttt]# echo $name 花花
shell条件测试
语法:
语法:(针对文件类型判断的真假) -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-r文件名-a-x文件名 -a (and)两状况同时成立!例如test -r file -a -x file,则 file同时具有r与x权限时,才回传 true。 -o(or)两状况任何一个成立!例如test file -o -x file,则 file具有r或×权限时,就可回传true。 ! 反相状态,如test ! -x file ,当file 不具有×时,回传 true -z 是没有字符串返回真有则返回假。-n 正好相反 .....
test条件测试
test 命令评估一个表达式,它的结果是真,还是假,如果条件为真,那么命令执行状态码结果就为 0 否则就是不为 0,通过 $? 取值
test 命令参数:-a (and)两状况同时成立!例如test -r file -a -x file,则 file同时具有r与x权限时,才回传 true。 -A(和)两状况同时成立!例如测试-r文件-a-x文件,则文件同时具有r与x权限时,才回传true.
实例:
#查看是否有 1.jpg 这个文件有就返回值“有文件”,没创建一个 [root@shell ttt]# test -e 1.jpg && echo "有文件" || touch 1.jpg 有文件 #-z 是没有字符串返回真有则返回假。-n 正好相反 [root@shell ttt]# test -z "" && echo ok || echo no ok [root@shell ttt]# test -z " " && echo ok || echo no no
中括号条件测试
脚本中经常进行条件测试,用的最多的一个。中括号跟 test 作用是一样的
注意:
-
中括号,前后的空格必须有
-
条件测试里有变量的时候要带双引号
实例:
#-f 判断文件是否存在 [root@shell ttt]# [ -f test.sh ] && echo "已存在" || touch test.sh [root@shell ttt]# [ -f test.sh ] && echo "已存在" || touch test.sh 已存在
双中括号条件测试
跟中括号和 test 一样
实例:
[root@shell ttt]# [[ -f test.sh ]] && echo "已存在" || touch test.sh 已存在
字符串比较测试
实例:
[root@shell ttt]# name=123 [root@shell ttt]# age=123 [root@shell ttt]# [ "$name" = "$age" ] && echo "一样" || echo "不对" 一样
数值比较
条件参数:
[root@shell ttt]# [ 2 \< 1 ] && echo yes || echo no no [root@shell ttt]# [ 2 -lt 1 ] && echo yes || echo no no [root@shell ttt]# [[ 2 -lt 1 ]] && echo yes || echo no no [root@shell ttt]# [[ 2 < 1 ]] && echo yes || echo no no [root@shell ttt]# nt=5 [root@shell ttt]# bt=3 [root@shell ttt]# test "$nt" -lt "$bt" && echo yes || echo no no
逻辑判断符号
[root@shell ttt]# a=1.jpg [root@shell ttt]# b=test.sh [root@shell ttt]# [ -e "$a" -a "$b" ] && echo yes || echo no yes #在中括号中 && || 识别不了。双中括号可以 [root@shell ttt]# [ -e "$a" && "$b" ] && echo yes || echo no -bash: [: 缺少 `]' no
脚本开发
[root@shell ttt]# vim test.sh #!/bin/bash path=root/ttt/ [ ! -d "$path" ] && mkdir $path -p cat <<END 1.[install lamp] 2.[install lnmp] 3.[exit] END read num [[ ! "$num" =~ [1-3] ]] && { echo "The num you iput must be {1|2|3}" echo "输入有误" exit 4 } [ "$num" -eq 1 ] && { echo "Start installing ... lamp..." sleep 2; [ -x "$path/lamp.sh" ] || { echo "The file is error..." exit 1 } source $path/lamp.sh echo $? } [ "$num" -eq 2 ] && { echo "Start installing ... lnmp..." sleep 2; [ -x "$path/lnmp.sh" ] || { echo "The file is error..." exit 2 } source $path/lamp.sh echo $? } [ "$num" -eq 3 ] && { echo "ByeBye" exit 3; } [root@shell ttt]# ./test.sh 1.[install lamp] 2.[install lnmp] 3.[exit] 3 ByeBye [root@shell ttt]# ./test.sh 1.[install lamp] 2.[install lnmp] 3.[exit] qe The num you iput must be {1|2|3} 输入有误
1 #!/bin/bash 2 path=root/ttt/ //查看是否有这个目录 3 4 [ ! -d "$path" ] && mkdir $path -p //没有这个目录就创建一个 5 6 cat <<END //给用户看的提示 7 1.[install lamp] 8 2.[install lnmp] 9 3.[exit] 10 END 11 12 read num //用户输入的变量 13 14 # 然后没有按照固定输入就提示报错。 15 [[ ! "$num" =~ [1-3] ]] && { 16 echo "The num you iput must be {1|2|3}" 17 echo "输入有误" 18 exit 4 //结束shell 19 } 20 21 #当用户输入 1 时,提示用户正在安装,沉睡两秒。 22 [ "$num" -eq 1 ] && { 23 echo "Start installing ... lamp..." 24 sleep 2; 25 #查看这个 lamp.sh 安装lamp是否有权限 26 [ -x "$path/lamp.sh" ] || { 27 echo "The file is error..." 28 exit 1 29 } 30 # 执行脚本 31 source $path/lamp.sh 32 echo $? 33 } 34 35 [ "$num" -eq 2 ] && { 36 echo "Start installing ... lnmp..." 37 sleep 2; 38 [ -x "$path/lnmp.sh" ] || { 39 echo "The file is error..." 40 exit 2 41 } 42 source $path/lamp.sh 43 echo $? 44 } 45 46 [ "$num" -eq 3 ] && { 47 echo "ByeBye" 48 exit 3; 49 }脚本解释
if 语句
语法:
单分支
if <条件分支> then 执行代码... fi
双分支
if <条件分支> then 执行代码... if <条件分支> then 执行代码... fi fi
if - else
if <条件分支> then 执行代码... else 否则干嘛... fi
多分支
elif 可以写多个
if <条件分支> then 执行代码... elif then 又如果干嘛... else 否则干嘛... fi
内存检测脚本
开发 shell 脚本
1.检测 linux 剩余的可用内存,当可用内存小于 100m,就发邮件给运维
2.并且该脚本加入 crontab,每三分钟检测一次
思路 1. 获取当前内存 2. 配置邮件告警,用 linux 发送邮件(mail服务的配置),邮件内容是内存剩余情况 3. 开发脚本,判断剩余内存是否小于 100m,if判断 4. 脚本加入 crontab,写规则
#查看内存使用情况 [root@shell ttt]# free -m total used free shared buff/cache available Mem: 1819 195 1202 9 421 1462 Swap: 2047 0 2047 #提取可用内存值 [root@shell ttt]# free -m |awk 'NR==2 {print $NF}' 1462 [root@shell ttt]# cat test.sh #!/bin/bash FreeM=`free -m |awk 'NR==2 {print $NF}'` CHARS="Current memory is $FreeM" if [ "$FreeM" -lt "2000" ] // -lt 小于 then echo $CHARS|tee /ttt/FREEMEM # mail 服务需要自己配置 、-s 主题、收件人、< 内容 # mail -s "`data +%F-%T`$CHARS" huahua@qq.com < /tmp/FREEMEM echo "内存不足" fi [root@shell ttt]# ./test.sh Current memory is 1462 内存不足 [root@shell ttt]# cat FREEMEM Current memory is 1462
Mysql 监控脚本
服务器本地端口监控,mysql 的状态
#下面的代码只要不返回 0 就代表 mysql 正常运行 [root@shell ~]# netstat -tunlp | grep mysql | wc -l 1 [root@shell ~]# ss -tunlp | grep mysql |wc -l 1 [root@shell ~]# lsof -i tcp:3306 |wc -l 2
远程监控 mysql 端口
yum install -y nmap nc //需要下载 # nmap 扫描端口 [root@shell ~]# nmap 127.0.0.1 -p 3380 |grep open|wc -l //IP可以更改为服务端 1 # telnet 远程登录端口 [root@shell ~]# echo -e "\n" |telnet 127.0.0.1 3380 2>/dev/null |grep Connected |wc -l 1
进程检查
# grep -v grep 过滤掉 grep 的 [root@shell ~]# ps -ef | grep mysql |grep -v grep |wc -l 0
shell 脚本检测 mysql 状态
[root@shell ttt]# vim mysql_shell.sh #!/bin/bash if [ `netstat -tunlp |grep mysql |wc -l` = "1" ] //将里面的参数修改即可、使用 lsof 到时候要注意 then echo "Mysql suvival" else echo "Mysql drop" fi [root@shell ttt]# ./Mysql_shell.sh Mysql drop
PHP链接Mysql
1.准备好依赖 yum remove php-mysql yum install php-mysqlnd php 2.写脚本 [root@shell ttt]# vim mysql_test.php <?php # 定义链接、调用 mysql_connect 函数、出错的话就链接 mysq_error 这个函数 $mysql_id=mysql_connect("localhost","root","password") of mysql_error(); if ($mysql_id){ echo "mysql connection successful,huahua ~~~"; }else{ echo mysql_error(); } ?> [root@shell ttt]# php msyql_test.php mysql connection successful,huahua ~~~
Python 链接 mysql
1. 安装 Python 开发环境的依赖 yum install python3 python3-devel python3-pip 2. 通过 python 的包管理工具,安装 mysql 模块 pip3 install pymysql 3. 写脚本 [root@shell ttt]# vim python_mysql.py #导入模块 import pymysql #变量 db 传参 db = pymysql.connect( host="localhost" port="3306" user='root' password="password" db="msyql" charset="utf8" ) #操控数据库 cursor=db.cursor() cursor.execute('select version()') //执行语句 data=cursor.fetchone() //拿到数据 print("数据库版本是:%s"%data) db.close() //关闭数据库链接
标签:脚本,shell,变量,ttt,sh,echo,root 来源: https://www.cnblogs.com/huahuadebk/p/16080161.html