From 4327e9ba24c9cc5d6ddb126cd043dedc1564d76f Mon Sep 17 00:00:00 2001 From: Hugues Alary Date: Thu, 8 Aug 2019 17:54:37 -0700 Subject: [PATCH] Resolve relative paths to absolute paths in command line arguments The executor accepts a few arguments dockerfile, context, cache-dir and digest-file that all represent paths. This commits allows those paths to be relative to the working directory of the executor. Fixes #732 #731 #675 --- cmd/executor/cmd/root.go | 34 +++++++++++++++++++++++++++++++++ integration/images.go | 30 +++++++++++++++++++++++++++++ integration/integration_test.go | 24 +++++++++++++++++++++++ 3 files changed, 88 insertions(+) diff --git a/cmd/executor/cmd/root.go b/cmd/executor/cmd/root.go index 0dd717f86..cdeb7b389 100644 --- a/cmd/executor/cmd/root.go +++ b/cmd/executor/cmd/root.go @@ -81,6 +81,9 @@ var RootCmd = &cobra.Command{ if err := executor.CheckPushPermissions(opts); err != nil { exit(errors.Wrap(err, "error checking push permissions -- make sure you entered the correct tag name, and that you are authenticated correctly, and try again")) } + if err := resolveRelativePaths(); err != nil { + exit(errors.Wrap(err, "error resolving relative paths to absolute paths")) + } if err := os.Chdir("/"); err != nil { exit(errors.Wrap(err, "error changing to root dir")) } @@ -227,6 +230,37 @@ func resolveSourceContext() error { return nil } +func resolveRelativePaths() error { + optsPaths := []*string{ + &opts.DockerfilePath, + &opts.SrcContext, + &opts.CacheDir, + &opts.TarPath, + &opts.DigestFile, + } + + for _, p := range optsPaths { + // Skip empty path + if *p == "" { + continue + } + // Skip path that is already absolute + if filepath.IsAbs(*p) { + logrus.Debugf("Path %s is absolute, skipping", *p) + continue + } + + // Resolve relative path to absolute path + var err error + relp := *p // save original relative path + if *p, err = filepath.Abs(*p); err != nil { + return errors.Wrapf(err, "Couldn't resolve relative path %s to an absolute path", *p) + } + logrus.Debugf("Resolved relative path %s to %s", relp, *p) + } + return nil +} + func exit(err error) { fmt.Println(err) os.Exit(1) diff --git a/integration/images.go b/integration/images.go index 4f7f3b8bc..a9847aef8 100644 --- a/integration/images.go +++ b/integration/images.go @@ -286,3 +286,33 @@ func (d *DockerFileBuilder) buildCachedImages(imageRepo, cacheRepo, dockerfilesP } return nil } + +// buildRelativePathsImage builds the images for testing passing relatives paths to Kaniko +func (d *DockerFileBuilder) buildRelativePathsImage(imageRepo, dockerfile string) error { + _, ex, _, _ := runtime.Caller(0) + cwd := filepath.Dir(ex) + + buildContextPath := "./relative-subdirectory" + kanikoImage := GetKanikoImage(imageRepo, dockerfile) + + kanikoCmd := exec.Command("docker", + append([]string{"run", + "-v", os.Getenv("HOME") + "/.config/gcloud:/root/.config/gcloud", + "-v", cwd + ":/workspace", + ExecutorImage, + "-f", dockerfile, + "-d", kanikoImage, + "--digest-file", "./digest", + "-c", buildContextPath, + })..., + ) + + timer := timing.Start(dockerfile + "_kaniko_relative_paths") + _, err := RunCommandWithoutTest(kanikoCmd) + timing.DefaultRun.Stop(timer) + if err != nil { + return fmt.Errorf("Failed to build relative path image %s with kaniko command \"%s\": %s", kanikoImage, kanikoCmd.Args, err) + } + + return nil +} diff --git a/integration/integration_test.go b/integration/integration_test.go index fcd6246f9..628da94fe 100644 --- a/integration/integration_test.go +++ b/integration/integration_test.go @@ -386,6 +386,30 @@ func TestCache(t *testing.T) { } } +func TestRelativePaths(t *testing.T) { + + dockerfile := "Dockerfile_test_copy" + + t.Run("test_relative_"+dockerfile, func(t *testing.T) { + t.Parallel() + imageBuilder.buildRelativePathsImage(config.imageRepo, dockerfile) + + dockerImage := GetDockerImage(config.imageRepo, dockerfile) + kanikoImage := GetKanikoImage(config.imageRepo, dockerfile) + + // container-diff + daemonDockerImage := daemonPrefix + dockerImage + containerdiffCmd := exec.Command("container-diff", "diff", "--no-cache", + daemonDockerImage, kanikoImage, + "-q", "--type=file", "--type=metadata", "--json") + diff := RunCommand(containerdiffCmd, t) + t.Logf("diff = %s", string(diff)) + + expected := fmt.Sprintf(emptyContainerDiff, dockerImage, kanikoImage, dockerImage, kanikoImage) + checkContainerDiffOutput(t, diff, expected) + }) +} + type fileDiff struct { Name string Size int