diff options
author | Giuseppe Scrivano <gscrivan@redhat.com> | 2019-07-09 13:19:15 +0200 |
---|---|---|
committer | Giuseppe Scrivano <gscrivan@redhat.com> | 2019-07-09 14:20:20 +0200 |
commit | c6c637da0012d54ddce32e06706c8903564b41cc (patch) | |
tree | ed2e2ebd44d0c8d4c3b5134e0f25f3fe5d9db2f6 /libpod/healthcheck_linux.go | |
parent | f7407f2eb512e1407f8281009eb829f37405119b (diff) | |
download | podman-c6c637da0012d54ddce32e06706c8903564b41cc.tar.gz podman-c6c637da0012d54ddce32e06706c8903564b41cc.tar.bz2 podman-c6c637da0012d54ddce32e06706c8903564b41cc.zip |
healthcheck: support rootless mode
now that dbus authentication works fine from a user namespace (systemd
241 works fine), we can enable rootless healthchecks.
It uses "systemd-run --user" for creating the healthcheck timer and
communicates with the user instance of systemd listening at
$XDG_RUNTIME_DIR/systemd/private.
Closes: https://github.com/containers/libpod/issues/3523
Signed-off-by: Giuseppe Scrivano <gscrivan@redhat.com>
Diffstat (limited to 'libpod/healthcheck_linux.go')
-rw-r--r-- | libpod/healthcheck_linux.go | 49 |
1 files changed, 45 insertions, 4 deletions
diff --git a/libpod/healthcheck_linux.go b/libpod/healthcheck_linux.go index d47a3b7cd..53fb271d1 100644 --- a/libpod/healthcheck_linux.go +++ b/libpod/healthcheck_linux.go @@ -4,13 +4,50 @@ import ( "fmt" "os" "os/exec" + "path/filepath" + "strconv" "strings" + "github.com/containers/libpod/pkg/rootless" "github.com/coreos/go-systemd/dbus" + godbus "github.com/godbus/dbus" "github.com/pkg/errors" "github.com/sirupsen/logrus" ) +func dbusAuthRootlessConnection(createBus func(opts ...godbus.ConnOption) (*godbus.Conn, error)) (*godbus.Conn, error) { + conn, err := createBus() + if err != nil { + return nil, err + } + + methods := []godbus.Auth{godbus.AuthExternal(strconv.Itoa(rootless.GetRootlessUID()))} + + err = conn.Auth(methods) + if err != nil { + conn.Close() + return nil, err + } + + return conn, nil +} + +func newRootlessConnection() (*dbus.Conn, error) { + return dbus.NewConnection(func() (*godbus.Conn, error) { + return dbusAuthRootlessConnection(func(opts ...godbus.ConnOption) (*godbus.Conn, error) { + path := filepath.Join(os.Getenv("XDG_RUNTIME_DIR"), "systemd/private") + return godbus.Dial(fmt.Sprintf("unix:path=%s", path)) + }) + }) +} + +func getConnection() (*dbus.Conn, error) { + if rootless.IsRootless() { + return newRootlessConnection() + } + return dbus.NewSystemdConnection() +} + // createTimer systemd timers for healthchecks of a container func (c *Container) createTimer() error { if c.disableHealthCheckSystemd() { @@ -21,9 +58,13 @@ func (c *Container) createTimer() error { return errors.Wrapf(err, "failed to get path for podman for a health check timer") } - var cmd = []string{"--unit", fmt.Sprintf("%s", c.ID()), fmt.Sprintf("--on-unit-inactive=%s", c.HealthCheckConfig().Interval.String()), "--timer-property=AccuracySec=1s", podman, "healthcheck", "run", c.ID()} + var cmd = []string{} + if rootless.IsRootless() { + cmd = append(cmd, "--user") + } + cmd = append(cmd, "--unit", fmt.Sprintf("%s", c.ID()), fmt.Sprintf("--on-unit-inactive=%s", c.HealthCheckConfig().Interval.String()), "--timer-property=AccuracySec=1s", podman, "healthcheck", "run", c.ID()) - conn, err := dbus.NewSystemdConnection() + conn, err := getConnection() if err != nil { return errors.Wrapf(err, "unable to get systemd connection to add healthchecks") } @@ -42,7 +83,7 @@ func (c *Container) startTimer() error { if c.disableHealthCheckSystemd() { return nil } - conn, err := dbus.NewSystemdConnection() + conn, err := getConnection() if err != nil { return errors.Wrapf(err, "unable to get systemd connection to start healthchecks") } @@ -57,7 +98,7 @@ func (c *Container) removeTimer() error { if c.disableHealthCheckSystemd() { return nil } - conn, err := dbus.NewSystemdConnection() + conn, err := getConnection() if err != nil { return errors.Wrapf(err, "unable to get systemd connection to remove healthchecks") } |