github.com/ssdev-go/moby@v17.12.1-ce-rc2+incompatible/client/container_wait.go (about) 1 package client 2 3 import ( 4 "encoding/json" 5 "net/url" 6 7 "golang.org/x/net/context" 8 9 "github.com/docker/docker/api/types/container" 10 "github.com/docker/docker/api/types/versions" 11 ) 12 13 // ContainerWait waits until the specified container is in a certain state 14 // indicated by the given condition, either "not-running" (default), 15 // "next-exit", or "removed". 16 // 17 // If this client's API version is before 1.30, condition is ignored and 18 // ContainerWait will return immediately with the two channels, as the server 19 // will wait as if the condition were "not-running". 20 // 21 // If this client's API version is at least 1.30, ContainerWait blocks until 22 // the request has been acknowledged by the server (with a response header), 23 // then returns two channels on which the caller can wait for the exit status 24 // of the container or an error if there was a problem either beginning the 25 // wait request or in getting the response. This allows the caller to 26 // synchronize ContainerWait with other calls, such as specifying a 27 // "next-exit" condition before issuing a ContainerStart request. 28 func (cli *Client) ContainerWait(ctx context.Context, containerID string, condition container.WaitCondition) (<-chan container.ContainerWaitOKBody, <-chan error) { 29 if versions.LessThan(cli.ClientVersion(), "1.30") { 30 return cli.legacyContainerWait(ctx, containerID) 31 } 32 33 resultC := make(chan container.ContainerWaitOKBody) 34 errC := make(chan error, 1) 35 36 query := url.Values{} 37 query.Set("condition", string(condition)) 38 39 resp, err := cli.post(ctx, "/containers/"+containerID+"/wait", query, nil, nil) 40 if err != nil { 41 defer ensureReaderClosed(resp) 42 errC <- err 43 return resultC, errC 44 } 45 46 go func() { 47 defer ensureReaderClosed(resp) 48 var res container.ContainerWaitOKBody 49 if err := json.NewDecoder(resp.body).Decode(&res); err != nil { 50 errC <- err 51 return 52 } 53 54 resultC <- res 55 }() 56 57 return resultC, errC 58 } 59 60 // legacyContainerWait returns immediately and doesn't have an option to wait 61 // until the container is removed. 62 func (cli *Client) legacyContainerWait(ctx context.Context, containerID string) (<-chan container.ContainerWaitOKBody, <-chan error) { 63 resultC := make(chan container.ContainerWaitOKBody) 64 errC := make(chan error) 65 66 go func() { 67 resp, err := cli.post(ctx, "/containers/"+containerID+"/wait", nil, nil, nil) 68 if err != nil { 69 errC <- err 70 return 71 } 72 defer ensureReaderClosed(resp) 73 74 var res container.ContainerWaitOKBody 75 if err := json.NewDecoder(resp.body).Decode(&res); err != nil { 76 errC <- err 77 return 78 } 79 80 resultC <- res 81 }() 82 83 return resultC, errC 84 }