Shell 實作守護進程方法
查詢 init.d 守護進程
記錄網路上找的不錯寫法 以下參考springboot 打包(jar)部署在 Linux 環境 - SegmentFault 思否 這個應該也能改成一般程式執行
注意!!這邊不是無限loop 估記是Java 程式做 loop
start.sh 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 #!/bin/bash AppName=ruoyi.jar JVM_OPTS="-Dname=$AppName -Duser.timezone=Asia/Shanghai -Xms512M -Xmx512M -XX:PermSize=256M -XX:MaxPermSize=512M -XX:+HeapDumpOnOutOfMemoryError -XX:+PrintGCDateStamps -XX:+PrintGCDetails -XX:NewRatio=1 -XX:SurvivorRatio=30 -XX:+UseParallelGC -XX:+UseParallelOldGC" APP_HOME=`pwd ` LOG_PATH=$APP_HOME /logs/$AppName .log if [ "$1 " = "" ];then echo -e "\033[0;31m 未輸入操作名 \033[0m \033[0;34m {start|stop|restart|status} \033[0m" exit 1 fi if [ "$AppName " = "" ];then echo -e "\033[0;31m 未輸入應用名 \033[0m" exit 1 fi function start(){ PID=`ps -ef |grep java|grep $AppName |grep -v grep|awk '{print $2}' ` if [ x"$PID " != x"" ]; then echo "$AppName is running..." else nohup java -jar $JVM_OPTS target/$AppName > /dev/null 2>&1 & echo "Start $AppName success..." fi } function stop(){ echo "Stop $AppName " PID="" query (){ PID=`ps -ef |grep java|grep $AppName |grep -v grep|awk '{print $2}' ` } query if [ x"$PID " != x"" ]; then kill -TERM $PID echo "$AppName (pid:$PID ) exiting..." while [ x"$PID " != x"" ] do sleep 1 query done echo "$AppName exited." else echo "$AppName already stopped." fi } function restart(){ stop sleep 2 start } function status(){ PID=`ps -ef |grep java|grep $AppName |grep -v grep|wc -l` if [ $PID != 0 ];then echo "$AppName is running..." else echo "$AppName is not running..." fi } case $1 in start) start;; stop) stop;; restart) restart;; status) status;; *) esac
另外一種 看試強制關閉start_init.sh 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 #!/bin/sh JAR_NAME=ruoyi.jar tpid=`ps -ef|grep $JAR_NAME |grep -v grep|grep -v kill |awk '{print $2}' ` if [ ${tpid} ]; then echo 'Stop Process...' fi sleep 5 tpid=`ps -ef|grep $JAR_NAME |grep -v grep|grep -v kill |awk '{print $2}' ` if [ ${tpid} ]; then echo 'Kill Process!' kill -9 $tpid else echo 'Stop Success!' fi tpid=`ps -ef|grep $JAR_NAME |grep -v grep|grep -v kill |awk '{print $2}' ` if [ ${tpid} ]; then echo 'App is running.' else echo 'App is NOT running.' fi rm -f tpid nohup java -jar ./$JAR_NAME >/dev/null 2>&1 & echo $! > tpidecho 'Start Success!'
這個應該可以改成一般非 Java 程式排程 再搭配關閉訊號控制程式,是不是就是完美關閉腳本 好吧,其實我還是覺得 Systemd 才是最佳解決方案
關閉訊號控制程式 最近有看到可以傳送關閉訊號控制程式跑完進程關閉程式
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 #!/bin/bash mp3convert () { echo "mp3convert..." ; sleep 5; echo "mp3convert done..." } PreTrap () { echo "in trap" QUIT=1 echo "exiting trap..." } CleanUp () { while kill -0 $PID >& /dev/null; do wait $PID ; echo "check again" ; done if [ ! -z $QUIT ]; then echo "clean up..." exit fi } trap PreTrap SIGINT SIGTERM SIGTSTPfor loop in 1 2 3; do ( echo "loop #$loop " mp3convert echo magic 1 echo magic 2 echo magic 3 ) & PID=$! CleanUp echo "done loop #$loop " done
測試結果,還真的有用 開兩個 cmd ,一個執行,另一個kill 並不會直接結束
參考:shell - bash trap interrupt command but should exit on end of loop - Stack Overflow
trap 相關指令,可以用來可以控制關閉方法
調整完美關閉腳本 TODO: 待修改
彩蛋
執行 Docker 容器可使用 dumb-init 或 tini 改善程序優雅結束的問題 | The Will Will Web