From 4b8e680bcc4864020effe46560a57098e0dc4c35 Mon Sep 17 00:00:00 2001 From: Tonis Tiigi Date: Thu, 22 Sep 2016 14:32:17 -0700 Subject: [PATCH] =?UTF-8?q?Add=20integration=20test=20for=20build=20?= =?UTF-8?q?=E2=80=94cache-from?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Tonis Tiigi --- integration-cli/docker_cli_build_test.go | 93 ++++++++++++++++++++++++ 1 file changed, 93 insertions(+) diff --git a/integration-cli/docker_cli_build_test.go b/integration-cli/docker_cli_build_test.go index 51daa22007..a624b9c3f3 100644 --- a/integration-cli/docker_cli_build_test.go +++ b/integration-cli/docker_cli_build_test.go @@ -6931,3 +6931,96 @@ func (s *DockerSuite) TestBuildWithFailure(c *check.C) { c.Assert(stdout, checker.Not(checker.Contains), "Step 1/2 : FROM busybox") c.Assert(stdout, checker.Not(checker.Contains), "Step 2/2 : RUN nobody") } + +func (s *DockerSuite) TestBuildCacheFrom(c *check.C) { + testRequires(c, DaemonIsLinux) // All tests that do save are skipped in windows + dockerfile := ` + FROM busybox + ENV FOO=bar + ADD baz / + RUN touch bax` + ctx, err := fakeContext(dockerfile, map[string]string{ + "Dockerfile": dockerfile, + "baz": "baz", + }) + c.Assert(err, checker.IsNil) + defer ctx.Close() + + id1, err := buildImageFromContext("build1", ctx, true) + c.Assert(err, checker.IsNil) + + // rebuild with cache-from + id2, out, err := buildImageFromContextWithOut("build2", ctx, true, "--cache-from=build1") + c.Assert(err, checker.IsNil) + c.Assert(id1, checker.Equals, id2) + c.Assert(strings.Count(out, "Using cache"), checker.Equals, 3) + dockerCmd(c, "rmi", "build2") + + // no cache match with unknown source + id2, out, err = buildImageFromContextWithOut("build2", ctx, true, "--cache-from=nosuchtag") + c.Assert(err, checker.IsNil) + c.Assert(id1, checker.Not(checker.Equals), id2) + c.Assert(strings.Count(out, "Using cache"), checker.Equals, 0) + dockerCmd(c, "rmi", "build2") + + // clear parent images + tempDir, err := ioutil.TempDir("", "test-build-cache-from-") + if err != nil { + c.Fatalf("failed to create temporary directory: %s", tempDir) + } + defer os.RemoveAll(tempDir) + tempFile := filepath.Join(tempDir, "img.tar") + dockerCmd(c, "save", "-o", tempFile, "build1") + dockerCmd(c, "rmi", "build1") + dockerCmd(c, "load", "-i", tempFile) + parentID, _ := dockerCmd(c, "inspect", "-f", "{{.Parent}}", "build1") + c.Assert(strings.TrimSpace(parentID), checker.Equals, "") + + // cache still applies without parents + id2, out, err = buildImageFromContextWithOut("build2", ctx, true, "--cache-from=build1") + c.Assert(err, checker.IsNil) + c.Assert(id1, checker.Equals, id2) + c.Assert(strings.Count(out, "Using cache"), checker.Equals, 3) + history1, _ := dockerCmd(c, "history", "-q", "build2") + + // Retry, no new intermediate images + id3, out, err := buildImageFromContextWithOut("build3", ctx, true, "--cache-from=build1") + c.Assert(err, checker.IsNil) + c.Assert(id1, checker.Equals, id3) + c.Assert(strings.Count(out, "Using cache"), checker.Equals, 3) + history2, _ := dockerCmd(c, "history", "-q", "build3") + + c.Assert(history1, checker.Equals, history2) + dockerCmd(c, "rmi", "build2") + dockerCmd(c, "rmi", "build3") + dockerCmd(c, "rmi", "build1") + dockerCmd(c, "load", "-i", tempFile) + + // Modify file, everything up to last command and layers are reused + dockerfile = ` + FROM busybox + ENV FOO=bar + ADD baz / + RUN touch newfile` + err = ioutil.WriteFile(filepath.Join(ctx.Dir, "Dockerfile"), []byte(dockerfile), 0644) + c.Assert(err, checker.IsNil) + + id2, out, err = buildImageFromContextWithOut("build2", ctx, true, "--cache-from=build1") + c.Assert(err, checker.IsNil) + c.Assert(id1, checker.Not(checker.Equals), id2) + c.Assert(strings.Count(out, "Using cache"), checker.Equals, 2) + + layers1Str, _ := dockerCmd(c, "inspect", "-f", "{{json .RootFS.Layers}}", "build1") + layers2Str, _ := dockerCmd(c, "inspect", "-f", "{{json .RootFS.Layers}}", "build2") + + var layers1 []string + var layers2 []string + c.Assert(json.Unmarshal([]byte(layers1Str), &layers1), checker.IsNil) + c.Assert(json.Unmarshal([]byte(layers2Str), &layers2), checker.IsNil) + + c.Assert(len(layers1), checker.Equals, len(layers2)) + for i := 0; i < len(layers1)-1; i++ { + c.Assert(layers1[i], checker.Equals, layers2[i]) + } + c.Assert(layers1[len(layers1)-1], checker.Not(checker.Equals), layers2[len(layers1)-1]) +}