Sudoers:允许特定参数的任何子命令

XYZ*_*ose 8 administration sudo

我试图允许一组用户获得对 dhcpcd 服务实例的一些控制。换句话说,我希望他们能够运行:

systemctl (start,stop,...) dhcpcd@eth0.service
Run Code Online (Sandbox Code Playgroud)

没有被提示输入密码,但只在 dhcpcd@eth0.service 上。我已经遇到过这样做的方法,但是它们需要在自己的行中枚举每个子命令。

%mygroup ALL=NOPASSWD: /usr/bin/systemctl start dhcpcd@eth0.service, /usr/bin/systemctl stop dhcpcd@eth0.service, ...
Run Code Online (Sandbox Code Playgroud)

有没有更优雅的方法来做到这一点?

gro*_*mal 9

仅通配符 ( man glob, man fnmatch)支持 Sudoers 通配符。然而,start, stop, restart( 等) 命令systemctl不能被全局化,因为它们不是文件。

从安全的角度来看,您需要枚举每个命令是一件好事。如果dhcpcd@eth0.service使用命令进行更新,请说shutdown-machine在系统更新时您的 sudo 用户将无法使用它(谢天谢地)。

sudoers 手册中有一个关于此的说明:

 Wildcards in command line arguments should be used with care.
 Command line arguments are matched as a single, concatenated string.  This mean a wildcard character such as ‘?’ or
 ‘*’ will match across word boundaries, which may be unexpected.  For example, while a sudoers entry like:

     %operator ALL = /bin/cat /var/log/messages*

 will allow command like:

     $ sudo cat /var/log/messages.1

 It will also allow:

     $ sudo cat /var/log/messages /etc/shadow

 which is probably not what was intended.  In most cases it is better to do command line processing outside of the
 sudoers file in a scripting language.
Run Code Online (Sandbox Code Playgroud)

另一方面,如果你想节省打字的时间,你可以完全按照手册的建议去做:使用脚本语言。例如,你可以写这样的东西,比如/usr/local/sbin/sudoers-dhcpd.sh:

#!/bin/sh

case "$1" in
  start)
    systemctl start dhcpcd@eth0.service
    ;;
  stop)
    systemctl stop dhcpcd@eth0.service
    ;;
  restart)
    systemctl restart dhcpcd@eth0.service
    ;;
  *)
    echo You are not allowed to do that!
    ;;
esac
Run Code Online (Sandbox Code Playgroud)

并添加如下 sudoers 行:

%mygroup ALL=NOPASSWD: /usr/local/sbin/sudoers-dhcpd.sh
Run Code Online (Sandbox Code Playgroud)