github.com/rita33cool1/iot-system-gateway@v0.0.0-20200911033302-e65bde238cc5/docker-engine/integration-cli/docker_cli_ps_test.go (about) 1 package main 2 3 import ( 4 "fmt" 5 "sort" 6 "strconv" 7 "strings" 8 "time" 9 10 "github.com/docker/docker/integration-cli/checker" 11 "github.com/docker/docker/integration-cli/cli" 12 "github.com/docker/docker/integration-cli/cli/build" 13 "github.com/docker/docker/pkg/stringid" 14 "github.com/go-check/check" 15 "github.com/gotestyourself/gotestyourself/icmd" 16 ) 17 18 func (s *DockerSuite) TestPsListContainersBase(c *check.C) { 19 existingContainers := ExistingContainerIDs(c) 20 21 out := runSleepingContainer(c, "-d") 22 firstID := strings.TrimSpace(out) 23 24 out = runSleepingContainer(c, "-d") 25 secondID := strings.TrimSpace(out) 26 27 // not long running 28 out, _ = dockerCmd(c, "run", "-d", "busybox", "true") 29 thirdID := strings.TrimSpace(out) 30 31 out = runSleepingContainer(c, "-d") 32 fourthID := strings.TrimSpace(out) 33 34 // make sure the second is running 35 c.Assert(waitRun(secondID), checker.IsNil) 36 37 // make sure third one is not running 38 dockerCmd(c, "wait", thirdID) 39 40 // make sure the forth is running 41 c.Assert(waitRun(fourthID), checker.IsNil) 42 43 // all 44 out, _ = dockerCmd(c, "ps", "-a") 45 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), []string{fourthID, thirdID, secondID, firstID}), checker.Equals, true, check.Commentf("ALL: Container list is not in the correct order: \n%s", out)) 46 47 // running 48 out, _ = dockerCmd(c, "ps") 49 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), []string{fourthID, secondID, firstID}), checker.Equals, true, check.Commentf("RUNNING: Container list is not in the correct order: \n%s", out)) 50 51 // limit 52 out, _ = dockerCmd(c, "ps", "-n=2", "-a") 53 expected := []string{fourthID, thirdID} 54 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("LIMIT & ALL: Container list is not in the correct order: \n%s", out)) 55 56 out, _ = dockerCmd(c, "ps", "-n=2") 57 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("LIMIT: Container list is not in the correct order: \n%s", out)) 58 59 // filter since 60 out, _ = dockerCmd(c, "ps", "-f", "since="+firstID, "-a") 61 expected = []string{fourthID, thirdID, secondID} 62 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("SINCE filter & ALL: Container list is not in the correct order: \n%s", out)) 63 64 out, _ = dockerCmd(c, "ps", "-f", "since="+firstID) 65 expected = []string{fourthID, secondID} 66 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("SINCE filter: Container list is not in the correct order: \n%s", out)) 67 68 out, _ = dockerCmd(c, "ps", "-f", "since="+thirdID) 69 expected = []string{fourthID} 70 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("SINCE filter: Container list is not in the correct order: \n%s", out)) 71 72 // filter before 73 out, _ = dockerCmd(c, "ps", "-f", "before="+fourthID, "-a") 74 expected = []string{thirdID, secondID, firstID} 75 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("BEFORE filter & ALL: Container list is not in the correct order: \n%s", out)) 76 77 out, _ = dockerCmd(c, "ps", "-f", "before="+fourthID) 78 expected = []string{secondID, firstID} 79 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("BEFORE filter: Container list is not in the correct order: \n%s", out)) 80 81 out, _ = dockerCmd(c, "ps", "-f", "before="+thirdID) 82 expected = []string{secondID, firstID} 83 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("SINCE filter: Container list is not in the correct order: \n%s", out)) 84 85 // filter since & before 86 out, _ = dockerCmd(c, "ps", "-f", "since="+firstID, "-f", "before="+fourthID, "-a") 87 expected = []string{thirdID, secondID} 88 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("SINCE filter, BEFORE filter & ALL: Container list is not in the correct order: \n%s", out)) 89 90 out, _ = dockerCmd(c, "ps", "-f", "since="+firstID, "-f", "before="+fourthID) 91 expected = []string{secondID} 92 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("SINCE filter, BEFORE filter: Container list is not in the correct order: \n%s", out)) 93 94 // filter since & limit 95 out, _ = dockerCmd(c, "ps", "-f", "since="+firstID, "-n=2", "-a") 96 expected = []string{fourthID, thirdID} 97 98 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("SINCE filter, LIMIT & ALL: Container list is not in the correct order: \n%s", out)) 99 100 out, _ = dockerCmd(c, "ps", "-f", "since="+firstID, "-n=2") 101 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("SINCE filter, LIMIT: Container list is not in the correct order: \n%s", out)) 102 103 // filter before & limit 104 out, _ = dockerCmd(c, "ps", "-f", "before="+fourthID, "-n=1", "-a") 105 expected = []string{thirdID} 106 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("BEFORE filter, LIMIT & ALL: Container list is not in the correct order: \n%s", out)) 107 108 out, _ = dockerCmd(c, "ps", "-f", "before="+fourthID, "-n=1") 109 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("BEFORE filter, LIMIT: Container list is not in the correct order: \n%s", out)) 110 111 // filter since & filter before & limit 112 out, _ = dockerCmd(c, "ps", "-f", "since="+firstID, "-f", "before="+fourthID, "-n=1", "-a") 113 expected = []string{thirdID} 114 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("SINCE filter, BEFORE filter, LIMIT & ALL: Container list is not in the correct order: \n%s", out)) 115 116 out, _ = dockerCmd(c, "ps", "-f", "since="+firstID, "-f", "before="+fourthID, "-n=1") 117 c.Assert(assertContainerList(RemoveOutputForExistingElements(out, existingContainers), expected), checker.Equals, true, check.Commentf("SINCE filter, BEFORE filter, LIMIT: Container list is not in the correct order: \n%s", out)) 118 119 } 120 121 func assertContainerList(out string, expected []string) bool { 122 lines := strings.Split(strings.Trim(out, "\n "), "\n") 123 124 if len(lines)-1 != len(expected) { 125 return false 126 } 127 128 containerIDIndex := strings.Index(lines[0], "CONTAINER ID") 129 for i := 0; i < len(expected); i++ { 130 foundID := lines[i+1][containerIDIndex : containerIDIndex+12] 131 if foundID != expected[i][:12] { 132 return false 133 } 134 } 135 136 return true 137 } 138 139 func (s *DockerSuite) TestPsListContainersSize(c *check.C) { 140 // Problematic on Windows as it doesn't report the size correctly @swernli 141 testRequires(c, DaemonIsLinux) 142 dockerCmd(c, "run", "-d", "busybox") 143 144 baseOut, _ := dockerCmd(c, "ps", "-s", "-n=1") 145 baseLines := strings.Split(strings.Trim(baseOut, "\n "), "\n") 146 baseSizeIndex := strings.Index(baseLines[0], "SIZE") 147 baseFoundsize := baseLines[1][baseSizeIndex:] 148 baseBytes, err := strconv.Atoi(strings.Split(baseFoundsize, "B")[0]) 149 c.Assert(err, checker.IsNil) 150 151 name := "test_size" 152 dockerCmd(c, "run", "--name", name, "busybox", "sh", "-c", "echo 1 > test") 153 id := getIDByName(c, name) 154 155 var result *icmd.Result 156 157 wait := make(chan struct{}) 158 go func() { 159 result = icmd.RunCommand(dockerBinary, "ps", "-s", "-n=1") 160 close(wait) 161 }() 162 select { 163 case <-wait: 164 case <-time.After(3 * time.Second): 165 c.Fatalf("Calling \"docker ps -s\" timed out!") 166 } 167 result.Assert(c, icmd.Success) 168 lines := strings.Split(strings.Trim(result.Combined(), "\n "), "\n") 169 c.Assert(lines, checker.HasLen, 2, check.Commentf("Expected 2 lines for 'ps -s -n=1' output, got %d", len(lines))) 170 sizeIndex := strings.Index(lines[0], "SIZE") 171 idIndex := strings.Index(lines[0], "CONTAINER ID") 172 foundID := lines[1][idIndex : idIndex+12] 173 c.Assert(foundID, checker.Equals, id[:12], check.Commentf("Expected id %s, got %s", id[:12], foundID)) 174 expectedSize := fmt.Sprintf("%dB", (2 + baseBytes)) 175 foundSize := lines[1][sizeIndex:] 176 c.Assert(foundSize, checker.Contains, expectedSize, check.Commentf("Expected size %q, got %q", expectedSize, foundSize)) 177 } 178 179 func (s *DockerSuite) TestPsListContainersFilterStatus(c *check.C) { 180 existingContainers := ExistingContainerIDs(c) 181 182 // start exited container 183 out := cli.DockerCmd(c, "run", "-d", "busybox").Combined() 184 firstID := strings.TrimSpace(out) 185 186 // make sure the exited container is not running 187 cli.DockerCmd(c, "wait", firstID) 188 189 // start running container 190 out = cli.DockerCmd(c, "run", "-itd", "busybox").Combined() 191 secondID := strings.TrimSpace(out) 192 193 // filter containers by exited 194 out = cli.DockerCmd(c, "ps", "--no-trunc", "-q", "--filter=status=exited").Combined() 195 containerOut := strings.TrimSpace(out) 196 c.Assert(RemoveOutputForExistingElements(containerOut, existingContainers), checker.Equals, firstID) 197 198 out = cli.DockerCmd(c, "ps", "-a", "--no-trunc", "-q", "--filter=status=running").Combined() 199 containerOut = strings.TrimSpace(out) 200 c.Assert(RemoveOutputForExistingElements(containerOut, existingContainers), checker.Equals, secondID) 201 202 result := cli.Docker(cli.Args("ps", "-a", "-q", "--filter=status=rubbish"), cli.WithTimeout(time.Second*60)) 203 result.Assert(c, icmd.Expected{ 204 ExitCode: 1, 205 Err: "Invalid filter 'status=rubbish'", 206 }) 207 208 // Windows doesn't support pausing of containers 209 if testEnv.OSType != "windows" { 210 // pause running container 211 out = cli.DockerCmd(c, "run", "-itd", "busybox").Combined() 212 pausedID := strings.TrimSpace(out) 213 cli.DockerCmd(c, "pause", pausedID) 214 // make sure the container is unpaused to let the daemon stop it properly 215 defer func() { cli.DockerCmd(c, "unpause", pausedID) }() 216 217 out = cli.DockerCmd(c, "ps", "--no-trunc", "-q", "--filter=status=paused").Combined() 218 containerOut = strings.TrimSpace(out) 219 c.Assert(RemoveOutputForExistingElements(containerOut, existingContainers), checker.Equals, pausedID) 220 } 221 } 222 223 func (s *DockerSuite) TestPsListContainersFilterHealth(c *check.C) { 224 existingContainers := ExistingContainerIDs(c) 225 // Test legacy no health check 226 out := runSleepingContainer(c, "--name=none_legacy") 227 containerID := strings.TrimSpace(out) 228 229 cli.WaitRun(c, containerID) 230 231 out = cli.DockerCmd(c, "ps", "-q", "-l", "--no-trunc", "--filter=health=none").Combined() 232 containerOut := strings.TrimSpace(out) 233 c.Assert(containerOut, checker.Equals, containerID, check.Commentf("Expected id %s, got %s for legacy none filter, output: %q", containerID, containerOut, out)) 234 235 // Test no health check specified explicitly 236 out = runSleepingContainer(c, "--name=none", "--no-healthcheck") 237 containerID = strings.TrimSpace(out) 238 239 cli.WaitRun(c, containerID) 240 241 out = cli.DockerCmd(c, "ps", "-q", "-l", "--no-trunc", "--filter=health=none").Combined() 242 containerOut = strings.TrimSpace(out) 243 c.Assert(containerOut, checker.Equals, containerID, check.Commentf("Expected id %s, got %s for none filter, output: %q", containerID, containerOut, out)) 244 245 // Test failing health check 246 out = runSleepingContainer(c, "--name=failing_container", "--health-cmd=exit 1", "--health-interval=1s") 247 containerID = strings.TrimSpace(out) 248 249 waitForHealthStatus(c, "failing_container", "starting", "unhealthy") 250 251 out = cli.DockerCmd(c, "ps", "-q", "--no-trunc", "--filter=health=unhealthy").Combined() 252 containerOut = strings.TrimSpace(out) 253 c.Assert(containerOut, checker.Equals, containerID, check.Commentf("Expected containerID %s, got %s for unhealthy filter, output: %q", containerID, containerOut, out)) 254 255 // Check passing healthcheck 256 out = runSleepingContainer(c, "--name=passing_container", "--health-cmd=exit 0", "--health-interval=1s") 257 containerID = strings.TrimSpace(out) 258 259 waitForHealthStatus(c, "passing_container", "starting", "healthy") 260 261 out = cli.DockerCmd(c, "ps", "-q", "--no-trunc", "--filter=health=healthy").Combined() 262 containerOut = strings.TrimSpace(RemoveOutputForExistingElements(out, existingContainers)) 263 c.Assert(containerOut, checker.Equals, containerID, check.Commentf("Expected containerID %s, got %s for healthy filter, output: %q", containerID, containerOut, out)) 264 } 265 266 func (s *DockerSuite) TestPsListContainersFilterID(c *check.C) { 267 // start container 268 out, _ := dockerCmd(c, "run", "-d", "busybox") 269 firstID := strings.TrimSpace(out) 270 271 // start another container 272 runSleepingContainer(c) 273 274 // filter containers by id 275 out, _ = dockerCmd(c, "ps", "-a", "-q", "--filter=id="+firstID) 276 containerOut := strings.TrimSpace(out) 277 c.Assert(containerOut, checker.Equals, firstID[:12], check.Commentf("Expected id %s, got %s for exited filter, output: %q", firstID[:12], containerOut, out)) 278 } 279 280 func (s *DockerSuite) TestPsListContainersFilterName(c *check.C) { 281 // start container 282 dockerCmd(c, "run", "--name=a_name_to_match", "busybox") 283 id := getIDByName(c, "a_name_to_match") 284 285 // start another container 286 runSleepingContainer(c, "--name=b_name_to_match") 287 288 // filter containers by name 289 out, _ := dockerCmd(c, "ps", "-a", "-q", "--filter=name=a_name_to_match") 290 containerOut := strings.TrimSpace(out) 291 c.Assert(containerOut, checker.Equals, id[:12], check.Commentf("Expected id %s, got %s for exited filter, output: %q", id[:12], containerOut, out)) 292 } 293 294 // Test for the ancestor filter for ps. 295 // There is also the same test but with image:tag@digest in docker_cli_by_digest_test.go 296 // 297 // What the test setups : 298 // - Create 2 image based on busybox using the same repository but different tags 299 // - Create an image based on the previous image (images_ps_filter_test2) 300 // - Run containers for each of those image (busybox, images_ps_filter_test1, images_ps_filter_test2) 301 // - Filter them out :P 302 func (s *DockerSuite) TestPsListContainersFilterAncestorImage(c *check.C) { 303 existingContainers := ExistingContainerIDs(c) 304 305 // Build images 306 imageName1 := "images_ps_filter_test1" 307 buildImageSuccessfully(c, imageName1, build.WithDockerfile(`FROM busybox 308 LABEL match me 1`)) 309 imageID1 := getIDByName(c, imageName1) 310 311 imageName1Tagged := "images_ps_filter_test1:tag" 312 buildImageSuccessfully(c, imageName1Tagged, build.WithDockerfile(`FROM busybox 313 LABEL match me 1 tagged`)) 314 imageID1Tagged := getIDByName(c, imageName1Tagged) 315 316 imageName2 := "images_ps_filter_test2" 317 buildImageSuccessfully(c, imageName2, build.WithDockerfile(fmt.Sprintf(`FROM %s 318 LABEL match me 2`, imageName1))) 319 imageID2 := getIDByName(c, imageName2) 320 321 // start containers 322 dockerCmd(c, "run", "--name=first", "busybox", "echo", "hello") 323 firstID := getIDByName(c, "first") 324 325 // start another container 326 dockerCmd(c, "run", "--name=second", "busybox", "echo", "hello") 327 secondID := getIDByName(c, "second") 328 329 // start third container 330 dockerCmd(c, "run", "--name=third", imageName1, "echo", "hello") 331 thirdID := getIDByName(c, "third") 332 333 // start fourth container 334 dockerCmd(c, "run", "--name=fourth", imageName1Tagged, "echo", "hello") 335 fourthID := getIDByName(c, "fourth") 336 337 // start fifth container 338 dockerCmd(c, "run", "--name=fifth", imageName2, "echo", "hello") 339 fifthID := getIDByName(c, "fifth") 340 341 var filterTestSuite = []struct { 342 filterName string 343 expectedIDs []string 344 }{ 345 // non existent stuff 346 {"nonexistent", []string{}}, 347 {"nonexistent:tag", []string{}}, 348 // image 349 {"busybox", []string{firstID, secondID, thirdID, fourthID, fifthID}}, 350 {imageName1, []string{thirdID, fifthID}}, 351 {imageName2, []string{fifthID}}, 352 // image:tag 353 {fmt.Sprintf("%s:latest", imageName1), []string{thirdID, fifthID}}, 354 {imageName1Tagged, []string{fourthID}}, 355 // short-id 356 {stringid.TruncateID(imageID1), []string{thirdID, fifthID}}, 357 {stringid.TruncateID(imageID2), []string{fifthID}}, 358 // full-id 359 {imageID1, []string{thirdID, fifthID}}, 360 {imageID1Tagged, []string{fourthID}}, 361 {imageID2, []string{fifthID}}, 362 } 363 364 var out string 365 for _, filter := range filterTestSuite { 366 out, _ = dockerCmd(c, "ps", "-a", "-q", "--no-trunc", "--filter=ancestor="+filter.filterName) 367 checkPsAncestorFilterOutput(c, RemoveOutputForExistingElements(out, existingContainers), filter.filterName, filter.expectedIDs) 368 } 369 370 // Multiple ancestor filter 371 out, _ = dockerCmd(c, "ps", "-a", "-q", "--no-trunc", "--filter=ancestor="+imageName2, "--filter=ancestor="+imageName1Tagged) 372 checkPsAncestorFilterOutput(c, RemoveOutputForExistingElements(out, existingContainers), imageName2+","+imageName1Tagged, []string{fourthID, fifthID}) 373 } 374 375 func checkPsAncestorFilterOutput(c *check.C, out string, filterName string, expectedIDs []string) { 376 actualIDs := []string{} 377 if out != "" { 378 actualIDs = strings.Split(out[:len(out)-1], "\n") 379 } 380 sort.Strings(actualIDs) 381 sort.Strings(expectedIDs) 382 383 c.Assert(actualIDs, checker.HasLen, len(expectedIDs), check.Commentf("Expected filtered container(s) for %s ancestor filter to be %v:%v, got %v:%v", filterName, len(expectedIDs), expectedIDs, len(actualIDs), actualIDs)) 384 if len(expectedIDs) > 0 { 385 same := true 386 for i := range expectedIDs { 387 if actualIDs[i] != expectedIDs[i] { 388 c.Logf("%s, %s", actualIDs[i], expectedIDs[i]) 389 same = false 390 break 391 } 392 } 393 c.Assert(same, checker.Equals, true, check.Commentf("Expected filtered container(s) for %s ancestor filter to be %v, got %v", filterName, expectedIDs, actualIDs)) 394 } 395 } 396 397 func (s *DockerSuite) TestPsListContainersFilterLabel(c *check.C) { 398 // start container 399 dockerCmd(c, "run", "--name=first", "-l", "match=me", "-l", "second=tag", "busybox") 400 firstID := getIDByName(c, "first") 401 402 // start another container 403 dockerCmd(c, "run", "--name=second", "-l", "match=me too", "busybox") 404 secondID := getIDByName(c, "second") 405 406 // start third container 407 dockerCmd(c, "run", "--name=third", "-l", "nomatch=me", "busybox") 408 thirdID := getIDByName(c, "third") 409 410 // filter containers by exact match 411 out, _ := dockerCmd(c, "ps", "-a", "-q", "--no-trunc", "--filter=label=match=me") 412 containerOut := strings.TrimSpace(out) 413 c.Assert(containerOut, checker.Equals, firstID, check.Commentf("Expected id %s, got %s for exited filter, output: %q", firstID, containerOut, out)) 414 415 // filter containers by two labels 416 out, _ = dockerCmd(c, "ps", "-a", "-q", "--no-trunc", "--filter=label=match=me", "--filter=label=second=tag") 417 containerOut = strings.TrimSpace(out) 418 c.Assert(containerOut, checker.Equals, firstID, check.Commentf("Expected id %s, got %s for exited filter, output: %q", firstID, containerOut, out)) 419 420 // filter containers by two labels, but expect not found because of AND behavior 421 out, _ = dockerCmd(c, "ps", "-a", "-q", "--no-trunc", "--filter=label=match=me", "--filter=label=second=tag-no") 422 containerOut = strings.TrimSpace(out) 423 c.Assert(containerOut, checker.Equals, "", check.Commentf("Expected nothing, got %s for exited filter, output: %q", containerOut, out)) 424 425 // filter containers by exact key 426 out, _ = dockerCmd(c, "ps", "-a", "-q", "--no-trunc", "--filter=label=match") 427 containerOut = strings.TrimSpace(out) 428 c.Assert(containerOut, checker.Contains, firstID) 429 c.Assert(containerOut, checker.Contains, secondID) 430 c.Assert(containerOut, checker.Not(checker.Contains), thirdID) 431 } 432 433 func (s *DockerSuite) TestPsListContainersFilterExited(c *check.C) { 434 runSleepingContainer(c, "--name=sleep") 435 436 dockerCmd(c, "run", "--name", "zero1", "busybox", "true") 437 firstZero := getIDByName(c, "zero1") 438 439 dockerCmd(c, "run", "--name", "zero2", "busybox", "true") 440 secondZero := getIDByName(c, "zero2") 441 442 out, _, err := dockerCmdWithError("run", "--name", "nonzero1", "busybox", "false") 443 c.Assert(err, checker.NotNil, check.Commentf("Should fail.", out, err)) 444 445 firstNonZero := getIDByName(c, "nonzero1") 446 447 out, _, err = dockerCmdWithError("run", "--name", "nonzero2", "busybox", "false") 448 c.Assert(err, checker.NotNil, check.Commentf("Should fail.", out, err)) 449 secondNonZero := getIDByName(c, "nonzero2") 450 451 // filter containers by exited=0 452 out, _ = dockerCmd(c, "ps", "-a", "-q", "--no-trunc", "--filter=exited=0") 453 ids := strings.Split(strings.TrimSpace(out), "\n") 454 c.Assert(ids, checker.HasLen, 2, check.Commentf("Should be 2 zero exited containers got %d: %s", len(ids), out)) 455 c.Assert(ids[0], checker.Equals, secondZero, check.Commentf("First in list should be %q, got %q", secondZero, ids[0])) 456 c.Assert(ids[1], checker.Equals, firstZero, check.Commentf("Second in list should be %q, got %q", firstZero, ids[1])) 457 458 out, _ = dockerCmd(c, "ps", "-a", "-q", "--no-trunc", "--filter=exited=1") 459 ids = strings.Split(strings.TrimSpace(out), "\n") 460 c.Assert(ids, checker.HasLen, 2, check.Commentf("Should be 2 zero exited containers got %d", len(ids))) 461 c.Assert(ids[0], checker.Equals, secondNonZero, check.Commentf("First in list should be %q, got %q", secondNonZero, ids[0])) 462 c.Assert(ids[1], checker.Equals, firstNonZero, check.Commentf("Second in list should be %q, got %q", firstNonZero, ids[1])) 463 464 } 465 466 func (s *DockerSuite) TestPsRightTagName(c *check.C) { 467 // TODO Investigate further why this fails on Windows to Windows CI 468 testRequires(c, DaemonIsLinux) 469 470 existingContainers := ExistingContainerNames(c) 471 472 tag := "asybox:shmatest" 473 dockerCmd(c, "tag", "busybox", tag) 474 475 var id1 string 476 out := runSleepingContainer(c) 477 id1 = strings.TrimSpace(string(out)) 478 479 var id2 string 480 out = runSleepingContainerInImage(c, tag) 481 id2 = strings.TrimSpace(string(out)) 482 483 var imageID string 484 out = inspectField(c, "busybox", "Id") 485 imageID = strings.TrimSpace(string(out)) 486 487 var id3 string 488 out = runSleepingContainerInImage(c, imageID) 489 id3 = strings.TrimSpace(string(out)) 490 491 out, _ = dockerCmd(c, "ps", "--no-trunc") 492 lines := strings.Split(strings.TrimSpace(string(out)), "\n") 493 lines = RemoveLinesForExistingElements(lines, existingContainers) 494 // skip header 495 lines = lines[1:] 496 c.Assert(lines, checker.HasLen, 3, check.Commentf("There should be 3 running container, got %d", len(lines))) 497 for _, line := range lines { 498 f := strings.Fields(line) 499 switch f[0] { 500 case id1: 501 c.Assert(f[1], checker.Equals, "busybox", check.Commentf("Expected %s tag for id %s, got %s", "busybox", id1, f[1])) 502 case id2: 503 c.Assert(f[1], checker.Equals, tag, check.Commentf("Expected %s tag for id %s, got %s", tag, id2, f[1])) 504 case id3: 505 c.Assert(f[1], checker.Equals, imageID, check.Commentf("Expected %s imageID for id %s, got %s", tag, id3, f[1])) 506 default: 507 c.Fatalf("Unexpected id %s, expected %s and %s and %s", f[0], id1, id2, id3) 508 } 509 } 510 } 511 512 func (s *DockerSuite) TestPsListContainersFilterCreated(c *check.C) { 513 // create a container 514 out, _ := dockerCmd(c, "create", "busybox") 515 cID := strings.TrimSpace(out) 516 shortCID := cID[:12] 517 518 // Make sure it DOESN'T show up w/o a '-a' for normal 'ps' 519 out, _ = dockerCmd(c, "ps", "-q") 520 c.Assert(out, checker.Not(checker.Contains), shortCID, check.Commentf("Should have not seen '%s' in ps output:\n%s", shortCID, out)) 521 522 // Make sure it DOES show up as 'Created' for 'ps -a' 523 out, _ = dockerCmd(c, "ps", "-a") 524 525 hits := 0 526 for _, line := range strings.Split(out, "\n") { 527 if !strings.Contains(line, shortCID) { 528 continue 529 } 530 hits++ 531 c.Assert(line, checker.Contains, "Created", check.Commentf("Missing 'Created' on '%s'", line)) 532 } 533 534 c.Assert(hits, checker.Equals, 1, check.Commentf("Should have seen '%s' in ps -a output once:%d\n%s", shortCID, hits, out)) 535 536 // filter containers by 'create' - note, no -a needed 537 out, _ = dockerCmd(c, "ps", "-q", "-f", "status=created") 538 containerOut := strings.TrimSpace(out) 539 c.Assert(cID, checker.HasPrefix, containerOut) 540 } 541 542 // Test for GitHub issue #12595 543 func (s *DockerSuite) TestPsImageIDAfterUpdate(c *check.C) { 544 // TODO: Investigate why this fails on Windows to Windows CI further. 545 testRequires(c, DaemonIsLinux) 546 originalImageName := "busybox:TestPsImageIDAfterUpdate-original" 547 updatedImageName := "busybox:TestPsImageIDAfterUpdate-updated" 548 549 existingContainers := ExistingContainerIDs(c) 550 551 icmd.RunCommand(dockerBinary, "tag", "busybox:latest", originalImageName).Assert(c, icmd.Success) 552 553 originalImageID := getIDByName(c, originalImageName) 554 555 result := icmd.RunCommand(dockerBinary, append([]string{"run", "-d", originalImageName}, sleepCommandForDaemonPlatform()...)...) 556 result.Assert(c, icmd.Success) 557 containerID := strings.TrimSpace(result.Combined()) 558 559 result = icmd.RunCommand(dockerBinary, "ps", "--no-trunc") 560 result.Assert(c, icmd.Success) 561 562 lines := strings.Split(strings.TrimSpace(string(result.Combined())), "\n") 563 lines = RemoveLinesForExistingElements(lines, existingContainers) 564 // skip header 565 lines = lines[1:] 566 c.Assert(len(lines), checker.Equals, 1) 567 568 for _, line := range lines { 569 f := strings.Fields(line) 570 c.Assert(f[1], checker.Equals, originalImageName) 571 } 572 573 icmd.RunCommand(dockerBinary, "commit", containerID, updatedImageName).Assert(c, icmd.Success) 574 icmd.RunCommand(dockerBinary, "tag", updatedImageName, originalImageName).Assert(c, icmd.Success) 575 576 result = icmd.RunCommand(dockerBinary, "ps", "--no-trunc") 577 result.Assert(c, icmd.Success) 578 579 lines = strings.Split(strings.TrimSpace(string(result.Combined())), "\n") 580 lines = RemoveLinesForExistingElements(lines, existingContainers) 581 // skip header 582 lines = lines[1:] 583 c.Assert(len(lines), checker.Equals, 1) 584 585 for _, line := range lines { 586 f := strings.Fields(line) 587 c.Assert(f[1], checker.Equals, originalImageID) 588 } 589 590 } 591 592 func (s *DockerSuite) TestPsNotShowPortsOfStoppedContainer(c *check.C) { 593 testRequires(c, DaemonIsLinux) 594 dockerCmd(c, "run", "--name=foo", "-d", "-p", "5000:5000", "busybox", "top") 595 c.Assert(waitRun("foo"), checker.IsNil) 596 out, _ := dockerCmd(c, "ps") 597 lines := strings.Split(strings.TrimSpace(string(out)), "\n") 598 expected := "0.0.0.0:5000->5000/tcp" 599 fields := strings.Fields(lines[1]) 600 c.Assert(fields[len(fields)-2], checker.Equals, expected, check.Commentf("Expected: %v, got: %v", expected, fields[len(fields)-2])) 601 602 dockerCmd(c, "kill", "foo") 603 dockerCmd(c, "wait", "foo") 604 out, _ = dockerCmd(c, "ps", "-l") 605 lines = strings.Split(strings.TrimSpace(string(out)), "\n") 606 fields = strings.Fields(lines[1]) 607 c.Assert(fields[len(fields)-2], checker.Not(checker.Equals), expected, check.Commentf("Should not got %v", expected)) 608 } 609 610 func (s *DockerSuite) TestPsShowMounts(c *check.C) { 611 existingContainers := ExistingContainerNames(c) 612 613 prefix, slash := getPrefixAndSlashFromDaemonPlatform() 614 615 mp := prefix + slash + "test" 616 617 dockerCmd(c, "volume", "create", "ps-volume-test") 618 // volume mount containers 619 runSleepingContainer(c, "--name=volume-test-1", "--volume", "ps-volume-test:"+mp) 620 c.Assert(waitRun("volume-test-1"), checker.IsNil) 621 runSleepingContainer(c, "--name=volume-test-2", "--volume", mp) 622 c.Assert(waitRun("volume-test-2"), checker.IsNil) 623 // bind mount container 624 var bindMountSource string 625 var bindMountDestination string 626 if DaemonIsWindows() { 627 bindMountSource = "c:\\" 628 bindMountDestination = "c:\\t" 629 } else { 630 bindMountSource = "/tmp" 631 bindMountDestination = "/t" 632 } 633 runSleepingContainer(c, "--name=bind-mount-test", "-v", bindMountSource+":"+bindMountDestination) 634 c.Assert(waitRun("bind-mount-test"), checker.IsNil) 635 636 out, _ := dockerCmd(c, "ps", "--format", "{{.Names}} {{.Mounts}}") 637 638 lines := strings.Split(strings.TrimSpace(string(out)), "\n") 639 lines = RemoveLinesForExistingElements(lines, existingContainers) 640 c.Assert(lines, checker.HasLen, 3) 641 642 fields := strings.Fields(lines[0]) 643 c.Assert(fields, checker.HasLen, 2) 644 c.Assert(fields[0], checker.Equals, "bind-mount-test") 645 c.Assert(fields[1], checker.Equals, bindMountSource) 646 647 fields = strings.Fields(lines[1]) 648 c.Assert(fields, checker.HasLen, 2) 649 650 anonymousVolumeID := fields[1] 651 652 fields = strings.Fields(lines[2]) 653 c.Assert(fields[1], checker.Equals, "ps-volume-test") 654 655 // filter by volume name 656 out, _ = dockerCmd(c, "ps", "--format", "{{.Names}} {{.Mounts}}", "--filter", "volume=ps-volume-test") 657 658 lines = strings.Split(strings.TrimSpace(string(out)), "\n") 659 lines = RemoveLinesForExistingElements(lines, existingContainers) 660 c.Assert(lines, checker.HasLen, 1) 661 662 fields = strings.Fields(lines[0]) 663 c.Assert(fields[1], checker.Equals, "ps-volume-test") 664 665 // empty results filtering by unknown volume 666 out, _ = dockerCmd(c, "ps", "--format", "{{.Names}} {{.Mounts}}", "--filter", "volume=this-volume-should-not-exist") 667 c.Assert(strings.TrimSpace(string(out)), checker.HasLen, 0) 668 669 // filter by mount destination 670 out, _ = dockerCmd(c, "ps", "--format", "{{.Names}} {{.Mounts}}", "--filter", "volume="+mp) 671 672 lines = strings.Split(strings.TrimSpace(string(out)), "\n") 673 lines = RemoveLinesForExistingElements(lines, existingContainers) 674 c.Assert(lines, checker.HasLen, 2) 675 676 fields = strings.Fields(lines[0]) 677 c.Assert(fields[1], checker.Equals, anonymousVolumeID) 678 fields = strings.Fields(lines[1]) 679 c.Assert(fields[1], checker.Equals, "ps-volume-test") 680 681 // filter by bind mount source 682 out, _ = dockerCmd(c, "ps", "--format", "{{.Names}} {{.Mounts}}", "--filter", "volume="+bindMountSource) 683 684 lines = strings.Split(strings.TrimSpace(string(out)), "\n") 685 lines = RemoveLinesForExistingElements(lines, existingContainers) 686 c.Assert(lines, checker.HasLen, 1) 687 688 fields = strings.Fields(lines[0]) 689 c.Assert(fields, checker.HasLen, 2) 690 c.Assert(fields[0], checker.Equals, "bind-mount-test") 691 c.Assert(fields[1], checker.Equals, bindMountSource) 692 693 // filter by bind mount destination 694 out, _ = dockerCmd(c, "ps", "--format", "{{.Names}} {{.Mounts}}", "--filter", "volume="+bindMountDestination) 695 696 lines = strings.Split(strings.TrimSpace(string(out)), "\n") 697 lines = RemoveLinesForExistingElements(lines, existingContainers) 698 c.Assert(lines, checker.HasLen, 1) 699 700 fields = strings.Fields(lines[0]) 701 c.Assert(fields, checker.HasLen, 2) 702 c.Assert(fields[0], checker.Equals, "bind-mount-test") 703 c.Assert(fields[1], checker.Equals, bindMountSource) 704 705 // empty results filtering by unknown mount point 706 out, _ = dockerCmd(c, "ps", "--format", "{{.Names}} {{.Mounts}}", "--filter", "volume="+prefix+slash+"this-path-was-never-mounted") 707 c.Assert(strings.TrimSpace(string(out)), checker.HasLen, 0) 708 } 709 710 func (s *DockerSuite) TestPsListContainersFilterNetwork(c *check.C) { 711 existing := ExistingContainerIDs(c) 712 713 // TODO default network on Windows is not called "bridge", and creating a 714 // custom network fails on Windows fails with "Error response from daemon: plugin not found") 715 testRequires(c, DaemonIsLinux) 716 717 // create some containers 718 runSleepingContainer(c, "--net=bridge", "--name=onbridgenetwork") 719 runSleepingContainer(c, "--net=none", "--name=onnonenetwork") 720 721 // Filter docker ps on non existing network 722 out, _ := dockerCmd(c, "ps", "--filter", "network=doesnotexist") 723 containerOut := strings.TrimSpace(string(out)) 724 lines := strings.Split(containerOut, "\n") 725 726 // skip header 727 lines = lines[1:] 728 729 // ps output should have no containers 730 c.Assert(RemoveLinesForExistingElements(lines, existing), checker.HasLen, 0) 731 732 // Filter docker ps on network bridge 733 out, _ = dockerCmd(c, "ps", "--filter", "network=bridge") 734 containerOut = strings.TrimSpace(string(out)) 735 736 lines = strings.Split(containerOut, "\n") 737 738 // skip header 739 lines = lines[1:] 740 741 // ps output should have only one container 742 c.Assert(RemoveLinesForExistingElements(lines, existing), checker.HasLen, 1) 743 744 // Making sure onbridgenetwork is on the output 745 c.Assert(containerOut, checker.Contains, "onbridgenetwork", check.Commentf("Missing the container on network\n")) 746 747 // Filter docker ps on networks bridge and none 748 out, _ = dockerCmd(c, "ps", "--filter", "network=bridge", "--filter", "network=none") 749 containerOut = strings.TrimSpace(string(out)) 750 751 lines = strings.Split(containerOut, "\n") 752 753 // skip header 754 lines = lines[1:] 755 756 //ps output should have both the containers 757 c.Assert(RemoveLinesForExistingElements(lines, existing), checker.HasLen, 2) 758 759 // Making sure onbridgenetwork and onnonenetwork is on the output 760 c.Assert(containerOut, checker.Contains, "onnonenetwork", check.Commentf("Missing the container on none network\n")) 761 c.Assert(containerOut, checker.Contains, "onbridgenetwork", check.Commentf("Missing the container on bridge network\n")) 762 763 nwID, _ := dockerCmd(c, "network", "inspect", "--format", "{{.ID}}", "bridge") 764 765 // Filter by network ID 766 out, _ = dockerCmd(c, "ps", "--filter", "network="+nwID) 767 containerOut = strings.TrimSpace(string(out)) 768 769 c.Assert(containerOut, checker.Contains, "onbridgenetwork") 770 771 // Filter by partial network ID 772 partialnwID := string(nwID[0:4]) 773 774 out, _ = dockerCmd(c, "ps", "--filter", "network="+partialnwID) 775 containerOut = strings.TrimSpace(string(out)) 776 777 lines = strings.Split(containerOut, "\n") 778 779 // skip header 780 lines = lines[1:] 781 782 // ps output should have only one container 783 c.Assert(RemoveLinesForExistingElements(lines, existing), checker.HasLen, 1) 784 785 // Making sure onbridgenetwork is on the output 786 c.Assert(containerOut, checker.Contains, "onbridgenetwork", check.Commentf("Missing the container on network\n")) 787 788 } 789 790 func (s *DockerSuite) TestPsByOrder(c *check.C) { 791 name1 := "xyz-abc" 792 out := runSleepingContainer(c, "--name", name1) 793 container1 := strings.TrimSpace(out) 794 795 name2 := "xyz-123" 796 out = runSleepingContainer(c, "--name", name2) 797 container2 := strings.TrimSpace(out) 798 799 name3 := "789-abc" 800 out = runSleepingContainer(c, "--name", name3) 801 802 name4 := "789-123" 803 out = runSleepingContainer(c, "--name", name4) 804 805 // Run multiple time should have the same result 806 out = cli.DockerCmd(c, "ps", "--no-trunc", "-q", "-f", "name=xyz").Combined() 807 c.Assert(strings.TrimSpace(out), checker.Equals, fmt.Sprintf("%s\n%s", container2, container1)) 808 809 // Run multiple time should have the same result 810 out = cli.DockerCmd(c, "ps", "--no-trunc", "-q", "-f", "name=xyz").Combined() 811 c.Assert(strings.TrimSpace(out), checker.Equals, fmt.Sprintf("%s\n%s", container2, container1)) 812 } 813 814 func (s *DockerSuite) TestPsListContainersFilterPorts(c *check.C) { 815 testRequires(c, DaemonIsLinux) 816 existingContainers := ExistingContainerIDs(c) 817 818 out, _ := dockerCmd(c, "run", "-d", "--publish=80", "busybox", "top") 819 id1 := strings.TrimSpace(out) 820 821 out, _ = dockerCmd(c, "run", "-d", "--expose=8080", "busybox", "top") 822 id2 := strings.TrimSpace(out) 823 824 out, _ = dockerCmd(c, "ps", "--no-trunc", "-q") 825 c.Assert(strings.TrimSpace(out), checker.Contains, id1) 826 c.Assert(strings.TrimSpace(out), checker.Contains, id2) 827 828 out, _ = dockerCmd(c, "ps", "--no-trunc", "-q", "--filter", "publish=80-8080/udp") 829 c.Assert(strings.TrimSpace(out), checker.Not(checker.Equals), id1) 830 c.Assert(strings.TrimSpace(out), checker.Not(checker.Equals), id2) 831 832 out, _ = dockerCmd(c, "ps", "--no-trunc", "-q", "--filter", "expose=8081") 833 c.Assert(strings.TrimSpace(out), checker.Not(checker.Equals), id1) 834 c.Assert(strings.TrimSpace(out), checker.Not(checker.Equals), id2) 835 836 out, _ = dockerCmd(c, "ps", "--no-trunc", "-q", "--filter", "publish=80-81") 837 c.Assert(strings.TrimSpace(out), checker.Equals, id1) 838 c.Assert(strings.TrimSpace(out), checker.Not(checker.Equals), id2) 839 840 out, _ = dockerCmd(c, "ps", "--no-trunc", "-q", "--filter", "expose=80/tcp") 841 c.Assert(strings.TrimSpace(out), checker.Equals, id1) 842 c.Assert(strings.TrimSpace(out), checker.Not(checker.Equals), id2) 843 844 out, _ = dockerCmd(c, "ps", "--no-trunc", "-q", "--filter", "expose=8080/tcp") 845 out = RemoveOutputForExistingElements(out, existingContainers) 846 c.Assert(strings.TrimSpace(out), checker.Not(checker.Equals), id1) 847 c.Assert(strings.TrimSpace(out), checker.Equals, id2) 848 } 849 850 func (s *DockerSuite) TestPsNotShowLinknamesOfDeletedContainer(c *check.C) { 851 testRequires(c, DaemonIsLinux) 852 853 existingContainers := ExistingContainerNames(c) 854 855 dockerCmd(c, "create", "--name=aaa", "busybox", "top") 856 dockerCmd(c, "create", "--name=bbb", "--link=aaa", "busybox", "top") 857 858 out, _ := dockerCmd(c, "ps", "--no-trunc", "-a", "--format", "{{.Names}}") 859 lines := strings.Split(strings.TrimSpace(string(out)), "\n") 860 lines = RemoveLinesForExistingElements(lines, existingContainers) 861 expected := []string{"bbb", "aaa,bbb/aaa"} 862 var names []string 863 names = append(names, lines...) 864 c.Assert(expected, checker.DeepEquals, names, check.Commentf("Expected array with non-truncated names: %v, got: %v", expected, names)) 865 866 dockerCmd(c, "rm", "bbb") 867 868 out, _ = dockerCmd(c, "ps", "--no-trunc", "-a", "--format", "{{.Names}}") 869 out = RemoveOutputForExistingElements(out, existingContainers) 870 c.Assert(strings.TrimSpace(out), checker.Equals, "aaa") 871 }