Linux系统shell脚本编程笔记——处理信号、作业控制等

目录

1.处理信号

1.1  重温Linux信号

1.2  生成信号

 1.3  捕获信号

1.4  捕获脚本退出

1.5  修改或移除捕获

2、 以后台模式运行脚本

3 、在非控制台下运行脚本

4、作业控制

4.1、查看作业

4.2、重启停止的作业

5、调整谦让度

5.1、 nice命令

5.2、 renice命令

6、定时运行作业

6.1、用at命令来计划执行作业

6.1.1、at命令的格式

6.1.2、获取作业的输出

6.1.3、列出等待的作业

6.1.4、删除作业

6.2、安排需要定期执行的脚本

6.2.1、cron时间表

6.2.2、构建cron时间表

6.2.3、浏览cron目录

6.2.4、anacron程序

6.3、使用新shell启动脚本


 完整笔记请前往此处获取:https://download.csdn.net/download/qq_55908180/88366003

除了可以以实时模式在命令行界面直接运行脚本之外,还有一些选项可以用来控制脚本,这种方法包括向脚本发送信号、修改脚本优先级以及在脚本运行时切换到运行模式。

1.处理信号

1.1  重温Linux信号

信号

描述

1

SIGHUP

挂起进程

2

SIGINT

终止进程

3

SIGQUIT

停止进程

9

SIGKILL

无条件终止进程

15

SIGTERM

尽可能终止进程

17

SIGSTOP

无条件停止进程,但不是终止进程

18

SIGTSTP

停止或暂停进程,但不终止进程

19

SIGCONT

继续运行停止的进程

1.2  生成信号

Shell允许通过键盘上的组合键生成两种基本信号。

1 中断进程

 Ctrl+C组合键会生成SIGINT信号,并把它发送给当前在shell脚本中运行的所有进程;

2 暂停进程

Ctrl+Z组合键会生成一个暂停信号(SIGTSTP),停止shell中运行的任何进程。注意,停止不是终止进程,停止进程会让程序继续保留在内存中,并且可以从上次停止的位置继续运行。

可以使用ps命令查看已停止的作业。

 如果有已经停止的作业存在,但是你仍要退出shell,只要再输入一遍exit命令就可以了,shell会退出并终止该作业。若你已知已停作业的PID,也可以使用kill命令来发送一个SIGKILL信号。如:

 1.3  捕获信号

也可以在信号出现时捕获并执行其他命令,trap命令允许指定shell脚本要监督并从shell中拦截Linux信号,只要脚本收到trap命令中列出的信号,则该信号就不再由shell处理,而是交给本地处理。trap命令的格式是:trap commands  signals如:

#!/bin/bash

trap "echo ' Sorry! I have trapped Ctrl-C'" SIGINT
echo This is a test script
count=1
while [ $count -le 10 ]
do 
		echo "Loop #$count"
		sleep 1
		count=$[ count + 1 ]
done
echo "This is the end of the script"

1.4  捕获脚本退出

在trap命令后面加上EXIT信号,就可以在脚本退出时进行捕获。如:

#!/bin/bash

trap "echo Goodbye..." EXIT
count=1
while [ $count -le 5 ]
do
		echo "Loop #$count"
		sleep 1
		count=$[ count + 1 ]
done

1.5  修改或移除捕获

想要在脚本的不同位置进行不同的捕获处理,只要重新使用带有新的选项的trap命令。如:

#!/bin/bash

trap "echo ' Sorry... Ctrl-C is trapped.'" SIGINT
count=1
while [ $count -le 5 ]
do
		echo "Loop #$count"
		sleep 1
		count=$[ $count + 1 ]
done
trap "echo ' I modified the trap!'" SIGINT
count=1
while [ $count -le 5 ]
do
		echo "Second Loop #$count"
		sleep 1
		count=$[ $count + 1 ]
done

在修改了捕获信号之后,脚本处理信号的方式发生了变化,但是如果一个信号是在捕获被修改前收到的,脚本就会根据最初的trap命令进行处理。

也可以删除已经设置好的捕获,只要在trap命令与希望恢复默认行为的信号列表之间加上两个破折号就行了。如:

#!/bin/bash

trap "echo ' Sorry... Ctrl-C is trapped.'" SIGINT
count=1
while [ $count -le 5 ]
do
		echo "Loop #$count"
		sleep 1
		count=$[ $count + 1 ]
done

#Remove the trap
trap -- SIGINT
echo "I just removed the trap"
count=1
while [ $count -le 5 ]
do
		echo "Second Loop #$count"
		sleep 1
		count=$[ $count + 1 ]
done

2、 以后台模式运行脚本

想要以后台模式运行脚本,只要在命令后面加一个&符就可以实现。如:

#!/bin/bash

count=1
while [ $count -le 10 ]
do
sleep 1
count=$[ $count + 1 ]
done

当&符放到命令后时,它会将命令和bash shell分离开来,把命令作为一个独立的后台进程运行。方括号的数字是分配的后台进程作业号,后面的数字是Linux系统分配的进程ID(PID)。记住:每一个进程都必须有一个唯一的PID。

在后台进程运行时,它仍会在终端显示STDOUT和STDERR消息。如:

#!/bin/bash

echo "Start the test script"
count=1
while [ $count -le 5 ]
do 
		echo "Loop #$count"
		sleep 5
		count=$[ $count + 1 ]
done
echo "Test script is complete"

 为了避免脚本输出以及输入的命令和命令输出混在一起,最好把后台运行的脚本的STDOUT和STDERR进行重定向,避免这种杂乱的输出。

3 、在非控制台下运行脚本

可以使用nohup命令实现在终端会话中启动shell脚本,然后让脚本一直以后台模式运行到结束。nohup命令运行另外一个命令来阻断所有发送给该进程的SIGHUP信号,这会在退出终端会话时阻止进程退出。命令格式如下:

nohup ./test3 &

为了保存该命令产生的输出,nohup命令会自动将sTDouT和sTDERR的消息重定向到一个名为nohup.out的文件中。直接看例子:

4、作业控制

启动、停止、终止以及恢复作业的这些功能统称为作业控制

4.1、查看作业

jobs命令是作业控制中的关键命令,jobs命令允许查看shell当前正在处理的作业。如:

脚本用$$变量来显示Linux系统分配给该脚本的PID。

使用jobs命令可以查看分配给shell的作业。jobs命令会显示这两个已停止/运行中的作业,以及它们的作业号和作业中使用的命令。如:

jobs命令的一些命令行参数如下:

参数

描述

-l

列出进程的PID以及作业号

-n

只列出上次shell发出通知后改变了状态的作业

-p

只列出作业的PID

-r

只列出运行中的作业

-s

只列出已停止的作业

4.2、重启停止的作业

在bash作业控制中,可以将已停止的作业作为后台进程或前台进程重启。前台进程会接管你当前工作的终端,所以在使用该功能时要小心了。

要以后台模式重启一个作业,可用bg命令加上作业号。如:

 要以前台模式重启作业,可用带有作业号的fg命令。

5、调整谦让度

调度优先级( scheduling priority)是内核分配给进程的CPU时间。在Linux系统中,由shell启动的所有进程的调度优先级默认都是相同的。

调度优先级是个整数值,从-20(最高优先级)到+19(最低优先级)。默认情况下,bash shell以优先级0来启动所有进程。

5.1、 nice命令

nice命令允许你设置命令启动时的调度优先级。要让命令以更低的优先级运行,只要用nice的-n命令行来指定新的优先级级别。如:

 注意:nice命令的-n选项并不是必须的,只需要在破折号后面跟上优先级就行了。

5.2、 renice命令

renice命令可以做到改变系统上已运行命令的优先级,它允许你指定运行进程的PID来改变它的优先级。如:

renice命令有限制:

1、只能对属于你的进程执行renice;

2、只能通过renice降低进程的优先级;

3、root用户可以通过renice来任意调整进程的优先级。

6、定时运行作业

Linux系统提供了多个在预选时间运行脚本的方法:at命令cron

6.1、用at命令来计划执行作业

at命令允许指定Linux系统什么时候运行脚本。at的守护进程atd会以后台模式运行,检查作业队列来运行作业。

6.1.1、at命令的格式

at  [-f  filename]  time

默认情况下,at命令会将STDIN的输人放到队列中。可以用-f参数来指定用于读取命令(脚本文件)的文件名。

time参数指定了Linux系统何时运行该作业。如果指定的时间已经错过,at

命令会在第二天的那个时间运行指定的作业。

at命令能够识别多种时间格式:

  1. 标准的小时和分钟制,如:9:30
  2. AM/PM形式,如:9:30PM
  3. 特殊的时间名词,如:now,noon,midnight等

等等…

6.1.2、获取作业的输出

Linux系统会将提交该作业的用户的电子邮件地址作为STDOUT和STDERR。任何发到STDOUT或STDERR的输出都会通过邮件系统发送给该用户。如:

#!/bin/bash

echo "This script ran at $(date +%B%d,%T)"
echo
sleep 5
echo "This is the script's end..."

使用e-mail作为at命令的输出极其不便。at命令利用sendmail应用程序来发送邮件。如果你的系统中没有安装sendmail,那就无法获得任何输出。所以,在使用at命令时,最好在脚本中对STDOUT和STDERR进行重定向。如:

#!/bin/bash

echo "This script ran at $(date +%B%d,%T)" >> test3a.out
echo
sleep 5
echo "This is the script's end..." >> test3a.out

6.1.3、列出等待的作业

atq命令可以查看系统中有哪些作业在等待。

6.1.4、删除作业

只要知道有哪些作业在作业队列中等待,就能用atrm命令来删除等待中的作业。

6.2、安排需要定期执行的脚本

用at命令在预设时间安排脚本执行非常好用,但是对于定期执行的脚本来说就比较麻烦。

Linux系统使用cron程序来安排要定期执行的作业。cron程序会在后台运行并检查一个特殊的表(被称作cron时间表),以获知已安排执行的作业。

6.2.1、cron时间表

cron时间表采用一种特别的格式来指定作业何时运行。其格式如下:

min  hour  dayofmonth  month  dayofweek  command

cron时间允许使用特殊值、取值范围(如1~9)或者使用通配符(*)来指定条目。

1、如你想要每天的9:30运行一个命令,可以用cron时间条目:

30 9 * * * command

2、如果想每周一12:30运行的命令,可以:30 12 * * 1 command

可以使用文本值(mon、tue、wed、thu、fri、sat、sun)或者数值(0表示周日,6表示周六)来指定dayofweek

3、如果想要每月第一天上午10:00执行命令:00 10 1 * * command

Dayofmonth表项指定月份中的日期值(1~31)

注意:命令列表必须指定要运行的命令或脚本的全路径名。当然,也可以添加任何想要添加的命令行参数和重定向符号。

6.2.2、构建cron时间表

每个系统用户(包括root用户)都可以用自己的cron时间表来运行安排好的任务。Linux提供了crontab命令来处理cron时间表。要列出已有的cron时间表,可以用-l选项。如:

用户的cron时间文件默认不存在,想要添加条目,可以使用-e选项。

6.2.3、浏览cron目录

如果创建的脚本对精确的执行时间要求不高,用预配置的cron脚本目录会更方便。有4个基本目录:hourly、daily、 monthly和weekly。如:

 因此,如果脚本需要每天运行一次,只要将脚本复制到daily目录,cron就会每天执行它。

6.2.4、anacron程序

如果Linux系统处于关机状态,但是此时有作业在这个时间安排了运行,则就会错过执行时间。可以使用anacron程序,如果anacron知道某个作业错过了执行时间,它会尽快运行该作业。这意味着如果Linux系统关机了几天,当它再次开机时,原定在关机期间运行的作业会自动运行。注意:anacron程序只会处理位于cron目录的程序,

anacron时间表的基本格式如下:

period delay identifier command  

period条目定义了作业多久运行一次,以天为单位。

delay条目会指定系统启动后anacron程序需要等待多少分钟再开始运行错过的脚本

command条目包含了run-parts程序和一个cron脚本目录名。run-parts程序负责运行目录中传给它的任何脚本。

identifier条目是一种特别的非空字符串,它用于唯一标识日志消息和错误邮件中的作业。

6.3、使用新shell启动脚本

每次启动一个新shell时, bash shell都会运行.bashrc文件。可以这样来验证:在主目录下的.bashrc文件中加入一条简单的echo语句,然后启动一个新shell。

.bashrc文件通常也是通过某个bash启动文件来运行的。因为.bashrc文件会运行两次:一次是当你登入bash shell时,另一次是当你启动一个bash shell时。如果你需要一个脚本在两个时刻都得以运行,可以把这个脚本放进该文件中。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值