Signed-off-by: Daniel Nephin <dnephin@docker.com>
Daniel Nephin authored on 2017/08/23 06:07:52... | ... |
@@ -229,3 +229,11 @@ func WithStdout(writer io.Writer) func(*icmd.Cmd) func() { |
229 | 229 |
return nil |
230 | 230 |
} |
231 | 231 |
} |
232 |
+ |
|
233 |
+// WithStdin sets the standard input reader for the command |
|
234 |
+func WithStdin(stdin io.Reader) func(*icmd.Cmd) func() { |
|
235 |
+ return func(cmd *icmd.Cmd) func() { |
|
236 |
+ cmd.Stdin = stdin |
|
237 |
+ return nil |
|
238 |
+ } |
|
239 |
+} |
... | ... |
@@ -14,18 +14,20 @@ import ( |
14 | 14 |
"strings" |
15 | 15 |
"time" |
16 | 16 |
|
17 |
+ "github.com/docker/docker/api/types" |
|
17 | 18 |
"github.com/docker/docker/api/types/events" |
18 | 19 |
"github.com/docker/docker/integration-cli/checker" |
19 | 20 |
"github.com/docker/docker/integration-cli/request" |
20 | 21 |
"github.com/docker/docker/opts" |
21 | 22 |
"github.com/docker/docker/pkg/ioutils" |
22 | 23 |
"github.com/docker/docker/pkg/stringid" |
23 |
- "github.com/docker/docker/pkg/testutil" |
|
24 | 24 |
icmd "github.com/docker/docker/pkg/testutil/cmd" |
25 | 25 |
"github.com/docker/go-connections/sockets" |
26 | 26 |
"github.com/docker/go-connections/tlsconfig" |
27 | 27 |
"github.com/go-check/check" |
28 | 28 |
"github.com/pkg/errors" |
29 |
+ "github.com/stretchr/testify/require" |
|
30 |
+ "golang.org/x/net/context" |
|
29 | 31 |
) |
30 | 32 |
|
31 | 33 |
type testingT interface { |
... | ... |
@@ -570,20 +572,13 @@ func (d *Daemon) WaitRun(contID string) error { |
570 | 570 |
return WaitInspectWithArgs(d.dockerBinary, contID, "{{.State.Running}}", "true", 10*time.Second, args...) |
571 | 571 |
} |
572 | 572 |
|
573 |
-// GetBaseDeviceSize returns the base device size of the daemon |
|
574 |
-func (d *Daemon) GetBaseDeviceSize(c *check.C) int64 { |
|
575 |
- infoCmdOutput, _, err := testutil.RunCommandPipelineWithOutput( |
|
576 |
- exec.Command(d.dockerBinary, "-H", d.Sock(), "info"), |
|
577 |
- exec.Command("grep", "Base Device Size"), |
|
578 |
- ) |
|
579 |
- c.Assert(err, checker.IsNil) |
|
580 |
- basesizeSlice := strings.Split(infoCmdOutput, ":") |
|
581 |
- basesize := strings.Trim(basesizeSlice[1], " ") |
|
582 |
- basesize = strings.Trim(basesize, "\n")[:len(basesize)-3] |
|
583 |
- basesizeFloat, err := strconv.ParseFloat(strings.Trim(basesize, " "), 64) |
|
584 |
- c.Assert(err, checker.IsNil) |
|
585 |
- basesizeBytes := int64(basesizeFloat) * (1024 * 1024 * 1024) |
|
586 |
- return basesizeBytes |
|
573 |
+// Info returns the info struct for this daemon |
|
574 |
+func (d *Daemon) Info(t require.TestingT) types.Info { |
|
575 |
+ apiclient, err := request.NewClientForHost(d.Sock()) |
|
576 |
+ require.NoError(t, err) |
|
577 |
+ info, err := apiclient.Info(context.Background()) |
|
578 |
+ require.NoError(t, err) |
|
579 |
+ return info |
|
587 | 580 |
} |
588 | 581 |
|
589 | 582 |
// Cmd executes a docker CLI command against this daemon. |
... | ... |
@@ -11,7 +11,6 @@ import ( |
11 | 11 |
"strings" |
12 | 12 |
|
13 | 13 |
"github.com/docker/docker/integration-cli/checker" |
14 |
- "github.com/docker/docker/pkg/testutil" |
|
15 | 14 |
icmd "github.com/docker/docker/pkg/testutil/cmd" |
16 | 15 |
"github.com/go-check/check" |
17 | 16 |
) |
... | ... |
@@ -548,7 +547,7 @@ func (s *DockerSuite) TestCpToStdout(c *check.C) { |
548 | 548 |
// failed to set up container |
549 | 549 |
c.Assert(strings.TrimSpace(out), checker.Equals, "0") |
550 | 550 |
|
551 |
- out, _, err := testutil.RunCommandPipelineWithOutput( |
|
551 |
+ out, err := RunCommandPipelineWithOutput( |
|
552 | 552 |
exec.Command(dockerBinary, "cp", containerID+":/test", "-"), |
553 | 553 |
exec.Command("tar", "-vtf", "-")) |
554 | 554 |
|
... | ... |
@@ -201,7 +201,7 @@ func (s *DockerDaemonSuite) TestDaemonRestartWithInvalidBasesize(c *check.C) { |
201 | 201 |
testRequires(c, Devicemapper) |
202 | 202 |
s.d.Start(c) |
203 | 203 |
|
204 |
- oldBasesizeBytes := s.d.GetBaseDeviceSize(c) |
|
204 |
+ oldBasesizeBytes := getBaseDeviceSize(c, s.d) |
|
205 | 205 |
var newBasesizeBytes int64 = 1073741824 //1GB in bytes |
206 | 206 |
|
207 | 207 |
if newBasesizeBytes < oldBasesizeBytes { |
... | ... |
@@ -221,7 +221,7 @@ func (s *DockerDaemonSuite) TestDaemonRestartWithIncreasedBasesize(c *check.C) { |
221 | 221 |
testRequires(c, Devicemapper) |
222 | 222 |
s.d.Start(c) |
223 | 223 |
|
224 |
- oldBasesizeBytes := s.d.GetBaseDeviceSize(c) |
|
224 |
+ oldBasesizeBytes := getBaseDeviceSize(c, s.d) |
|
225 | 225 |
|
226 | 226 |
var newBasesizeBytes int64 = 53687091200 //50GB in bytes |
227 | 227 |
|
... | ... |
@@ -232,13 +232,31 @@ func (s *DockerDaemonSuite) TestDaemonRestartWithIncreasedBasesize(c *check.C) { |
232 | 232 |
err := s.d.RestartWithError("--storage-opt", fmt.Sprintf("dm.basesize=%d", newBasesizeBytes)) |
233 | 233 |
c.Assert(err, check.IsNil, check.Commentf("we should have been able to start the daemon with increased base device size: %v", err)) |
234 | 234 |
|
235 |
- basesizeAfterRestart := s.d.GetBaseDeviceSize(c) |
|
235 |
+ basesizeAfterRestart := getBaseDeviceSize(c, s.d) |
|
236 | 236 |
newBasesize, err := convertBasesize(newBasesizeBytes) |
237 | 237 |
c.Assert(err, check.IsNil, check.Commentf("Error in converting base device size: %v", err)) |
238 | 238 |
c.Assert(newBasesize, check.Equals, basesizeAfterRestart, check.Commentf("Basesize passed is not equal to Basesize set")) |
239 | 239 |
s.d.Stop(c) |
240 | 240 |
} |
241 | 241 |
|
242 |
+func getBaseDeviceSize(c *check.C, d *daemon.Daemon) int64 { |
|
243 |
+ info := d.Info(c) |
|
244 |
+ for _, statusLine := range info.DriverStatus { |
|
245 |
+ key, value := statusLine[0], statusLine[1] |
|
246 |
+ if key == "Base Device Size" { |
|
247 |
+ return parseDeviceSize(c, value) |
|
248 |
+ } |
|
249 |
+ } |
|
250 |
+ c.Fatal("failed to parse Base Device Size from info") |
|
251 |
+ return int64(0) |
|
252 |
+} |
|
253 |
+ |
|
254 |
+func parseDeviceSize(c *check.C, raw string) int64 { |
|
255 |
+ size, err := units.RAMInBytes(strings.TrimSpace(raw)) |
|
256 |
+ c.Assert(err, check.IsNil) |
|
257 |
+ return size |
|
258 |
+} |
|
259 |
+ |
|
242 | 260 |
func convertBasesize(basesizeBytes int64) (int64, error) { |
243 | 261 |
basesize := units.HumanSize(float64(basesizeBytes)) |
244 | 262 |
basesize = strings.Trim(basesize, " ")[:len(basesize)-3] |
... | ... |
@@ -18,7 +18,6 @@ import ( |
18 | 18 |
"github.com/docker/docker/integration-cli/cli" |
19 | 19 |
"github.com/docker/docker/integration-cli/cli/build" |
20 | 20 |
"github.com/docker/docker/integration-cli/request" |
21 |
- "github.com/docker/docker/pkg/testutil" |
|
22 | 21 |
icmd "github.com/docker/docker/pkg/testutil/cmd" |
23 | 22 |
"github.com/go-check/check" |
24 | 23 |
) |
... | ... |
@@ -230,7 +229,7 @@ func (s *DockerSuite) TestEventsImageImport(c *check.C) { |
230 | 230 |
cleanedContainerID := strings.TrimSpace(out) |
231 | 231 |
|
232 | 232 |
since := daemonUnixTime(c) |
233 |
- out, _, err := testutil.RunCommandPipelineWithOutput( |
|
233 |
+ out, err := RunCommandPipelineWithOutput( |
|
234 | 234 |
exec.Command(dockerBinary, "export", cleanedContainerID), |
235 | 235 |
exec.Command(dockerBinary, "import", "-"), |
236 | 236 |
) |
... | ... |
@@ -11,7 +11,6 @@ import ( |
11 | 11 |
|
12 | 12 |
"github.com/docker/docker/integration-cli/checker" |
13 | 13 |
"github.com/docker/docker/integration-cli/cli" |
14 |
- "github.com/docker/docker/pkg/testutil" |
|
15 | 14 |
icmd "github.com/docker/docker/pkg/testutil/cmd" |
16 | 15 |
"github.com/go-check/check" |
17 | 16 |
) |
... | ... |
@@ -21,7 +20,7 @@ func (s *DockerSuite) TestImportDisplay(c *check.C) { |
21 | 21 |
out, _ := dockerCmd(c, "run", "-d", "busybox", "true") |
22 | 22 |
cleanedContainerID := strings.TrimSpace(out) |
23 | 23 |
|
24 |
- out, _, err := testutil.RunCommandPipelineWithOutput( |
|
24 |
+ out, err := RunCommandPipelineWithOutput( |
|
25 | 25 |
exec.Command(dockerBinary, "export", cleanedContainerID), |
26 | 26 |
exec.Command(dockerBinary, "import", "-"), |
27 | 27 |
) |
... | ... |
@@ -17,7 +17,6 @@ import ( |
17 | 17 |
|
18 | 18 |
"github.com/docker/docker/integration-cli/checker" |
19 | 19 |
"github.com/docker/docker/integration-cli/cli/build" |
20 |
- "github.com/docker/docker/pkg/testutil" |
|
21 | 20 |
icmd "github.com/docker/docker/pkg/testutil/cmd" |
22 | 21 |
"github.com/go-check/check" |
23 | 22 |
digest "github.com/opencontainers/go-digest" |
... | ... |
@@ -34,7 +33,7 @@ func (s *DockerSuite) TestSaveXzAndLoadRepoStdout(c *check.C) { |
34 | 34 |
|
35 | 35 |
dockerCmd(c, "inspect", repoName) |
36 | 36 |
|
37 |
- repoTarball, _, err := testutil.RunCommandPipelineWithOutput( |
|
37 |
+ repoTarball, err := RunCommandPipelineWithOutput( |
|
38 | 38 |
exec.Command(dockerBinary, "save", repoName), |
39 | 39 |
exec.Command("xz", "-c"), |
40 | 40 |
exec.Command("gzip", "-c")) |
... | ... |
@@ -63,7 +62,7 @@ func (s *DockerSuite) TestSaveXzGzAndLoadRepoStdout(c *check.C) { |
63 | 63 |
|
64 | 64 |
dockerCmd(c, "inspect", repoName) |
65 | 65 |
|
66 |
- out, _, err := testutil.RunCommandPipelineWithOutput( |
|
66 |
+ out, err := RunCommandPipelineWithOutput( |
|
67 | 67 |
exec.Command(dockerBinary, "save", repoName), |
68 | 68 |
exec.Command("xz", "-c"), |
69 | 69 |
exec.Command("gzip", "-c")) |
... | ... |
@@ -90,7 +89,7 @@ func (s *DockerSuite) TestSaveSingleTag(c *check.C) { |
90 | 90 |
out, _ := dockerCmd(c, "images", "-q", "--no-trunc", repoName) |
91 | 91 |
cleanedImageID := strings.TrimSpace(out) |
92 | 92 |
|
93 |
- out, _, err := testutil.RunCommandPipelineWithOutput( |
|
93 |
+ out, err := RunCommandPipelineWithOutput( |
|
94 | 94 |
exec.Command(dockerBinary, "save", fmt.Sprintf("%v:latest", repoName)), |
95 | 95 |
exec.Command("tar", "t"), |
96 | 96 |
exec.Command("grep", "-E", fmt.Sprintf("(^repositories$|%v)", cleanedImageID))) |
... | ... |
@@ -109,7 +108,7 @@ func (s *DockerSuite) TestSaveCheckTimes(c *check.C) { |
109 | 109 |
c.Assert(err, checker.IsNil, check.Commentf("failed to marshal from %q: err %v", repoName, err)) |
110 | 110 |
c.Assert(len(data), checker.Not(checker.Equals), 0, check.Commentf("failed to marshal the data from %q", repoName)) |
111 | 111 |
tarTvTimeFormat := "2006-01-02 15:04" |
112 |
- out, _, err = testutil.RunCommandPipelineWithOutput( |
|
112 |
+ out, err = RunCommandPipelineWithOutput( |
|
113 | 113 |
exec.Command(dockerBinary, "save", repoName), |
114 | 114 |
exec.Command("tar", "tv"), |
115 | 115 |
exec.Command("grep", "-E", fmt.Sprintf("%s %s", data[0].Created.Format(tarTvTimeFormat), digest.Digest(data[0].ID).Hex()))) |
... | ... |
@@ -167,7 +166,7 @@ func (s *DockerSuite) TestSaveAndLoadRepoFlags(c *check.C) { |
167 | 167 |
|
168 | 168 |
before, _ := dockerCmd(c, "inspect", repoName) |
169 | 169 |
|
170 |
- out, _, err := testutil.RunCommandPipelineWithOutput( |
|
170 |
+ out, err := RunCommandPipelineWithOutput( |
|
171 | 171 |
exec.Command(dockerBinary, "save", repoName), |
172 | 172 |
exec.Command(dockerBinary, "load")) |
173 | 173 |
c.Assert(err, checker.IsNil, check.Commentf("failed to save and load repo: %s, %v", out, err)) |
... | ... |
@@ -196,7 +195,7 @@ func (s *DockerSuite) TestSaveMultipleNames(c *check.C) { |
196 | 196 |
// Make two images |
197 | 197 |
dockerCmd(c, "tag", "emptyfs:latest", fmt.Sprintf("%v-two:latest", repoName)) |
198 | 198 |
|
199 |
- out, _, err := testutil.RunCommandPipelineWithOutput( |
|
199 |
+ out, err := RunCommandPipelineWithOutput( |
|
200 | 200 |
exec.Command(dockerBinary, "save", fmt.Sprintf("%v-one", repoName), fmt.Sprintf("%v-two:latest", repoName)), |
201 | 201 |
exec.Command("tar", "xO", "repositories"), |
202 | 202 |
exec.Command("grep", "-q", "-E", "(-one|-two)"), |
... | ... |
@@ -228,7 +227,7 @@ func (s *DockerSuite) TestSaveRepoWithMultipleImages(c *check.C) { |
228 | 228 |
deleteImages(repoName) |
229 | 229 |
|
230 | 230 |
// create the archive |
231 |
- out, _, err := testutil.RunCommandPipelineWithOutput( |
|
231 |
+ out, err := RunCommandPipelineWithOutput( |
|
232 | 232 |
exec.Command(dockerBinary, "save", repoName, "busybox:latest"), |
233 | 233 |
exec.Command("tar", "t")) |
234 | 234 |
c.Assert(err, checker.IsNil, check.Commentf("failed to save multiple images: %s, %v", out, err)) |
... | ... |
@@ -272,7 +271,7 @@ func (s *DockerSuite) TestSaveDirectoryPermissions(c *check.C) { |
272 | 272 |
RUN adduser -D user && mkdir -p /opt/a/b && chown -R user:user /opt/a |
273 | 273 |
RUN touch /opt/a/b/c && chown user:user /opt/a/b/c`)) |
274 | 274 |
|
275 |
- out, _, err := testutil.RunCommandPipelineWithOutput( |
|
275 |
+ out, err := RunCommandPipelineWithOutput( |
|
276 | 276 |
exec.Command(dockerBinary, "save", name), |
277 | 277 |
exec.Command("tar", "-xf", "-", "-C", extractionDirectory), |
278 | 278 |
) |
... | ... |
@@ -384,7 +383,7 @@ func (s *DockerSuite) TestSaveLoadNoTag(c *check.C) { |
384 | 384 |
id := inspectField(c, name, "Id") |
385 | 385 |
|
386 | 386 |
// Test to make sure that save w/o name just shows imageID during load |
387 |
- out, _, err := testutil.RunCommandPipelineWithOutput( |
|
387 |
+ out, err := RunCommandPipelineWithOutput( |
|
388 | 388 |
exec.Command(dockerBinary, "save", id), |
389 | 389 |
exec.Command(dockerBinary, "load")) |
390 | 390 |
c.Assert(err, checker.IsNil, check.Commentf("failed to save and load repo: %s, %v", out, err)) |
... | ... |
@@ -395,7 +394,7 @@ func (s *DockerSuite) TestSaveLoadNoTag(c *check.C) { |
395 | 395 |
c.Assert(out, checker.Contains, id) |
396 | 396 |
|
397 | 397 |
// Test to make sure that save by name shows that name during load |
398 |
- out, _, err = testutil.RunCommandPipelineWithOutput( |
|
398 |
+ out, err = RunCommandPipelineWithOutput( |
|
399 | 399 |
exec.Command(dockerBinary, "save", name), |
400 | 400 |
exec.Command(dockerBinary, "load")) |
401 | 401 |
c.Assert(err, checker.IsNil, check.Commentf("failed to save and load repo: %s, %v", out, err)) |
... | ... |
@@ -12,7 +12,6 @@ import ( |
12 | 12 |
"net/http" |
13 | 13 |
"net/http/httptest" |
14 | 14 |
"os" |
15 |
- "os/exec" |
|
16 | 15 |
"path/filepath" |
17 | 16 |
"strings" |
18 | 17 |
"time" |
... | ... |
@@ -23,7 +22,6 @@ import ( |
23 | 23 |
"github.com/docker/docker/integration-cli/checker" |
24 | 24 |
"github.com/docker/docker/integration-cli/cli" |
25 | 25 |
"github.com/docker/docker/integration-cli/daemon" |
26 |
- "github.com/docker/docker/pkg/testutil" |
|
27 | 26 |
icmd "github.com/docker/docker/pkg/testutil/cmd" |
28 | 27 |
"github.com/docker/docker/pkg/testutil/tempfile" |
29 | 28 |
"github.com/docker/libnetwork/driverapi" |
... | ... |
@@ -467,14 +465,17 @@ func (s *DockerSwarmSuite) TestSwarmIngressNetwork(c *check.C) { |
467 | 467 |
d := s.AddDaemon(c, true, true) |
468 | 468 |
|
469 | 469 |
// Ingress network can be removed |
470 |
- out, _, err := testutil.RunCommandPipelineWithOutput( |
|
471 |
- exec.Command("echo", "Y"), |
|
472 |
- exec.Command("docker", "-H", d.Sock(), "network", "rm", "ingress"), |
|
473 |
- ) |
|
474 |
- c.Assert(err, checker.IsNil, check.Commentf(out)) |
|
470 |
+ removeNetwork := func(name string) *icmd.Result { |
|
471 |
+ return cli.Docker( |
|
472 |
+ cli.Args("-H", d.Sock(), "network", "rm", name), |
|
473 |
+ cli.WithStdin(strings.NewReader("Y"))) |
|
474 |
+ } |
|
475 |
+ |
|
476 |
+ result := removeNetwork("ingress") |
|
477 |
+ result.Assert(c, icmd.Success) |
|
475 | 478 |
|
476 | 479 |
// And recreated |
477 |
- out, err = d.Cmd("network", "create", "-d", "overlay", "--ingress", "new-ingress") |
|
480 |
+ out, err := d.Cmd("network", "create", "-d", "overlay", "--ingress", "new-ingress") |
|
478 | 481 |
c.Assert(err, checker.IsNil, check.Commentf(out)) |
479 | 482 |
|
480 | 483 |
// But only one is allowed |
... | ... |
@@ -485,21 +486,19 @@ func (s *DockerSwarmSuite) TestSwarmIngressNetwork(c *check.C) { |
485 | 485 |
// It cannot be removed if it is being used |
486 | 486 |
out, err = d.Cmd("service", "create", "--no-resolve-image", "--name", "srv1", "-p", "9000:8000", "busybox", "top") |
487 | 487 |
c.Assert(err, checker.IsNil, check.Commentf(out)) |
488 |
- out, _, err = testutil.RunCommandPipelineWithOutput( |
|
489 |
- exec.Command("echo", "Y"), |
|
490 |
- exec.Command("docker", "-H", d.Sock(), "network", "rm", "new-ingress"), |
|
491 |
- ) |
|
492 |
- c.Assert(err, checker.NotNil) |
|
493 |
- c.Assert(strings.TrimSpace(out), checker.Contains, "ingress network cannot be removed because service") |
|
488 |
+ |
|
489 |
+ result = removeNetwork("new-ingress") |
|
490 |
+ result.Assert(c, icmd.Expected{ |
|
491 |
+ ExitCode: 1, |
|
492 |
+ Err: "ingress network cannot be removed because service", |
|
493 |
+ }) |
|
494 | 494 |
|
495 | 495 |
// But it can be removed once no more services depend on it |
496 | 496 |
out, err = d.Cmd("service", "update", "--publish-rm", "9000:8000", "srv1") |
497 | 497 |
c.Assert(err, checker.IsNil, check.Commentf(out)) |
498 |
- out, _, err = testutil.RunCommandPipelineWithOutput( |
|
499 |
- exec.Command("echo", "Y"), |
|
500 |
- exec.Command("docker", "-H", d.Sock(), "network", "rm", "new-ingress"), |
|
501 |
- ) |
|
502 |
- c.Assert(err, checker.IsNil, check.Commentf(out)) |
|
498 |
+ |
|
499 |
+ result = removeNetwork("new-ingress") |
|
500 |
+ result.Assert(c, icmd.Success) |
|
503 | 501 |
|
504 | 502 |
// A service which needs the ingress network cannot be created if no ingress is present |
505 | 503 |
out, err = d.Cmd("service", "create", "--no-resolve-image", "--name", "srv2", "-p", "500:500", "busybox", "top") |
... | ... |
@@ -520,15 +519,14 @@ func (s *DockerSwarmSuite) TestSwarmCreateServiceWithNoIngressNetwork(c *check.C |
520 | 520 |
d := s.AddDaemon(c, true, true) |
521 | 521 |
|
522 | 522 |
// Remove ingress network |
523 |
- out, _, err := testutil.RunCommandPipelineWithOutput( |
|
524 |
- exec.Command("echo", "Y"), |
|
525 |
- exec.Command("docker", "-H", d.Sock(), "network", "rm", "ingress"), |
|
526 |
- ) |
|
527 |
- c.Assert(err, checker.IsNil, check.Commentf(out)) |
|
523 |
+ result := cli.Docker( |
|
524 |
+ cli.Args("-H", d.Sock(), "network", "rm", "ingress"), |
|
525 |
+ cli.WithStdin(strings.NewReader("Y"))) |
|
526 |
+ result.Assert(c, icmd.Success) |
|
528 | 527 |
|
529 | 528 |
// Create a overlay network and launch a service on it |
530 | 529 |
// Make sure nothing panics because ingress network is missing |
531 |
- out, err = d.Cmd("network", "create", "-d", "overlay", "another-network") |
|
530 |
+ out, err := d.Cmd("network", "create", "-d", "overlay", "another-network") |
|
532 | 531 |
c.Assert(err, checker.IsNil, check.Commentf(out)) |
533 | 532 |
out, err = d.Cmd("service", "create", "--no-resolve-image", "--name", "srv4", "--network", "another-network", "busybox", "top") |
534 | 533 |
c.Assert(err, checker.IsNil, check.Commentf(out)) |
... | ... |
@@ -15,7 +15,6 @@ import ( |
15 | 15 |
"github.com/docker/docker/integration-cli/checker" |
16 | 16 |
"github.com/docker/docker/pkg/stringid" |
17 | 17 |
"github.com/docker/docker/pkg/system" |
18 |
- "github.com/docker/docker/pkg/testutil" |
|
19 | 18 |
"github.com/go-check/check" |
20 | 19 |
) |
21 | 20 |
|
... | ... |
@@ -62,15 +61,15 @@ func (s *DockerDaemonSuite) TestDaemonUserNamespaceRootSetting(c *check.C) { |
62 | 62 |
c.Assert(err, checker.IsNil, check.Commentf("Could not inspect running container: out: %q", pid)) |
63 | 63 |
// check the uid and gid maps for the PID to ensure root is remapped |
64 | 64 |
// (cmd = cat /proc/<pid>/uid_map | grep -E '0\s+9999\s+1') |
65 |
- out, rc1, err := testutil.RunCommandPipelineWithOutput( |
|
65 |
+ out, err = RunCommandPipelineWithOutput( |
|
66 | 66 |
exec.Command("cat", "/proc/"+strings.TrimSpace(pid)+"/uid_map"), |
67 | 67 |
exec.Command("grep", "-E", fmt.Sprintf("0[[:space:]]+%d[[:space:]]+", uid))) |
68 |
- c.Assert(rc1, checker.Equals, 0, check.Commentf("Didn't match uid_map: output: %s", out)) |
|
68 |
+ c.Assert(err, check.IsNil) |
|
69 | 69 |
|
70 |
- out, rc2, err := testutil.RunCommandPipelineWithOutput( |
|
70 |
+ out, err = RunCommandPipelineWithOutput( |
|
71 | 71 |
exec.Command("cat", "/proc/"+strings.TrimSpace(pid)+"/gid_map"), |
72 | 72 |
exec.Command("grep", "-E", fmt.Sprintf("0[[:space:]]+%d[[:space:]]+", gid))) |
73 |
- c.Assert(rc2, checker.Equals, 0, check.Commentf("Didn't match gid_map: output: %s", out)) |
|
73 |
+ c.Assert(err, check.IsNil) |
|
74 | 74 |
|
75 | 75 |
// check that the touched file is owned by remapped uid:gid |
76 | 76 |
stat, err := system.Stat(filepath.Join(tmpDir, "testfile")) |
... | ... |
@@ -165,7 +165,11 @@ func NewHTTPClient(host string) (*http.Client, error) { |
165 | 165 |
|
166 | 166 |
// NewClient returns a new Docker API client |
167 | 167 |
func NewClient() (dclient.APIClient, error) { |
168 |
- host := DaemonHost() |
|
168 |
+ return NewClientForHost(DaemonHost()) |
|
169 |
+} |
|
170 |
+ |
|
171 |
+// NewClientForHost returns a Docker API client for the host |
|
172 |
+func NewClientForHost(host string) (dclient.APIClient, error) { |
|
169 | 173 |
httpClient, err := NewHTTPClient(host) |
170 | 174 |
if err != nil { |
171 | 175 |
return nil, err |
... | ... |
@@ -9,6 +9,7 @@ import ( |
9 | 9 |
|
10 | 10 |
"github.com/docker/docker/pkg/stringutils" |
11 | 11 |
"github.com/docker/docker/pkg/testutil/cmd" |
12 |
+ "github.com/pkg/errors" |
|
12 | 13 |
) |
13 | 14 |
|
14 | 15 |
func getPrefixAndSlashFromDaemonPlatform() (prefix, slash string) { |
... | ... |
@@ -64,3 +65,50 @@ func RandomTmpDirPath(s string, platform string) string { |
64 | 64 |
} |
65 | 65 |
return filepath.ToSlash(path) // Using / |
66 | 66 |
} |
67 |
+ |
|
68 |
+// RunCommandPipelineWithOutput runs the array of commands with the output |
|
69 |
+// of each pipelined with the following (like cmd1 | cmd2 | cmd3 would do). |
|
70 |
+// It returns the final output, the exitCode different from 0 and the error |
|
71 |
+// if something bad happened. |
|
72 |
+// Deprecated: use icmd instead |
|
73 |
+func RunCommandPipelineWithOutput(cmds ...*exec.Cmd) (output string, err error) { |
|
74 |
+ if len(cmds) < 2 { |
|
75 |
+ return "", errors.New("pipeline does not have multiple cmds") |
|
76 |
+ } |
|
77 |
+ |
|
78 |
+ // connect stdin of each cmd to stdout pipe of previous cmd |
|
79 |
+ for i, cmd := range cmds { |
|
80 |
+ if i > 0 { |
|
81 |
+ prevCmd := cmds[i-1] |
|
82 |
+ cmd.Stdin, err = prevCmd.StdoutPipe() |
|
83 |
+ |
|
84 |
+ if err != nil { |
|
85 |
+ return "", fmt.Errorf("cannot set stdout pipe for %s: %v", cmd.Path, err) |
|
86 |
+ } |
|
87 |
+ } |
|
88 |
+ } |
|
89 |
+ |
|
90 |
+ // start all cmds except the last |
|
91 |
+ for _, cmd := range cmds[:len(cmds)-1] { |
|
92 |
+ if err = cmd.Start(); err != nil { |
|
93 |
+ return "", fmt.Errorf("starting %s failed with error: %v", cmd.Path, err) |
|
94 |
+ } |
|
95 |
+ } |
|
96 |
+ |
|
97 |
+ defer func() { |
|
98 |
+ var pipeErrMsgs []string |
|
99 |
+ // wait all cmds except the last to release their resources |
|
100 |
+ for _, cmd := range cmds[:len(cmds)-1] { |
|
101 |
+ if pipeErr := cmd.Wait(); pipeErr != nil { |
|
102 |
+ pipeErrMsgs = append(pipeErrMsgs, fmt.Sprintf("command %s failed with error: %v", cmd.Path, pipeErr)) |
|
103 |
+ } |
|
104 |
+ } |
|
105 |
+ if len(pipeErrMsgs) > 0 && err == nil { |
|
106 |
+ err = fmt.Errorf("pipelineError from Wait: %v", strings.Join(pipeErrMsgs, ", ")) |
|
107 |
+ } |
|
108 |
+ }() |
|
109 |
+ |
|
110 |
+ // wait on last cmd |
|
111 |
+ out, err := cmds[len(cmds)-1].CombinedOutput() |
|
112 |
+ return string(out), err |
|
113 |
+} |
67 | 114 |
deleted file mode 100644 |
... | ... |
@@ -1,62 +0,0 @@ |
1 |
-package testutil |
|
2 |
- |
|
3 |
-import ( |
|
4 |
- "errors" |
|
5 |
- "fmt" |
|
6 |
- "os/exec" |
|
7 |
- "strings" |
|
8 |
- |
|
9 |
- "github.com/docker/docker/pkg/system" |
|
10 |
-) |
|
11 |
- |
|
12 |
-func runCommandWithOutput(cmd *exec.Cmd) (output string, exitCode int, err error) { |
|
13 |
- out, err := cmd.CombinedOutput() |
|
14 |
- exitCode = system.ProcessExitCode(err) |
|
15 |
- output = string(out) |
|
16 |
- return |
|
17 |
-} |
|
18 |
- |
|
19 |
-// RunCommandPipelineWithOutput runs the array of commands with the output |
|
20 |
-// of each pipelined with the following (like cmd1 | cmd2 | cmd3 would do). |
|
21 |
-// It returns the final output, the exitCode different from 0 and the error |
|
22 |
-// if something bad happened. |
|
23 |
-func RunCommandPipelineWithOutput(cmds ...*exec.Cmd) (output string, exitCode int, err error) { |
|
24 |
- if len(cmds) < 2 { |
|
25 |
- return "", 0, errors.New("pipeline does not have multiple cmds") |
|
26 |
- } |
|
27 |
- |
|
28 |
- // connect stdin of each cmd to stdout pipe of previous cmd |
|
29 |
- for i, cmd := range cmds { |
|
30 |
- if i > 0 { |
|
31 |
- prevCmd := cmds[i-1] |
|
32 |
- cmd.Stdin, err = prevCmd.StdoutPipe() |
|
33 |
- |
|
34 |
- if err != nil { |
|
35 |
- return "", 0, fmt.Errorf("cannot set stdout pipe for %s: %v", cmd.Path, err) |
|
36 |
- } |
|
37 |
- } |
|
38 |
- } |
|
39 |
- |
|
40 |
- // start all cmds except the last |
|
41 |
- for _, cmd := range cmds[:len(cmds)-1] { |
|
42 |
- if err = cmd.Start(); err != nil { |
|
43 |
- return "", 0, fmt.Errorf("starting %s failed with error: %v", cmd.Path, err) |
|
44 |
- } |
|
45 |
- } |
|
46 |
- |
|
47 |
- defer func() { |
|
48 |
- var pipeErrMsgs []string |
|
49 |
- // wait all cmds except the last to release their resources |
|
50 |
- for _, cmd := range cmds[:len(cmds)-1] { |
|
51 |
- if pipeErr := cmd.Wait(); pipeErr != nil { |
|
52 |
- pipeErrMsgs = append(pipeErrMsgs, fmt.Sprintf("command %s failed with error: %v", cmd.Path, pipeErr)) |
|
53 |
- } |
|
54 |
- } |
|
55 |
- if len(pipeErrMsgs) > 0 && err == nil { |
|
56 |
- err = fmt.Errorf("pipelineError from Wait: %v", strings.Join(pipeErrMsgs, ", ")) |
|
57 |
- } |
|
58 |
- }() |
|
59 |
- |
|
60 |
- // wait on last cmd |
|
61 |
- return runCommandWithOutput(cmds[len(cmds)-1]) |
|
62 |
-} |
63 | 1 |
deleted file mode 100644 |
... | ... |
@@ -1,55 +0,0 @@ |
1 |
-package testutil |
|
2 |
- |
|
3 |
-import ( |
|
4 |
- "os" |
|
5 |
- "os/exec" |
|
6 |
- "runtime" |
|
7 |
- "testing" |
|
8 |
-) |
|
9 |
- |
|
10 |
-func TestRunCommandPipelineWithOutputWithNotEnoughCmds(t *testing.T) { |
|
11 |
- _, _, err := RunCommandPipelineWithOutput(exec.Command("ls")) |
|
12 |
- expectedError := "pipeline does not have multiple cmds" |
|
13 |
- if err == nil || err.Error() != expectedError { |
|
14 |
- t.Fatalf("Expected an error with %s, got err:%s", expectedError, err) |
|
15 |
- } |
|
16 |
-} |
|
17 |
- |
|
18 |
-func TestRunCommandPipelineWithOutputErrors(t *testing.T) { |
|
19 |
- p := "$PATH" |
|
20 |
- if runtime.GOOS == "windows" { |
|
21 |
- p = "%PATH%" |
|
22 |
- } |
|
23 |
- cmd1 := exec.Command("ls") |
|
24 |
- cmd1.Stdout = os.Stdout |
|
25 |
- cmd2 := exec.Command("anything really") |
|
26 |
- _, _, err := RunCommandPipelineWithOutput(cmd1, cmd2) |
|
27 |
- if err == nil || err.Error() != "cannot set stdout pipe for anything really: exec: Stdout already set" { |
|
28 |
- t.Fatalf("Expected an error, got %v", err) |
|
29 |
- } |
|
30 |
- |
|
31 |
- cmdWithError := exec.Command("doesnotexists") |
|
32 |
- cmdCat := exec.Command("cat") |
|
33 |
- _, _, err = RunCommandPipelineWithOutput(cmdWithError, cmdCat) |
|
34 |
- if err == nil || err.Error() != `starting doesnotexists failed with error: exec: "doesnotexists": executable file not found in `+p { |
|
35 |
- t.Fatalf("Expected an error, got %v", err) |
|
36 |
- } |
|
37 |
-} |
|
38 |
- |
|
39 |
-func TestRunCommandPipelineWithOutput(t *testing.T) { |
|
40 |
- //TODO: Should run on Solaris |
|
41 |
- if runtime.GOOS == "solaris" { |
|
42 |
- t.Skip() |
|
43 |
- } |
|
44 |
- cmds := []*exec.Cmd{ |
|
45 |
- // Print 2 characters |
|
46 |
- exec.Command("echo", "-n", "11"), |
|
47 |
- // Count the number or char from stdin (previous command) |
|
48 |
- exec.Command("wc", "-m"), |
|
49 |
- } |
|
50 |
- out, exitCode, err := RunCommandPipelineWithOutput(cmds...) |
|
51 |
- expectedOutput := "2\n" |
|
52 |
- if out != expectedOutput || exitCode != 0 || err != nil { |
|
53 |
- t.Fatalf("Expected %s for commands %v, got out:%s, exitCode:%d, err:%v", expectedOutput, cmds, out, exitCode, err) |
|
54 |
- } |
|
55 |
-} |