我在bash中有一个脚本来启动一个java程序,我想在执行后得到程序的pid。 pid将保存在文本文件中。
现在我有这样的事情:
if [ "$USER" == "root" ]
then
su $APP_USER -c "nohup java $JAVA_OPTS >> $LOG_OUT 2>> $LOG_ERR &"
su $APP_USER -c "echo $! > $PID_PATH/$CAT.pid"
else
nohup java $JAVA_OPTS >> $LOG_OUT 2>> $LOG_ERR &
echo $! > "$PID_PATH/$CAT.pid"
fi
我也尝试过这样但但它既不起作用。
if [ "$USER" == "root" ]
then
su $APP_USER -c "(nohup java $JAVA_OPTS >> $LOG_OUT 2>> $LOG_ERR &); (echo $! > $PID_PATH/$CAT.pid)"
else
nohup java $JAVA_OPTS >> $LOG_OUT 2>> $LOG_ERR &
echo $! > "$PID_PATH/$CAT.pid"
fi
当我运行时,我的APP_USER一切正常,当我以root身份运行时,我的java程序启动但是pid文件被创建为空。
答案 0 :(得分:4)
试
su $APP_USER -c "nohup java $JAVA_OPTS >> $LOG_OUT 2>> $LOG_ERR & echo \$! > $PID_PATH/$CAT.pid"
在传递给su命令之前,\
后面的 $!
会阻止变量的扩展。
答案 1 :(得分:1)
问题是每个su
命令都是对用户的单独调用,因此$!
不会存储您的上一个PID,因为它没有。
您需要做的是将PID保存在与第一个su
相同的调用中。最简单的方法是在两个命令周围加上引号,并用分号分隔它们
su $APP_USER -c "nohup java $JAVA_OPTS >> $LOG_OUT 2>> $LOG_ERR &; "echo $! > $PID_PATH/$CAT.pid"
现在su
将在同一环境中调用这两个命令。
答案 2 :(得分:1)
如果您的系统提供start-stop-daemon
,则可能更容易使用它而不是创建疯狂的包装器。默认情况下,您会让用户更改(--user
)和nohup行为(--background
)。此外,您可以使用--make-pidfile
做出正确的事情 - 无论您是否切换用户。