diff options
Diffstat (limited to 'pkg/systemd')
-rw-r--r-- | pkg/systemd/generate/common.go | 24 | ||||
-rw-r--r-- | pkg/systemd/generate/containers.go | 12 | ||||
-rw-r--r-- | pkg/systemd/generate/containers_test.go | 143 |
3 files changed, 173 insertions, 6 deletions
diff --git a/pkg/systemd/generate/common.go b/pkg/systemd/generate/common.go index 60b0c4b52..b0a441d54 100644 --- a/pkg/systemd/generate/common.go +++ b/pkg/systemd/generate/common.go @@ -42,7 +42,7 @@ RequiresMountsFor={{{{.RunRoot}}}} // filterPodFlags removes --pod, --pod-id-file and --infra-conmon-pidfile from the specified command. // argCount is the number of last arguments which should not be filtered, e.g. the container entrypoint. func filterPodFlags(command []string, argCount int) []string { - processed := []string{} + processed := make([]string, 0, len(command)) for i := 0; i < len(command)-argCount; i++ { s := command[i] if s == "--pod" || s == "--pod-id-file" || s == "--infra-conmon-pidfile" { @@ -63,7 +63,7 @@ func filterPodFlags(command []string, argCount int) []string { // filterCommonContainerFlags removes --sdnotify, --rm and --cgroups from the specified command. // argCount is the number of last arguments which should not be filtered, e.g. the container entrypoint. func filterCommonContainerFlags(command []string, argCount int) []string { - processed := []string{} + processed := make([]string, 0, len(command)) for i := 0; i < len(command)-argCount; i++ { s := command[i] @@ -71,7 +71,7 @@ func filterCommonContainerFlags(command []string, argCount int) []string { case s == "--rm": // Boolean flags support --flag and --flag={true,false}. continue - case s == "--sdnotify", s == "--cgroups", s == "--cidfile", s == "--restart": + case s == "--cgroups", s == "--cidfile", s == "--restart": i++ continue case strings.HasPrefix(s, "--rm="), @@ -111,6 +111,24 @@ func escapeSystemdArg(arg string) string { return arg } +func removeSdNotifyArg(args []string, argCount int) []string { + processed := make([]string, 0, len(args)) + for i := 0; i < len(args)-argCount; i++ { + s := args[i] + + switch { + case s == "--sdnotify": + i++ + continue + case strings.HasPrefix(s, "--sdnotify="): + continue + } + processed = append(processed, s) + } + processed = append(processed, args[len(args)-argCount:]...) + return processed +} + func removeDetachArg(args []string, argCount int) []string { // "--detach=false" could also be in the container entrypoint // split them off so we do not remove it there diff --git a/pkg/systemd/generate/containers.go b/pkg/systemd/generate/containers.go index 6596ef73b..1f8c519b7 100644 --- a/pkg/systemd/generate/containers.go +++ b/pkg/systemd/generate/containers.go @@ -378,6 +378,9 @@ func executeContainerTemplate(info *containerInfo, options entities.GenerateSyst fs.StringArrayP("env", "e", nil, "") fs.String("sdnotify", "", "") fs.String("restart", "", "") + // have to define extra -h flag to prevent help error when parsing -h hostname + // https://github.com/containers/podman/issues/15124 + fs.StringP("help", "h", "", "") if err := fs.Parse(remainingCmd); err != nil { return "", fmt.Errorf("parsing remaining command-line arguments: %w", err) } @@ -403,8 +406,13 @@ func executeContainerTemplate(info *containerInfo, options entities.GenerateSyst // Default to --sdnotify=conmon unless already set by the // container. - hasSdnotifyParam := fs.Lookup("sdnotify").Changed - if !hasSdnotifyParam { + sdnotifyFlag := fs.Lookup("sdnotify") + if !sdnotifyFlag.Changed { + startCommand = append(startCommand, "--sdnotify=conmon") + } else if sdnotifyFlag.Value.String() == libpodDefine.SdNotifyModeIgnore { + // If ignore is set force conmon otherwise the unit with Type=notify will fail. + logrus.Infof("Forcing --sdnotify=conmon for container %s", info.ContainerNameOrID) + remainingCmd = removeSdNotifyArg(remainingCmd, fs.NArg()) startCommand = append(startCommand, "--sdnotify=conmon") } diff --git a/pkg/systemd/generate/containers_test.go b/pkg/systemd/generate/containers_test.go index 640aa298e..873cbfbb3 100644 --- a/pkg/systemd/generate/containers_test.go +++ b/pkg/systemd/generate/containers_test.go @@ -2,6 +2,7 @@ package generate import ( "fmt" + "strings" "testing" "github.com/containers/podman/v4/pkg/domain/entities" @@ -317,6 +318,39 @@ NotifyAccess=all WantedBy=default.target ` + goodWithNameAndSdnotifyIgnore := `# jadda-jadda.service +# autogenerated by Podman CI + +[Unit] +Description=Podman jadda-jadda.service +Documentation=man:podman-generate-systemd(1) +Wants=network-online.target +After=network-online.target +RequiresMountsFor=/var/run/containers/storage + +[Service] +Environment=PODMAN_SYSTEMD_UNIT=%n +Restart=on-failure +TimeoutStopSec=70 +ExecStartPre=/bin/rm -f %t/%n.ctr-id +ExecStart=/usr/bin/podman container run \ + --cidfile=%t/%n.ctr-id \ + --cgroups=no-conmon \ + --rm \ + --sdnotify=conmon \ + -d \ + --replace \ + --name jadda-jadda \ + --hostname hello-world awesome-image:latest command arg1 ... argN "foo=arg \"with \" space" +ExecStop=/usr/bin/podman stop --ignore --cidfile=%t/%n.ctr-id +ExecStopPost=/usr/bin/podman rm -f --ignore --cidfile=%t/%n.ctr-id +Type=notify +NotifyAccess=all + +[Install] +WantedBy=default.target +` + goodWithExplicitShortDetachParam := `# jadda-jadda.service # autogenerated by Podman CI @@ -781,6 +815,37 @@ NotifyAccess=all WantedBy=default.target ` + goodNewWithHostname := `# jadda-jadda.service +# autogenerated by Podman CI + +[Unit] +Description=Podman jadda-jadda.service +Documentation=man:podman-generate-systemd(1) +Wants=network-online.target +After=network-online.target +RequiresMountsFor=/var/run/containers/storage + +[Service] +Environment=PODMAN_SYSTEMD_UNIT=%n +Restart=on-failure +TimeoutStopSec=70 +ExecStartPre=/bin/rm -f %t/%n.ctr-id +ExecStart=/usr/bin/podman run \ + --cidfile=%t/%n.ctr-id \ + --cgroups=no-conmon \ + --rm \ + --sdnotify=conmon \ + -d \ + -h hostname awesome-image:latest +ExecStop=/usr/bin/podman stop --ignore --cidfile=%t/%n.ctr-id +ExecStopPost=/usr/bin/podman rm -f --ignore --cidfile=%t/%n.ctr-id +Type=notify +NotifyAccess=all + +[Install] +WantedBy=default.target +` + templateGood := `# container-foo@.service # autogenerated by Podman CI @@ -992,7 +1057,7 @@ WantedBy=default.target false, false, }, - {"good with name and sdnotify", + {"good with name and --sdnotify=container", containerInfo{ Executable: "/usr/bin/podman", ServiceName: "jadda-jadda", @@ -1011,6 +1076,63 @@ WantedBy=default.target false, false, }, + {"good with name and --sdnotify container", + containerInfo{ + Executable: "/usr/bin/podman", + ServiceName: "jadda-jadda", + ContainerNameOrID: "jadda-jadda", + PIDFile: "/run/containers/storage/overlay-containers/639c53578af4d84b8800b4635fa4e680ee80fd67e0e6a2d4eea48d1e3230f401/userdata/conmon.pid", + StopTimeout: 10, + PodmanVersion: "CI", + CreateCommand: []string{"I'll get stripped", "container", "run", "--sdnotify", "container", "--name", "jadda-jadda", "--hostname", "hello-world", "awesome-image:latest", "command", "arg1", "...", "argN", "foo=arg \"with \" space"}, + EnvVariable: define.EnvVariable, + GraphRoot: "/var/lib/containers/storage", + RunRoot: "/var/run/containers/storage", + }, + strings.ReplaceAll(goodWithNameAndSdnotify, "--sdnotify=container", "--sdnotify container"), + true, + false, + false, + false, + }, + {"good with name and --sdnotify=ignore", + containerInfo{ + Executable: "/usr/bin/podman", + ServiceName: "jadda-jadda", + ContainerNameOrID: "jadda-jadda", + PIDFile: "/run/containers/storage/overlay-containers/639c53578af4d84b8800b4635fa4e680ee80fd67e0e6a2d4eea48d1e3230f401/userdata/conmon.pid", + StopTimeout: 10, + PodmanVersion: "CI", + CreateCommand: []string{"I'll get stripped", "container", "run", "--sdnotify=ignore", "--name", "jadda-jadda", "--hostname", "hello-world", "awesome-image:latest", "command", "arg1", "...", "argN", "foo=arg \"with \" space"}, + EnvVariable: define.EnvVariable, + GraphRoot: "/var/lib/containers/storage", + RunRoot: "/var/run/containers/storage", + }, + goodWithNameAndSdnotifyIgnore, + true, + false, + false, + false, + }, + {"good with name and --sdnotify ignore", + containerInfo{ + Executable: "/usr/bin/podman", + ServiceName: "jadda-jadda", + ContainerNameOrID: "jadda-jadda", + PIDFile: "/run/containers/storage/overlay-containers/639c53578af4d84b8800b4635fa4e680ee80fd67e0e6a2d4eea48d1e3230f401/userdata/conmon.pid", + StopTimeout: 10, + PodmanVersion: "CI", + CreateCommand: []string{"I'll get stripped", "container", "run", "--sdnotify", "ignore", "--name", "jadda-jadda", "--hostname", "hello-world", "awesome-image:latest", "command", "arg1", "...", "argN", "foo=arg \"with \" space"}, + EnvVariable: define.EnvVariable, + GraphRoot: "/var/lib/containers/storage", + RunRoot: "/var/run/containers/storage", + }, + goodWithNameAndSdnotifyIgnore, + true, + false, + false, + false, + }, {"good with explicit short detach param", containerInfo{ Executable: "/usr/bin/podman", @@ -1341,6 +1463,25 @@ WantedBy=default.target false, false, }, + {"good with -h hostname", + containerInfo{ + Executable: "/usr/bin/podman", + ServiceName: "jadda-jadda", + ContainerNameOrID: "jadda-jadda", + PIDFile: "/var/run/containers/storage/overlay-containers/639c53578af4d84b8800b4635fa4e680ee80fd67e0e6a2d4eea48d1e3230f401/userdata/conmon.pid", + StopTimeout: 10, + PodmanVersion: "CI", + GraphRoot: "/var/lib/containers/storage", + RunRoot: "/var/run/containers/storage", + CreateCommand: []string{"I'll get stripped", "create", "-h", "hostname", "awesome-image:latest"}, + EnvVariable: define.EnvVariable, + }, + goodNewWithHostname, + true, + false, + false, + false, + }, {"good template", containerInfo{ Executable: "/usr/bin/podman", |