mirror of https://github.com/docker/cli.git
Merge pull request #4453 from thaJeztah/small_interface_waitExitOrRemoved
cli/command/container: waitExitOrRemoved: take APIClient as argument
This commit is contained in:
commit
e0e2772439
|
@ -187,7 +187,7 @@ func runContainer(dockerCli command.Cli, opts *runOptions, copts *containerOptio
|
||||||
defer closeFn()
|
defer closeFn()
|
||||||
}
|
}
|
||||||
|
|
||||||
statusChan := waitExitOrRemoved(ctx, dockerCli, containerID, copts.autoRemove)
|
statusChan := waitExitOrRemoved(ctx, dockerCli.Client(), containerID, copts.autoRemove)
|
||||||
|
|
||||||
// start the container
|
// start the container
|
||||||
if err := client.ContainerStart(ctx, containerID, types.ContainerStartOptions{}); err != nil {
|
if err := client.ContainerStart(ctx, containerID, types.ContainerStartOptions{}); err != nil {
|
||||||
|
|
|
@ -145,14 +145,14 @@ func RunStart(dockerCli command.Cli, opts *StartOptions) error {
|
||||||
|
|
||||||
// 3. We should open a channel for receiving status code of the container
|
// 3. We should open a channel for receiving status code of the container
|
||||||
// no matter it's detached, removed on daemon side(--rm) or exit normally.
|
// no matter it's detached, removed on daemon side(--rm) or exit normally.
|
||||||
statusChan := waitExitOrRemoved(ctx, dockerCli, c.ID, c.HostConfig.AutoRemove)
|
statusChan := waitExitOrRemoved(ctx, dockerCli.Client(), c.ID, c.HostConfig.AutoRemove)
|
||||||
startOptions := types.ContainerStartOptions{
|
|
||||||
CheckpointID: opts.Checkpoint,
|
|
||||||
CheckpointDir: opts.CheckpointDir,
|
|
||||||
}
|
|
||||||
|
|
||||||
// 4. Start the container.
|
// 4. Start the container.
|
||||||
if err := dockerCli.Client().ContainerStart(ctx, c.ID, startOptions); err != nil {
|
err = dockerCli.Client().ContainerStart(ctx, c.ID, types.ContainerStartOptions{
|
||||||
|
CheckpointID: opts.Checkpoint,
|
||||||
|
CheckpointDir: opts.CheckpointDir,
|
||||||
|
})
|
||||||
|
if err != nil {
|
||||||
cancelFun()
|
cancelFun()
|
||||||
<-cErr
|
<-cErr
|
||||||
if c.HostConfig.AutoRemove {
|
if c.HostConfig.AutoRemove {
|
||||||
|
|
|
@ -4,16 +4,16 @@ import (
|
||||||
"context"
|
"context"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
|
||||||
"github.com/docker/cli/cli/command"
|
|
||||||
"github.com/docker/docker/api/types"
|
"github.com/docker/docker/api/types"
|
||||||
"github.com/docker/docker/api/types/container"
|
"github.com/docker/docker/api/types/container"
|
||||||
"github.com/docker/docker/api/types/events"
|
"github.com/docker/docker/api/types/events"
|
||||||
"github.com/docker/docker/api/types/filters"
|
"github.com/docker/docker/api/types/filters"
|
||||||
"github.com/docker/docker/api/types/versions"
|
"github.com/docker/docker/api/types/versions"
|
||||||
|
"github.com/docker/docker/client"
|
||||||
"github.com/sirupsen/logrus"
|
"github.com/sirupsen/logrus"
|
||||||
)
|
)
|
||||||
|
|
||||||
func waitExitOrRemoved(ctx context.Context, dockerCli command.Cli, containerID string, waitRemove bool) <-chan int {
|
func waitExitOrRemoved(ctx context.Context, apiClient client.APIClient, containerID string, waitRemove bool) <-chan int {
|
||||||
if len(containerID) == 0 {
|
if len(containerID) == 0 {
|
||||||
// containerID can never be empty
|
// containerID can never be empty
|
||||||
panic("Internal Error: waitExitOrRemoved needs a containerID as parameter")
|
panic("Internal Error: waitExitOrRemoved needs a containerID as parameter")
|
||||||
|
@ -22,8 +22,8 @@ func waitExitOrRemoved(ctx context.Context, dockerCli command.Cli, containerID s
|
||||||
// Older versions used the Events API, and even older versions did not
|
// Older versions used the Events API, and even older versions did not
|
||||||
// support server-side removal. This legacyWaitExitOrRemoved method
|
// support server-side removal. This legacyWaitExitOrRemoved method
|
||||||
// preserves that old behavior and any issues it may have.
|
// preserves that old behavior and any issues it may have.
|
||||||
if versions.LessThan(dockerCli.Client().ClientVersion(), "1.30") {
|
if versions.LessThan(apiClient.ClientVersion(), "1.30") {
|
||||||
return legacyWaitExitOrRemoved(ctx, dockerCli, containerID, waitRemove)
|
return legacyWaitExitOrRemoved(ctx, apiClient, containerID, waitRemove)
|
||||||
}
|
}
|
||||||
|
|
||||||
condition := container.WaitConditionNextExit
|
condition := container.WaitConditionNextExit
|
||||||
|
@ -31,7 +31,7 @@ func waitExitOrRemoved(ctx context.Context, dockerCli command.Cli, containerID s
|
||||||
condition = container.WaitConditionRemoved
|
condition = container.WaitConditionRemoved
|
||||||
}
|
}
|
||||||
|
|
||||||
resultC, errC := dockerCli.Client().ContainerWait(ctx, containerID, condition)
|
resultC, errC := apiClient.ContainerWait(ctx, containerID, condition)
|
||||||
|
|
||||||
statusC := make(chan int)
|
statusC := make(chan int)
|
||||||
go func() {
|
go func() {
|
||||||
|
@ -52,7 +52,7 @@ func waitExitOrRemoved(ctx context.Context, dockerCli command.Cli, containerID s
|
||||||
return statusC
|
return statusC
|
||||||
}
|
}
|
||||||
|
|
||||||
func legacyWaitExitOrRemoved(ctx context.Context, dockerCli command.Cli, containerID string, waitRemove bool) <-chan int {
|
func legacyWaitExitOrRemoved(ctx context.Context, apiClient client.APIClient, containerID string, waitRemove bool) <-chan int {
|
||||||
var removeErr error
|
var removeErr error
|
||||||
statusChan := make(chan int)
|
statusChan := make(chan int)
|
||||||
exitCode := 125
|
exitCode := 125
|
||||||
|
@ -65,7 +65,7 @@ func legacyWaitExitOrRemoved(ctx context.Context, dockerCli command.Cli, contain
|
||||||
Filters: f,
|
Filters: f,
|
||||||
}
|
}
|
||||||
eventCtx, cancel := context.WithCancel(ctx)
|
eventCtx, cancel := context.WithCancel(ctx)
|
||||||
eventq, errq := dockerCli.Client().Events(eventCtx, options)
|
eventq, errq := apiClient.Events(eventCtx, options)
|
||||||
|
|
||||||
eventProcessor := func(e events.Message) bool {
|
eventProcessor := func(e events.Message) bool {
|
||||||
stopProcessing := false
|
stopProcessing := false
|
||||||
|
@ -84,9 +84,9 @@ func legacyWaitExitOrRemoved(ctx context.Context, dockerCli command.Cli, contain
|
||||||
} else {
|
} else {
|
||||||
// If we are talking to an older daemon, `AutoRemove` is not supported.
|
// If we are talking to an older daemon, `AutoRemove` is not supported.
|
||||||
// We need to fall back to the old behavior, which is client-side removal
|
// We need to fall back to the old behavior, which is client-side removal
|
||||||
if versions.LessThan(dockerCli.Client().ClientVersion(), "1.25") {
|
if versions.LessThan(apiClient.ClientVersion(), "1.25") {
|
||||||
go func() {
|
go func() {
|
||||||
removeErr = dockerCli.Client().ContainerRemove(ctx, containerID, types.ContainerRemoveOptions{RemoveVolumes: true})
|
removeErr = apiClient.ContainerRemove(ctx, containerID, types.ContainerRemoveOptions{RemoveVolumes: true})
|
||||||
if removeErr != nil {
|
if removeErr != nil {
|
||||||
logrus.Errorf("error removing container: %v", removeErr)
|
logrus.Errorf("error removing container: %v", removeErr)
|
||||||
cancel() // cancel the event Q
|
cancel() // cancel the event Q
|
||||||
|
|
|
@ -2,13 +2,12 @@ package container
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
|
"fmt"
|
||||||
"strings"
|
"strings"
|
||||||
"testing"
|
"testing"
|
||||||
|
|
||||||
"github.com/docker/cli/internal/test"
|
|
||||||
"github.com/docker/docker/api"
|
"github.com/docker/docker/api"
|
||||||
"github.com/docker/docker/api/types/container"
|
"github.com/docker/docker/api/types/container"
|
||||||
"github.com/pkg/errors"
|
|
||||||
"gotest.tools/v3/assert"
|
"gotest.tools/v3/assert"
|
||||||
is "gotest.tools/v3/assert/cmp"
|
is "gotest.tools/v3/assert/cmp"
|
||||||
)
|
)
|
||||||
|
@ -24,7 +23,7 @@ func waitFn(cid string) (<-chan container.WaitResponse, <-chan error) {
|
||||||
res.StatusCode = 42
|
res.StatusCode = 42
|
||||||
resC <- res
|
resC <- res
|
||||||
case strings.Contains(cid, "non-existent"):
|
case strings.Contains(cid, "non-existent"):
|
||||||
err := errors.Errorf("no such container: %v", cid)
|
err := fmt.Errorf("no such container: %v", cid)
|
||||||
errC <- err
|
errC <- err
|
||||||
case strings.Contains(cid, "wait-error"):
|
case strings.Contains(cid, "wait-error"):
|
||||||
res.Error = &container.WaitExitError{Message: "removal failed"}
|
res.Error = &container.WaitExitError{Message: "removal failed"}
|
||||||
|
@ -61,7 +60,7 @@ func TestWaitExitOrRemoved(t *testing.T) {
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
client := test.NewFakeCli(&fakeClient{waitFunc: waitFn, Version: api.DefaultVersion})
|
client := &fakeClient{waitFunc: waitFn, Version: api.DefaultVersion}
|
||||||
for _, testcase := range testcases {
|
for _, testcase := range testcases {
|
||||||
statusC := waitExitOrRemoved(context.Background(), client, testcase.cid, true)
|
statusC := waitExitOrRemoved(context.Background(), client, testcase.cid, true)
|
||||||
exitCode := <-statusC
|
exitCode := <-statusC
|
||||||
|
|
Loading…
Reference in New Issue