mirror of
https://github.com/containrrr/watchtower.git
synced 2025-12-16 15:10:12 +01:00
Implement support for updating stopped containers
This commit adds a command line flag, "--check-all". If true, the behavior requested by #112 is used (i.e., stopped containers are updated but not restarted). If false, the previous behavior is used (ignore stopped containers entirely).
This commit is contained in:
parent
2cfbebb0e9
commit
ab14e25f7c
4 changed files with 42 additions and 13 deletions
|
|
@ -67,6 +67,8 @@ func Update(client container.Client, names []string, cleanup bool, noRestart boo
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
|
container.WasRunning = container.IsRunning()
|
||||||
|
|
||||||
if container.Stale {
|
if container.Stale {
|
||||||
if err := client.StopContainer(container, waitTime); err != nil {
|
if err := client.StopContainer(container, waitTime); err != nil {
|
||||||
log.Error(err)
|
log.Error(err)
|
||||||
|
|
|
||||||
|
|
@ -37,31 +37,41 @@ type Client interface {
|
||||||
// * DOCKER_HOST the docker-engine host to send api requests to
|
// * DOCKER_HOST the docker-engine host to send api requests to
|
||||||
// * DOCKER_TLS_VERIFY whether to verify tls certificates
|
// * DOCKER_TLS_VERIFY whether to verify tls certificates
|
||||||
// * DOCKER_API_VERSION the minimum docker api version to work with
|
// * DOCKER_API_VERSION the minimum docker api version to work with
|
||||||
func NewClient(pullImages, enableLabel bool) Client {
|
func NewClient(pullImages, enableLabel bool, checkAll bool) Client {
|
||||||
cli, err := dockerclient.NewEnvClient()
|
cli, err := dockerclient.NewEnvClient()
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Fatalf("Error instantiating Docker client: %s", err)
|
log.Fatalf("Error instantiating Docker client: %s", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
return dockerClient{api: cli, pullImages: pullImages, enableLabel: enableLabel}
|
return dockerClient{
|
||||||
|
api: cli,
|
||||||
|
pullImages: pullImages,
|
||||||
|
enableLabel: enableLabel,
|
||||||
|
checkAll: checkAll}
|
||||||
}
|
}
|
||||||
|
|
||||||
type dockerClient struct {
|
type dockerClient struct {
|
||||||
api *dockerclient.Client
|
api *dockerclient.Client
|
||||||
pullImages bool
|
pullImages bool
|
||||||
enableLabel bool
|
enableLabel bool
|
||||||
|
checkAll bool
|
||||||
}
|
}
|
||||||
|
|
||||||
func (client dockerClient) ListContainers(fn Filter) ([]Container, error) {
|
func (client dockerClient) ListContainers(fn Filter) ([]Container, error) {
|
||||||
cs := []Container{}
|
cs := []Container{}
|
||||||
bg := context.Background()
|
bg := context.Background()
|
||||||
|
|
||||||
log.Debug("Retrieving running containers")
|
if client.checkAll {
|
||||||
|
log.Debug("Retrieving containers")
|
||||||
|
} else {
|
||||||
|
log.Debug("Retrieving running containers")
|
||||||
|
}
|
||||||
|
|
||||||
runningContainers, err := client.api.ContainerList(
|
runningContainers, err := client.api.ContainerList(
|
||||||
bg,
|
bg,
|
||||||
types.ContainerListOptions{})
|
types.ContainerListOptions{
|
||||||
|
All: client.checkAll})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -103,10 +113,12 @@ func (client dockerClient) StopContainer(c Container, timeout time.Duration) err
|
||||||
signal = defaultStopSignal
|
signal = defaultStopSignal
|
||||||
}
|
}
|
||||||
|
|
||||||
log.Infof("Stopping %s (%s) with %s", c.Name(), c.ID(), signal)
|
if c.WasRunning {
|
||||||
|
log.Infof("Stopping %s (%s) with %s", c.Name(), c.ID(), signal)
|
||||||
|
|
||||||
if err := client.api.ContainerKill(bg, c.ID(), signal); err != nil {
|
if err := client.api.ContainerKill(bg, c.ID(), signal); err != nil {
|
||||||
return err
|
return err
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Wait for container to exit, but proceed anyway after the timeout elapses
|
// Wait for container to exit, but proceed anyway after the timeout elapses
|
||||||
|
|
@ -173,11 +185,13 @@ func (client dockerClient) StartContainer(c Container) error {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
log.Debugf("Starting container %s (%s)", name, creation.ID)
|
if c.WasRunning {
|
||||||
|
log.Debugf("Starting container %s (%s)", name, creation.ID)
|
||||||
|
|
||||||
err = client.api.ContainerStart(bg, creation.ID, types.ContainerStartOptions{})
|
err = client.api.ContainerStart(bg, creation.ID, types.ContainerStartOptions{})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
|
|
|
||||||
|
|
@ -27,7 +27,8 @@ func NewContainer(containerInfo *types.ContainerJSON, imageInfo *types.ImageInsp
|
||||||
|
|
||||||
// Container represents a running Docker container.
|
// Container represents a running Docker container.
|
||||||
type Container struct {
|
type Container struct {
|
||||||
Stale bool
|
Stale bool
|
||||||
|
WasRunning bool
|
||||||
|
|
||||||
containerInfo *types.ContainerJSON
|
containerInfo *types.ContainerJSON
|
||||||
imageInfo *types.ImageInspect
|
imageInfo *types.ImageInspect
|
||||||
|
|
@ -106,6 +107,13 @@ func (c Container) IsWatchtower() bool {
|
||||||
return ok && val == "true"
|
return ok && val == "true"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// IsRunning returns a boolean flag indicating whether or not the current
|
||||||
|
// container is running. The status is determined by the value of the
|
||||||
|
// container's "State.Running" property.
|
||||||
|
func (c Container) IsRunning() bool {
|
||||||
|
return c.containerInfo.State.Running
|
||||||
|
}
|
||||||
|
|
||||||
// StopSignal returns the custom stop signal (if any) that is encoded in the
|
// StopSignal returns the custom stop signal (if any) that is encoded in the
|
||||||
// container's metadata. If the container has not specified a custom stop
|
// container's metadata. If the container has not specified a custom stop
|
||||||
// signal, the empty string "" is returned.
|
// signal, the empty string "" is returned.
|
||||||
|
|
|
||||||
7
main.go
7
main.go
|
|
@ -61,6 +61,11 @@ func main() {
|
||||||
Usage: "the cron expression which defines when to update",
|
Usage: "the cron expression which defines when to update",
|
||||||
EnvVar: "WATCHTOWER_SCHEDULE",
|
EnvVar: "WATCHTOWER_SCHEDULE",
|
||||||
},
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "check-all",
|
||||||
|
Usage: "check non-running containers",
|
||||||
|
EnvVar: "WATCHTOWER_CHECK_ALL",
|
||||||
|
},
|
||||||
cli.BoolFlag{
|
cli.BoolFlag{
|
||||||
Name: "no-pull",
|
Name: "no-pull",
|
||||||
Usage: "do not pull new images",
|
Usage: "do not pull new images",
|
||||||
|
|
@ -159,7 +164,7 @@ func before(c *cli.Context) error {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
client = container.NewClient(!c.GlobalBool("no-pull"), c.GlobalBool("label-enable"))
|
client = container.NewClient(!c.GlobalBool("no-pull"), c.GlobalBool("label-enable"), c.GlobalBool("check-all"))
|
||||||
notifier = notifications.NewNotifier(c)
|
notifier = notifications.NewNotifier(c)
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue