Nếu bạn có thể giết tiến trình bị ràng buộc với PIDFile (/run/foo.pid) khi /tmp/foo.path bị xóa (ví dụ: cả hai như các hành động bên trong tập lệnh tắt dịch vụ), thì có.
Tôi đã đạt được nó trên Tomcat chạy qua <= RHEL-7.7 với dịch vụ giả mạo bao gồm hành động ExecStartPost ghi lại nội dung của ứng dụng pidfile (catalina.pid) vào đường dẫn dịch vụ PIDFile. Một "PathExists" trong tệp .path tương ứng theo dõi sự xuất hiện trên catalina.pid này để nối dịch vụ systemd khi người dùng (trong trường hợp của tôi, không có đặc quyền) gọi tập lệnh khởi động. Khi người dùng khởi chạy tắt máy, pidfile của ứng dụng sẽ bị xóa, PID (cũng không có đặc quyền) chết một cách duyên dáng và systemd dừng dịch vụ do hậu quả giám sát hệ thống.
dịch vụ:
[nouser@nohost system]# cat poc.service
# . . .
[Unit]
After=network.target
After=%p.path
Wants=%p.path
# . . .
[Service]
Type=forking
Environment="%p_APPLICATION_PID_FILE=/opt/%p/logs/catalina.pid"
PIDFile=/var/run/%p.pid
ExecStart=/bin/sh -c '/path/to/tomcat/control/script/invoked/with/su/hypen start'
ExecStartPost=/bin/sh -c 'cat ${%p_APPLICATION_PID_FILE} > $(systemctl show %n -p PIDFile|cut -f2- -d"=")'
ExecStop=/bin/sh -c '/path/to/tomcat/control/script/invoked/with/su/hypen stop'
# . . .
poc.path:
[nouser@nohost system]# cat poc.path
# . . .
[Path]
PathExists=/opt/%p/logs/catalina.pid
# . . .
Cách này cũng phục vụ cho tôi cho các ứng dụng Spring Boot. Nhưng khi chúng sinh ra bị treo trên một quy trình bash, tôi đã phải giết ngay quy trình cha mẹ đó để buộc PID 1 trở thành cha mẹ ứng dụng. Nếu không, tạp chí hiển thị thông báo "* .service: Quá trình giám sát XXXXX không phải là con của chúng tôi. Rất có thể chúng tôi sẽ không nhận thấy khi nó thoát.", Và cuối cùng, dịch vụ systemd không dừng ở hành động tắt máy của người dùng.