systemd: Erteilen Sie einem nicht privilegierten Benutzer die Berechtigung, einen bestimmten Dienst zu ändern

20

Ich verwende einen privaten Spieleserver auf einer kopflosen Linux-Box. Da ich kein Idiot bin, wird der Server als eigener nichtprivilegierter Benutzer mit den erforderlichen Mindestzugriffsrechten ausgeführt, um Updates herunterzuladen und die Weltdatenbank zu ändern.

Ich habe auch eine System-Unit-Datei erstellt, um den Server bei Bedarf ordnungsgemäß zu starten, zu stoppen und neu zu starten (beispielsweise für die genannten Updates).

Fordern , um tatsächlich jedoch systemctloder service <game> start/stop/restartich immer noch in entweder als root oder anmelden muß sudofähig Benutzer.

Gibt es eine Möglichkeit, systemd mitzuteilen, dass für den <game>Dienst nichtprivilegierte Benutzer gamesrvdie Befehle start / stop / restart ausführen dürfen?

Shadur
quelle
Welche Version von PolicyKit / Distribution? Debian (und Derivate) sind auf einer älteren Version, die ein anderes Konfigurationsdateiformat erfordert .
Gert van den Berg

Antworten:

37

Ich kann mir zwei Möglichkeiten vorstellen, dies zu tun:


Zum einen wird der Dienst zu einem Benutzerdienst und nicht zu einem Systemdienst.

Anstatt eine Systemeinheit zu erstellen, wird die systemd-Einheit im Home-Verzeichnis des Dienstbenutzers unter at abgelegt $HOME/.config/systemd/user/daemon-name.service. Derselbe Benutzer kann den Dienst dann mit verwalten systemctl --user <action> daemon-name.service.

Damit die Benutzereinheit beim Booten starten kann , muss root die Verweildauer für das Konto aktivieren, d sudo loginctl enable-linger username. H. Das Gerät muss auch sein WantedBy=default.target.


Die andere Möglichkeit besteht darin, dem Benutzer den Zugriff auf die Verwaltung der Systemeinheit über PolicyKit zu ermöglichen. Dies erfordert systemd 226 oder höher (und PolicyKit> = 0.106 für die JavaScript rules.d-Dateien - prüfen Sie mit pkaction --version).

Sie würden eine neue PolicyKit-Konfigurationsdatei erstellen, die z. B. /etc/polkit-1/rules.d/57-manage-daemon-name.rulesnach den Attributen sucht, die Sie zulassen möchten. Zum Beispiel :

// Allow alice to manage example.service;
// fall back to implicit authorization otherwise.
polkit.addRule(function(action, subject) {
    if (action.id == "org.freedesktop.systemd1.manage-units" &&
        action.lookup("unit") == "example.service" &&
        subject.user == "alice") {
        return polkit.Result.YES;
    }
});

Der benannte Benutzer kann dann den benannten Dienst mit systemctlund ohne Verwendung verwalten sudo.

Michael Hampton
quelle
Benutzermodus und loginctlarbeitete.
Shadur
1
Funktioniert das unter Ubuntu 16.04? Ist es normal, dass das Verzeichnis rules.d nicht existiert? Ich kann es nicht zum Laufen bringen. Meine Regeln werden ignoriert.
ygoe
3
Muss ich etwas neu starten, um das PolicyKit zu aktivieren?
Josir
@MichaelHampton Mit dem systemd -user kann ich alles bekommen, was ich arbeiten möchte, außer den Dienststart beim Booten. Ich denke, das ist normal, da ich es an mehreren Stellen gelesen habe (z. B. im Archlinux-Wiki), aber Sie sagen, es sollte funktionieren, sind Sie sich sicher?
Daks
@daks Ja, es funktioniert. Wenn Sie immer noch ein Problem damit haben, stellen Sie eine neue Frage.
Michael Hampton
12

sudoist dafür gemacht. Bearbeiten Sie Ihre /etc/sudoersDatei mit visudo, um ein Cmd_aliasfür die Befehle hinzuzufügen , die der nichtprivilegierte Benutzer verwenden soll:

# game server commands
Cmnd_Alias GAME_CMDS = /usr/bin/systemctl start <game service>, /usr/bin/systemctl stop <game service>

und fügen Sie eine Zeile hinzu, damit der nichtprivilegierte Benutzer die mit dem Alias ​​definierten Befehle wie folgt verwenden kann:

unprivileged_user ALL=(ALL) NOPASSWD: GAME_CMDS

Weitere Informationen zu den verschiedenen Parametern des Befehls sudo finden Sie in der Dokumentation zu diesem Thema.

Möglicherweise müssen Sie das sudoPaket installieren , damit sudoes auf Ihrem System verfügbar ist.

Henrik Pingel setzt Monica wieder ein
quelle
Ich weiß, wie man Sudo benutzt, ja. Ich habe mich gefragt, ob es eine Option gibt, mit der ich das überspringen kann, da in diesem Fall die systemdUnit-Datei als erstes angibt, dass sie ausgeführt werden muss gamesrv.
Shadur
1

Sie können sich sudomit dem Bereitstellen eines entsprechenden Zugriffs verbinden root, aber es kann auch verwendet werden, um einem bestimmten Benutzer root-Zugriff auf einen bestimmten, begrenzten Satz von Befehlen zu gewähren.

Wie wurde dies bereits bei Server Fault beantwortet ? (Zugriff auf eine Reihe von Befehlen an einen Nicht-Root-Benutzer ohne sudo Zugriff auf eine Reihe von Befehlen an einen Nicht-Root-Benutzer ohne sudo).

Die Verwendung von PolicyKit ist weiterhin ungewöhnlich. Die Verwendung einer systemd "Benutzereinheit" sollte funktionieren, aber in der Vergangenheit wurde Ihr Ziel oft erreicht, indem die Möglichkeit genutzt wurde sudo, einem Benutzer die Ausführung bestimmter Befehle als root zu ermöglichen.

Mark Stosberg
quelle