在 Ubuntu 16.04 上在其自己的 ip netns 命名空间中运行服务

在 Ubuntu 16.04 上在其自己的 ip netns 命名空间中运行服务

我曾经在 14.04 中通过执行来运行服务

ip netns exec namespacename service start servicename

但我意识到这在 16.04 上不再起作用。该服务在正常命名空间中启动。

我尝试编辑 /lib/systemd/system/servicename.service 文件以使用命名空间,但没有成功。第一个问题是该程序是以其自己的用户执行的,该用户无权访问命名空间。我将其更改为以 root 身份运行该程序,然后在 ExecStart 中使用 sudo,但出于某种原因,服务控制从未返回到命令提示符。

关于如何实现服务在 Ubuntu 16.04 上每次重新启动时自动且永久地在命名空间内运行的任何想法?

如果重要的话,所讨论的服务是 transmission-daemon

更新:

我设法让它与以下 .service 文件一起工作。文件中的“vpn”是命名空间的名称。我的问题是Type服务设置错误。我仍然觉得这个解决方案不是最好的解决方案。如果你有更好的方法,请告诉我!

[Unit]
Description=Transmission BitTorrent Daemon
After=network.target

[Service]
User=root
Type=simple
ExecStart=/bin/sh -c 'exec /sbin/ip netns exec vpn /usr/bin/sudo -u debian-transmission /usr/bin/transmission-daemon -f --log-error --config-dir /var/lib/transmission-daemon/info'
ExecReload=/bin/kill -s HUP $MAINPID

[Install]
WantedBy=multi-user.target

答案1

最近在 man systemd.exec(5) 中发现

PrivateNetwork=
           Takes a boolean argument. If true, sets up a new network namespace for the executed processes and configures only the loopback network device
           "lo" inside it. No other network devices will be available to the executed process. This is useful to turn off network access by the executed
           process. Defaults to false. It is possible to run two or more units within the same private network namespace by using the JoinsNamespaceOf=
           directive, see systemd.unit(5) for details. Note that this option will disconnect all socket families from the host, this includes AF_NETLINK
           and AF_UNIX. The latter has the effect that AF_UNIX sockets in the abstract socket namespace will become unavailable to the processes
           (however, those located in the file system will continue to be accessible).

答案2

使用systemd,您可以通过添加NetworkNamespacePath=行到服务的.service文件。

NetworkNamespacePath=从 Ubuntu 22.04 和 Systemd 249 开始可用。(我不知道此功能具体是什么时候首次推出的。)

man 5 systemd.exec

   NetworkNamespacePath=
       Takes an absolute file system path refererring to a Linux network
       namespace pseudo-file (i.e. a file like /proc/$PID/ns/net or a bind
       mount or symlink to one). When set the invoked processes are added
       to the network namespace referenced by that path. The path has to
       point to a valid namespace file at the moment the processes are
       forked off. If this option is used PrivateNetwork= has no effect.
       If this option is used together with JoinsNamespaceOf= then it only
       has an effect if this unit is started before any of the listed
       units that have PrivateNetwork= or NetworkNamespacePath=
       configured, as otherwise the network namespace of those units is
       reused.

       When this option is used on a socket unit any sockets bound on
       behalf of this unit will be bound within the specified network
       namespace.

       This option is only available for system services and is not
       supported for services running in per-user instances of the service
       manager.

从 Ubuntu 23.04 和系统 252 开始:

       This option is only available for system services, or for services
       running in per-user instances of the service manager when
       PrivateUsers= is enabled.

相关内容