mirror of
https://github.com/containers/podman.git
synced 2025-06-20 00:51:16 +08:00
Add parallel operation to podman stop
This is the other command that benefits greatly from being run in parallel, due to the potential 15-second timeout for containers that ignore SIGTERM. While we're at it, also clean up how stop timeout is set. This needs to be an optional parameter, so that the value set when the container is created with `--stop-timeout` will be respected. Signed-off-by: Matthew Heon <matthew.heon@pm.me>
This commit is contained in:
@ -85,9 +85,8 @@ func stop(cmd *cobra.Command, args []string) error {
|
|||||||
var (
|
var (
|
||||||
errs utils.OutputErrors
|
errs utils.OutputErrors
|
||||||
)
|
)
|
||||||
stopOptions.Timeout = containerConfig.Engine.StopTimeout
|
|
||||||
if cmd.Flag("time").Changed {
|
if cmd.Flag("time").Changed {
|
||||||
stopOptions.Timeout = stopTimeout
|
stopOptions.Timeout = &stopTimeout
|
||||||
}
|
}
|
||||||
|
|
||||||
responses, err := registry.ContainerEngine().ContainerStop(context.Background(), args, stopOptions)
|
responses, err := registry.ContainerEngine().ContainerStop(context.Background(), args, stopOptions)
|
||||||
|
@ -84,7 +84,7 @@ type StopOptions struct {
|
|||||||
CIDFiles []string
|
CIDFiles []string
|
||||||
Ignore bool
|
Ignore bool
|
||||||
Latest bool
|
Latest bool
|
||||||
Timeout uint
|
Timeout *uint
|
||||||
}
|
}
|
||||||
|
|
||||||
type StopReport struct {
|
type StopReport struct {
|
||||||
|
@ -162,32 +162,33 @@ func (ic *ContainerEngine) ContainerStop(ctx context.Context, namesOrIds []strin
|
|||||||
if err != nil && !(options.Ignore && errors.Cause(err) == define.ErrNoSuchCtr) {
|
if err != nil && !(options.Ignore && errors.Cause(err) == define.ErrNoSuchCtr) {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
for _, con := range ctrs {
|
errMap, err := parallel.ParallelContainerOp(ctx, ctrs, func(c *libpod.Container) error {
|
||||||
report := entities.StopReport{Id: con.ID()}
|
var err error
|
||||||
err = con.StopWithTimeout(options.Timeout)
|
if options.Timeout != nil {
|
||||||
if err != nil {
|
err = c.StopWithTimeout(*options.Timeout)
|
||||||
// These first two are considered non-fatal under the right conditions
|
} else {
|
||||||
if errors.Cause(err) == define.ErrCtrStopped {
|
err = c.Stop()
|
||||||
logrus.Debugf("Container %s is already stopped", con.ID())
|
|
||||||
reports = append(reports, &report)
|
|
||||||
continue
|
|
||||||
|
|
||||||
} else if options.All && errors.Cause(err) == define.ErrCtrStateInvalid {
|
|
||||||
logrus.Debugf("Container %s is not running, could not stop", con.ID())
|
|
||||||
reports = append(reports, &report)
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
report.Err = err
|
|
||||||
reports = append(reports, &report)
|
|
||||||
continue
|
|
||||||
} else if err := con.Cleanup(ctx); err != nil {
|
|
||||||
// Only if no error, proceed to cleanup to ensure all
|
|
||||||
// mounts are removed before we exit.
|
|
||||||
report.Err = err
|
|
||||||
reports = append(reports, &report)
|
|
||||||
continue
|
|
||||||
}
|
}
|
||||||
reports = append(reports, &report)
|
if err != nil {
|
||||||
|
switch {
|
||||||
|
case errors.Cause(err) == define.ErrCtrStopped:
|
||||||
|
logrus.Debugf("Container %s is already stopped", c.ID())
|
||||||
|
case options.All && errors.Cause(err) == define.ErrCtrStateInvalid:
|
||||||
|
logrus.Debugf("Container %s is not running, could not stop", c.ID())
|
||||||
|
default:
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return c.Cleanup(ctx)
|
||||||
|
})
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
for ctr, err := range errMap {
|
||||||
|
report := new(entities.StopReport)
|
||||||
|
report.Id = ctr.ID()
|
||||||
|
report.Err = err
|
||||||
|
reports = append(reports, report)
|
||||||
}
|
}
|
||||||
return reports, nil
|
return reports, nil
|
||||||
}
|
}
|
||||||
|
@ -100,7 +100,7 @@ func (ic *ContainerEngine) ContainerStop(ctx context.Context, namesOrIds []strin
|
|||||||
}
|
}
|
||||||
for _, c := range ctrs {
|
for _, c := range ctrs {
|
||||||
report := entities.StopReport{Id: c.ID}
|
report := entities.StopReport{Id: c.ID}
|
||||||
if err = containers.Stop(ic.ClientCxt, c.ID, &options.Timeout); err != nil {
|
if err = containers.Stop(ic.ClientCxt, c.ID, options.Timeout); err != nil {
|
||||||
// These first two are considered non-fatal under the right conditions
|
// These first two are considered non-fatal under the right conditions
|
||||||
if errors.Cause(err).Error() == define.ErrCtrStopped.Error() {
|
if errors.Cause(err).Error() == define.ErrCtrStopped.Error() {
|
||||||
logrus.Debugf("Container %s is already stopped", c.ID)
|
logrus.Debugf("Container %s is already stopped", c.ID)
|
||||||
|
Reference in New Issue
Block a user