一、src
后台开发中,常常需要写 daemon 程序在后台默默执行一些任务。除了正常的逻辑之外,还需要考虑处理异常退出时怎么办,比如ctrl + c
、kill -9
。这时可以用到 signal 这个函数来注册异常信号的回调函数。
二、思路
1. 创建1个Signal对象,这个对象代表对1个linux命令的监听
2. 创建1个Handler对象,表示监听到xx命令时需要执行的行为。注意因为覆盖了原有的行为,所以也要把原有的行为加上,比如中断程序执行。
3. 将Signal对象和Handler对象关联、注册为回调
package com.cib.dqms.utils
import org.apache.hadoop.fs.{FileSystem, Path}
import sun.misc.{Signal, SignalHandler}
/**
* 监听ctrl + c和kill -9,退出时将临时文件删除。
*/
object LinuxSys {
def shutdown(fs:FileSystem,tempDir:String): Unit ={
val customHandler = new CustomHandler(fs,tempDir)
val intSignal = new Signal("INT") //ctrl + c
Signal.handle(intSignal,customHandler)
val termSignal = new Signal("TERM") //kill -9
Signal.handle(termSignal,customHandler)
}
private class CustomHandler(fs:FileSystem,tempDir:String) extends SignalHandler{
override def handle(signal: Signal): Unit = {
fs.delete(new Path(tempDir),true)
System.exit(-1)
}
}
}
三、Signal,监听命令的种类
理解
信号就是进程之间的通信语言,
kill -l 显示
kill -l
1) SIGHUP 2) SIGINT 3) SIGQUIT 4) SIGILL 5) SIGTRAP
6) SIGABRT 7) SIGBUS 8) SIGFPE 9) SIGKILL 10) SIGUSR1
11) SIGSEGV 12) SIGUSR2 13) SIGPIPE 14) SIGALRM 15) SIGTERM
16) SIGSTKFLT 17) SIGCHLD 18) SIGCONT 19) SIGSTOP 20) SIGTSTP
21) SIGTTIN 22) SIGTTOU 23) SIGURG 24) SIGXCPU 25) SIGXFSZ
26) SIGVTALRM 27) SIGPROF 28) SIGWINCH 29) SIGIO 30) SIGPWR
31) SIGSYS 34) SIGRTMIN 35) SIGRTMIN+1 36) SIGRTMIN+2 37) SIGRTMIN+3
38) SIGRTMIN+4 39) SIGRTMIN+5 40) SIGRTMIN+6 41) SIGRTMIN+7 42) SIGRTMIN+8
43) SIGRTMIN+9 44) SIGRTMIN+10 45) SIGRTMIN+11 46) SIGRTMIN+12 47) SIGRTMIN+13
48) SIGRTMIN+14 49) SIGRTMIN+15 50) SIGRTMAX-14 51) SIGRTMAX-13 52) SIGRTMAX-12
53) SIGRTMAX-11 54) SIGRTMAX-10 55) SIGRTMAX-9 56) SIGRTMAX-8 57) SIGRTMAX-7
58) SIGRTMAX-6 59) SIGRTMAX-5 60) SIGRTMAX-4 61) SIGRTMAX-3 62) SIGRTMAX-2
63) SIGRTMAX-1 64) SIGRTMAX
常用的就是SIGINT和SIGTERM
信号 | desc |
---|---|
SIGINT | 程序终止(interrupt)信号, 在用户键入INTR字符(通常是Ctrl-C)时发出,用于通知前台进程组终止进程 |
SIGTERM | 程序结束(terminate)信号, 与SIGKILL不同的是该信号可以被阻塞和处理。通常用来要求程序自己正常退出,SIGTERMshell命令kill缺省产生这个信号。如果进程终止不了,我们才会尝试SIGKILL。 |