首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何设计系统路径单元?

如何设计系统路径单元?
EN

Stack Overflow用户
提问于 2017-03-06 15:07:42
回答 2查看 2.7K关注 0票数 2

程序my_prog将在启动后启动。它创建一个由root:root拥有的Unix域套接字root:root

我想做以下几件事:

  • 创建套接字文件后,将其所有者更改为www-data:www-data
  • 在程序退出后删除套接字文件。

这是我单元文件my_prog.service的第一个版本。

代码语言:javascript
复制
[Unit]
Description=My Program
After=network.target

[Service]
ExecStart=/usr/local/bin/my_prog
ExecStartPost=chmod www-data:www-data /tmp/my_prog.sock
ExecStopPost=rm -f /tmp/my_prog.sock

[Install]
WantedBy=multi-user.target

这个版本有两个问题:

  • /tmp/my_prog.sock的所有者从未改变--始终是root:root
  • 停止此服务后,永远不会删除/tmp/my_prog.sock

我想是命令chmodrm执行得太快给了我这样意想不到的结果:

  • chmodmy_prog完成创建套接字文件之前运行,
  • rmmy_program退出之前运行(my_program禁止其套接字文件在运行时被删除?)。

以下是我的第二个版本,它没有给我正确的结果,或者:

文件my_prog.service

代码语言:javascript
复制
[Unit]
Description=My Program
After=network.target

[Service]
ExecStart=/usr/local/bin/my_prog

[Install]
WantedBy=multi-user.target

文件my_prog-socket.path

代码语言:javascript
复制
[Unit]
Description=My program - notify socket existence

[Path]
PathExists=/tmp/my_prog.sock

文件my_prog-socket.service

代码语言:javascript
复制
[Unit]
Description=My program - change owner and remove socket

[Service]
ExecStart=chown www-data:www-data /tmp/my_prog.sock
ExecStopPost=rm -f /tmp/my_prog.sock

我把所有的花招都花光了。我的单位档案怎么了?有比上面更优雅的设计吗?

谢谢!

P.S.:对于那些感兴趣的人来说,这个遗留版本/etc/init.d/my-prog的工作至少与预期的一样:

代码语言:javascript
复制
#!/bin/sh
### BEGIN INIT INFO
# Provides:         my-program
# Default-Start:    2 3 4 5
# Default-Stop:     0 1 6
# Short-Description:    My Program
# Description:      My Program
### END INIT INFO


PATH=/sbin:/bin:/usr/sbin:/usr/bin
DAEMON=/usr/local/bin/my_prog
NAME=my-program
DESC="My Program"
SCRIPTNAME=/etc/init.d/$NAME
PIDFILE=/var/run/my-prog.pid
SOCKET_FILE="/tmp/my-prog.sock"

test -x $DAEMON || exit 0

grant_socket_access()
{
    #Wait program to create socket.
    count=1
    while [ "$count" -lt "50" ]
    do
        if [ -S $SOCKET_FILE ]
        then
            chown www-data:www-data $SOCKET_FILE
            return 0
        fi
        sleep 0.2
        count=`expr $count + 1`
    done
    echo >&2 "$NAME fails to grant access to Unix socket file: $SOCKET_FILE"
    return 1
}

. /lib/lsb/init-functions

case "$1" in
    start)
        log_daemon_msg "Starting $DESC" $NAME
        rm -f $SOCKET_FILE
        if start-stop-daemon --start --quiet --pidfile $PIDFILE --exec $DAEMON -b -m
        then
            grant_socket_access
        else
            rm -f $SOCKET_FILE
        fi
        log_end_msg $?
        ;;
    stop)
        log_daemon_msg "Stopping $DESC" $NAME
        rm -f $SOCKET_FILE
        if start-stop-daemon --stop --retry TERM/10/KILL/5 --quiet --pidfile $PIDFILE --exec $DAEMON --remove-pidfile
        then
            log_daemon_msg "$DESC" "$NAME stopped"
            log_end_msg 0
        else
            log_end_msg 1
        fi
        ;;
    reload|force-reload)
        log_daemon_msg "Reloading $DESC" $NAME
        rm -f $SOCKET_FILE
        if start-stop-daemon --stop --signal HUP --quiet --pidfile $PIDFILE --exec $DAEMON
        then
            grant_socket_access
            log_end_msg $?
        else
            log_end_msg 1
        fi
        ;;
    restart)
        log_daemon_msg "Restarting $DESC" $NAME
        $0 stop
        $0 start
        ;;
    status)
        status_of_proc -p "$PIDFILE" "$DAEMON" "$NAME" && exit 0 || exit $?
        ;;
    *)
        echo "Usage: $SCRIPTNAME {start|stop|restart|reload|force-reload|status}" >&2
        exit 1
        ;;
esac

exit 0

编辑

按照@Mark善意提供的配方,我已经修改了我最初的第一个版本,使之有/bin/chown/bin/rm

我从新版本的行ExecStopPost=/bin/rm -f /tmp/my_prog.sock中获得了所需的结果。但是,ExecStart=/bin/chown www-data:www-data /tmp/my_prog.sock输出此错误:

代码语言:javascript
复制
chown[8388]: /bin/chown: connot access '/tmp/my_prog.socket'
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2017-03-06 15:13:35

通过systemd-analyze verify ./your-file.service运行脚本可以发现以下问题:

代码语言:javascript
复制
[/home/mark/tmp/t.service:7] Executable path is not absolute, ignoring: chmod www-data:www-data /tmp/my_prog.sock                                   
[/home/mark/tmp/t.service:8] Executable path is not absolute, ignoring: rm -f /tmp/my_prog.sock  

man systemd.service中的文档记录了可执行路径必须是绝对的要求。

您的错误引用了一个具有.socket扩展名的文件,但是您的示例显示了一个.sock扩展名。确认您在任何地方都始终使用.sock.socket

如果您的服务不需要作为根用户运行,则可以通过使用chownUser=指令以不同用户的身份运行服务,从而提高安全性并避免使用Group=。这将创建一个由该用户拥有的套接字,而不是根。

票数 1
EN

Stack Overflow用户

发布于 2019-06-05 20:18:12

谢谢!绝对可执行路径解决了我的第二个问题。我的第一个问题仍然是

你的第一个问题是,chmod不接受“所有者:组”,你真的想要'chown‘

例如:

代码语言:javascript
复制
ExecStartPost=**chown** www-data:www-data /tmp/my_prog.sock
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/42628988

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档