github.com/GoogleContainerTools/skaffold@v1.39.18/pkg/skaffold/build/jib/gradle_test.go (about)

     1  /*
     2  Copyright 2019 The Skaffold Authors
     3  
     4  Licensed under the Apache License, Version 2.0 (the "License");
     5  you may not use this file except in compliance with the License.
     6  You may obtain a copy of the License at
     7  
     8      http://www.apache.org/licenses/LICENSE-2.0
     9  
    10  Unless required by applicable law or agreed to in writing, software
    11  distributed under the License is distributed on an "AS IS" BASIS,
    12  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13  See the License for the specific language governing permissions and
    14  limitations under the License.
    15  */
    16  
    17  package jib
    18  
    19  import (
    20  	"context"
    21  	"errors"
    22  	"fmt"
    23  	"io/ioutil"
    24  	"os"
    25  	"os/exec"
    26  	"runtime"
    27  	"strings"
    28  	"testing"
    29  	"time"
    30  
    31  	v1 "github.com/opencontainers/image-spec/specs-go/v1"
    32  
    33  	"github.com/GoogleContainerTools/skaffold/pkg/skaffold/docker"
    34  	"github.com/GoogleContainerTools/skaffold/pkg/skaffold/platform"
    35  	"github.com/GoogleContainerTools/skaffold/pkg/skaffold/schema/latest"
    36  	"github.com/GoogleContainerTools/skaffold/pkg/skaffold/util"
    37  	"github.com/GoogleContainerTools/skaffold/testutil"
    38  )
    39  
    40  func TestBuildJibGradleToDocker(t *testing.T) {
    41  	tests := []struct {
    42  		description   string
    43  		artifact      *latest.JibArtifact
    44  		commands      util.Command
    45  		shouldErr     bool
    46  		expectedError string
    47  	}{
    48  		{
    49  			description: "build",
    50  			artifact:    &latest.JibArtifact{},
    51  			commands: testutil.CmdRun(
    52  				"gradle fake-gradleBuildArgs-for-jibDockerBuild --image=img:tag",
    53  			),
    54  		},
    55  		{
    56  			description: "build with project",
    57  			artifact:    &latest.JibArtifact{Project: "project"},
    58  			commands: testutil.CmdRun(
    59  				"gradle fake-gradleBuildArgs-for-project-for-jibDockerBuild --image=img:tag",
    60  			),
    61  		},
    62  		{
    63  			description: "build with custom base image",
    64  			artifact:    &latest.JibArtifact{BaseImage: "docker://busybox"},
    65  			commands: testutil.CmdRun(
    66  				"gradle fake-gradleBuildArgs-for-jibDockerBuild -Djib.from.image=docker://busybox --image=img:tag",
    67  			),
    68  		},
    69  		{
    70  			description: "fail build",
    71  			artifact:    &latest.JibArtifact{},
    72  			commands: testutil.CmdRunErr(
    73  				"gradle fake-gradleBuildArgs-for-jibDockerBuild --image=img:tag",
    74  				errors.New("BUG"),
    75  			),
    76  			shouldErr:     true,
    77  			expectedError: "gradle build failed",
    78  		},
    79  	}
    80  
    81  	for _, test := range tests {
    82  		testutil.Run(t, test.description, func(t *testutil.T) {
    83  			t.NewTempDir().Touch("build.gradle").Chdir()
    84  			t.Override(&gradleBuildArgsFunc, getGradleBuildArgsFuncFake(t, MinimumJibGradleVersion))
    85  			t.Override(&util.DefaultExecCommand, test.commands)
    86  			api := (&testutil.FakeAPIClient{}).Add("img:tag", "imageID")
    87  			localDocker := fakeLocalDaemon(api)
    88  
    89  			builder := NewArtifactBuilder(localDocker, &mockConfig{}, false, false, nil)
    90  			result, err := builder.Build(context.Background(), ioutil.Discard, &latest.Artifact{
    91  				ArtifactType: latest.ArtifactType{
    92  					JibArtifact: test.artifact,
    93  				},
    94  			}, "img:tag", platform.Matcher{})
    95  
    96  			t.CheckError(test.shouldErr, err)
    97  			if test.shouldErr {
    98  				t.CheckErrorContains(test.expectedError, err)
    99  			} else {
   100  				t.CheckDeepEqual("imageID", result)
   101  			}
   102  		})
   103  	}
   104  }
   105  
   106  func TestBuildJibGradleToRegistry(t *testing.T) {
   107  	tests := []struct {
   108  		description   string
   109  		artifact      *latest.JibArtifact
   110  		commands      util.Command
   111  		shouldErr     bool
   112  		expectedError string
   113  	}{
   114  		{
   115  			description: "remote build",
   116  			artifact:    &latest.JibArtifact{},
   117  			commands: testutil.CmdRun(
   118  				"gradle fake-gradleBuildArgs-for-jib --image=img:tag",
   119  			),
   120  		},
   121  		{
   122  			description: "build with project",
   123  			artifact:    &latest.JibArtifact{Project: "project"},
   124  			commands: testutil.CmdRun(
   125  				"gradle fake-gradleBuildArgs-for-project-for-jib --image=img:tag",
   126  			),
   127  		},
   128  		{
   129  			description: "build with custom base image",
   130  			artifact:    &latest.JibArtifact{BaseImage: "docker://busybox"},
   131  			commands: testutil.CmdRun(
   132  				"gradle fake-gradleBuildArgs-for-jib -Djib.from.image=docker://busybox --image=img:tag",
   133  			),
   134  		},
   135  		{
   136  			description: "fail build",
   137  			artifact:    &latest.JibArtifact{},
   138  			commands: testutil.CmdRunErr(
   139  				"gradle fake-gradleBuildArgs-for-jib --image=img:tag",
   140  				errors.New("BUG"),
   141  			),
   142  			shouldErr:     true,
   143  			expectedError: "gradle build failed",
   144  		},
   145  	}
   146  
   147  	for _, test := range tests {
   148  		testutil.Run(t, test.description, func(t *testutil.T) {
   149  			t.NewTempDir().Touch("build.gradle").Chdir()
   150  			t.Override(&gradleBuildArgsFunc, getGradleBuildArgsFuncFake(t, MinimumJibGradleVersion))
   151  			t.Override(&util.DefaultExecCommand, test.commands)
   152  			t.Override(&docker.RemoteDigest, func(identifier string, _ docker.Config, _ []v1.Platform) (string, error) {
   153  				if identifier == "img:tag" {
   154  					return "digest", nil
   155  				}
   156  				return "", errors.New("unknown remote tag")
   157  			})
   158  			localDocker := fakeLocalDaemon(&testutil.FakeAPIClient{})
   159  
   160  			builder := NewArtifactBuilder(localDocker, &mockConfig{}, true, false, nil)
   161  			result, err := builder.Build(context.Background(), ioutil.Discard, &latest.Artifact{
   162  				ArtifactType: latest.ArtifactType{
   163  					JibArtifact: test.artifact,
   164  				},
   165  			}, "img:tag", platform.Matcher{})
   166  
   167  			t.CheckError(test.shouldErr, err)
   168  			if test.shouldErr {
   169  				t.CheckErrorContains(test.expectedError, err)
   170  			} else {
   171  				t.CheckDeepEqual("digest", result)
   172  			}
   173  		})
   174  	}
   175  }
   176  
   177  func TestMinimumGradleVersion(t *testing.T) {
   178  	testutil.CheckDeepEqual(t, "1.4.0", MinimumJibGradleVersion)
   179  }
   180  
   181  func TestGradleWrapperDefinition(t *testing.T) {
   182  	testutil.CheckDeepEqual(t, "gradle", GradleCommand.Executable)
   183  	testutil.CheckDeepEqual(t, "gradlew", GradleCommand.Wrapper)
   184  }
   185  
   186  func TestGetDependenciesGradle(t *testing.T) {
   187  	tmpDir := testutil.NewTempDir(t)
   188  
   189  	tmpDir.Touch("build", "dep1", "dep2")
   190  	build := tmpDir.Path("build")
   191  	dep1 := tmpDir.Path("dep1")
   192  	dep2 := tmpDir.Path("dep2")
   193  
   194  	ctx := context.Background()
   195  
   196  	tests := []struct {
   197  		description string
   198  		stdout      string
   199  		modTime     time.Time
   200  		expected    []string
   201  		err         error
   202  	}{
   203  		{
   204  			description: "failure",
   205  			stdout:      "",
   206  			modTime:     time.Unix(0, 0),
   207  			err:         errors.New("error"),
   208  		},
   209  		{
   210  			description: "success",
   211  			stdout:      fmt.Sprintf("BEGIN JIB JSON\n{\"build\":[\"%s\"],\"inputs\":[\"%s\"],\"ignore\":[]}", build, dep1),
   212  			modTime:     time.Unix(0, 0),
   213  			expected:    []string{"build", "dep1"},
   214  		},
   215  		{
   216  			// Expected output differs from stdout since build file hasn't change, thus gradle command won't run
   217  			description: "success",
   218  			stdout:      fmt.Sprintf("BEGIN JIB JSON\n{\"build\":[\"%s\"],\"inputs\":[\"%s\", \"%s\"],\"ignore\":[]}", build, dep1, dep2),
   219  			modTime:     time.Unix(0, 0),
   220  			expected:    []string{"build", "dep1"},
   221  		},
   222  		{
   223  			description: "success",
   224  			stdout:      fmt.Sprintf("BEGIN JIB JSON\n{\"build\":[\"%s\"],\"inputs\":[\"%s\", \"%s\"],\"ignore\":[]}", build, dep1, dep2),
   225  			modTime:     time.Unix(10000, 0),
   226  			expected:    []string{"build", "dep1", "dep2"},
   227  		},
   228  	}
   229  	for _, test := range tests {
   230  		testutil.Run(t, test.description, func(t *testutil.T) {
   231  			t.Override(&util.DefaultExecCommand, testutil.CmdRunOutErr(
   232  				strings.Join(getCommandGradle(ctx, tmpDir.Root(), &latest.JibArtifact{Project: "gradle-test"}).Args, " "),
   233  				test.stdout,
   234  				test.err,
   235  			))
   236  
   237  			// Change build file mod time
   238  			if err := os.Chtimes(build, test.modTime, test.modTime); err != nil {
   239  				t.Fatal(err)
   240  			}
   241  
   242  			ws := tmpDir.Root()
   243  			deps, err := getDependenciesGradle(ctx, ws, &latest.JibArtifact{Project: "gradle-test"})
   244  			if test.err != nil {
   245  				prefix := fmt.Sprintf("could not fetch dependencies for workspace %s: initial Jib dependency refresh failed: failed to get Jib dependencies: ", ws)
   246  				t.CheckErrorAndDeepEqual(true, err, prefix+test.err.Error(), err.Error())
   247  			} else {
   248  				t.CheckDeepEqual(test.expected, deps)
   249  			}
   250  		})
   251  	}
   252  }
   253  
   254  func TestGetCommandGradle(t *testing.T) {
   255  	ctx := context.Background()
   256  
   257  	tests := []struct {
   258  		description      string
   259  		jibArtifact      latest.JibArtifact
   260  		filesInWorkspace []string
   261  		expectedCmd      func(workspace string) exec.Cmd
   262  	}{
   263  		{
   264  			description:      "gradle default",
   265  			jibArtifact:      latest.JibArtifact{},
   266  			filesInWorkspace: []string{},
   267  			expectedCmd: func(workspace string) exec.Cmd {
   268  				return GradleCommand.CreateCommand(ctx, workspace, []string{"_skaffoldFailIfJibOutOfDate", "-Djib.requiredVersion=" + MinimumJibGradleVersion, ":_jibSkaffoldFilesV2", "-q", "--console=plain"})
   269  			},
   270  		},
   271  		{
   272  			description:      "gradle default with project",
   273  			jibArtifact:      latest.JibArtifact{Project: "project"},
   274  			filesInWorkspace: []string{},
   275  			expectedCmd: func(workspace string) exec.Cmd {
   276  				return GradleCommand.CreateCommand(ctx, workspace, []string{"_skaffoldFailIfJibOutOfDate", "-Djib.requiredVersion=" + MinimumJibGradleVersion, ":project:_jibSkaffoldFilesV2", "-q", "--console=plain"})
   277  			},
   278  		},
   279  		{
   280  			description:      "gradle with wrapper",
   281  			jibArtifact:      latest.JibArtifact{},
   282  			filesInWorkspace: []string{"gradlew", "gradlew.cmd"},
   283  			expectedCmd: func(workspace string) exec.Cmd {
   284  				return GradleCommand.CreateCommand(ctx, workspace, []string{"_skaffoldFailIfJibOutOfDate", "-Djib.requiredVersion=" + MinimumJibGradleVersion, ":_jibSkaffoldFilesV2", "-q", "--console=plain"})
   285  			},
   286  		},
   287  		{
   288  			description:      "gradle with wrapper and project",
   289  			jibArtifact:      latest.JibArtifact{Project: "project"},
   290  			filesInWorkspace: []string{"gradlew", "gradlew.cmd"},
   291  			expectedCmd: func(workspace string) exec.Cmd {
   292  				return GradleCommand.CreateCommand(ctx, workspace, []string{"_skaffoldFailIfJibOutOfDate", "-Djib.requiredVersion=" + MinimumJibGradleVersion, ":project:_jibSkaffoldFilesV2", "-q", "--console=plain"})
   293  			},
   294  		},
   295  	}
   296  	for _, test := range tests {
   297  		testutil.Run(t, test.description, func(t *testutil.T) {
   298  			tmpDir := t.NewTempDir().
   299  				Touch(test.filesInWorkspace...)
   300  
   301  			cmd := getCommandGradle(ctx, tmpDir.Root(), &test.jibArtifact)
   302  
   303  			expectedCmd := test.expectedCmd(tmpDir.Root())
   304  			t.CheckDeepEqual(expectedCmd.Path, cmd.Path)
   305  			t.CheckDeepEqual(expectedCmd.Args, cmd.Args)
   306  			t.CheckDeepEqual(expectedCmd.Dir, cmd.Dir)
   307  		})
   308  	}
   309  }
   310  
   311  func TestGetSyncMapCommandGradle(t *testing.T) {
   312  	ctx := context.Background()
   313  	tests := []struct {
   314  		description string
   315  		workspace   string
   316  		jibArtifact latest.JibArtifact
   317  		expectedCmd func(workspace string) exec.Cmd
   318  	}{
   319  		{
   320  			description: "single module",
   321  			jibArtifact: latest.JibArtifact{},
   322  			expectedCmd: func(workspace string) exec.Cmd {
   323  				return GradleCommand.CreateCommand(ctx, workspace, []string{"fake-gradleBuildArgs-for-_jibSkaffoldSyncMap-skipTests"})
   324  			},
   325  		},
   326  		{
   327  			description: "multi module",
   328  			jibArtifact: latest.JibArtifact{Project: "project"},
   329  			expectedCmd: func(workspace string) exec.Cmd {
   330  				return GradleCommand.CreateCommand(ctx, workspace, []string{"fake-gradleBuildArgs-for-project-for-_jibSkaffoldSyncMap-skipTests"})
   331  			},
   332  		},
   333  	}
   334  	for _, test := range tests {
   335  		testutil.Run(t, test.description, func(t *testutil.T) {
   336  			t.Override(&gradleBuildArgsFunc, getGradleBuildArgsFuncFake(t, MinimumJibGradleVersionForSync))
   337  			cmd := getSyncMapCommandGradle(ctx, test.workspace, &test.jibArtifact)
   338  			expectedCmd := test.expectedCmd(test.workspace)
   339  			t.CheckDeepEqual(expectedCmd.Path, cmd.Path)
   340  			t.CheckDeepEqual(expectedCmd.Args, cmd.Args)
   341  			t.CheckDeepEqual(expectedCmd.Dir, cmd.Dir)
   342  		})
   343  	}
   344  }
   345  
   346  func TestGenerateGradleBuildArgs(t *testing.T) {
   347  	tests := []struct {
   348  		description        string
   349  		in                 latest.JibArtifact
   350  		platforms          platform.Matcher
   351  		expectedMinVersion string
   352  		deps               []*latest.ArtifactDependency
   353  		image              string
   354  		skipTests          bool
   355  		pushImages         bool
   356  		r                  ArtifactResolver
   357  		insecureRegistries map[string]bool
   358  		out                []string
   359  	}{
   360  		{description: "single module", image: "image", out: []string{"fake-gradleBuildArgs-for-testTask", "--image=image"}},
   361  		{description: "single module without tests", image: "image", skipTests: true, out: []string{"fake-gradleBuildArgs-for-testTask-skipTests", "--image=image"}},
   362  		{description: "multi module", in: latest.JibArtifact{Project: "project"}, image: "image", out: []string{"fake-gradleBuildArgs-for-project-for-testTask", "--image=image"}},
   363  		{description: "multi module without tests", in: latest.JibArtifact{Project: "project"}, image: "image", skipTests: true, out: []string{"fake-gradleBuildArgs-for-project-for-testTask-skipTests", "--image=image"}},
   364  		{description: "multi module without tests with insecure registries", in: latest.JibArtifact{Project: "project"}, image: "registry.tld/image", skipTests: true, insecureRegistries: map[string]bool{"registry.tld": true}, out: []string{"fake-gradleBuildArgs-for-project-for-testTask-skipTests", "-Djib.allowInsecureRegistries=true", "--image=registry.tld/image"}},
   365  		{description: "single module with custom base image", in: latest.JibArtifact{BaseImage: "docker://busybox"}, image: "image", out: []string{"fake-gradleBuildArgs-for-testTask", "-Djib.from.image=docker://busybox", "--image=image"}},
   366  		{description: "multi module with custom base image", in: latest.JibArtifact{Project: "project", BaseImage: "docker://busybox"}, image: "image", out: []string{"fake-gradleBuildArgs-for-project-for-testTask", "-Djib.from.image=docker://busybox", "--image=image"}},
   367  		{description: "host platform", image: "image", platforms: platform.Matcher{Platforms: []v1.Platform{{OS: runtime.GOOS, Architecture: runtime.GOARCH}}}, out: []string{"fake-gradleBuildArgs-for-testTask", fmt.Sprintf("-Djib.from.platforms=%s/%s", runtime.GOOS, runtime.GOARCH), "--image=image"}},
   368  		{description: "cross-platform", image: "image", platforms: platform.Matcher{Platforms: []v1.Platform{{OS: "freebsd", Architecture: "arm"}}}, out: []string{"fake-gradleBuildArgs-for-testTask", "-Djib.from.platforms=freebsd/arm", "--image=image"}, expectedMinVersion: MinimumJibGradleVersionForCrossPlatform},
   369  		{description: "multi-platform", image: "image", platforms: platform.Matcher{Platforms: []v1.Platform{{OS: "linux", Architecture: "amd64"}, {OS: "darwin", Architecture: "arm64"}}}, out: []string{"fake-gradleBuildArgs-for-testTask", "-Djib.from.platforms=linux/amd64,darwin/arm64", "--image=image"}, expectedMinVersion: MinimumJibGradleVersionForCrossPlatform},
   370  		{
   371  			description: "single module with local base image from required artifacts",
   372  			in:          latest.JibArtifact{BaseImage: "alias"},
   373  			image:       "image",
   374  			deps:        []*latest.ArtifactDependency{{ImageName: "img", Alias: "alias"}},
   375  			r:           mockArtifactResolver{m: map[string]string{"img": "img:tag"}},
   376  			out:         []string{"fake-gradleBuildArgs-for-testTask", "-Djib.from.image=docker://img:tag", "--image=image"},
   377  		},
   378  		{
   379  			description: "multi module with local base image from required artifacts",
   380  			in:          latest.JibArtifact{Project: "project", BaseImage: "alias"},
   381  			image:       "image",
   382  			deps:        []*latest.ArtifactDependency{{ImageName: "img", Alias: "alias"}},
   383  			r:           mockArtifactResolver{m: map[string]string{"img": "img:tag"}},
   384  			out:         []string{"fake-gradleBuildArgs-for-project-for-testTask", "-Djib.from.image=docker://img:tag", "--image=image"},
   385  		}, {
   386  			description: "single module with remote base image from required artifacts",
   387  			in:          latest.JibArtifact{BaseImage: "alias"},
   388  			image:       "image",
   389  			pushImages:  true,
   390  			deps:        []*latest.ArtifactDependency{{ImageName: "img", Alias: "alias"}},
   391  			r:           mockArtifactResolver{m: map[string]string{"img": "img:tag"}},
   392  			out:         []string{"fake-gradleBuildArgs-for-testTask", "-Djib.from.image=img:tag", "--image=image"},
   393  		},
   394  		{
   395  			description: "multi module with remote base image from required artifacts",
   396  			in:          latest.JibArtifact{Project: "project", BaseImage: "alias"},
   397  			image:       "image",
   398  			pushImages:  true,
   399  			deps:        []*latest.ArtifactDependency{{ImageName: "img", Alias: "alias"}},
   400  			r:           mockArtifactResolver{m: map[string]string{"img": "img:tag"}},
   401  			out:         []string{"fake-gradleBuildArgs-for-project-for-testTask", "-Djib.from.image=img:tag", "--image=image"},
   402  		},
   403  	}
   404  	for _, test := range tests {
   405  		testutil.Run(t, test.description, func(t *testutil.T) {
   406  			minVersion := MinimumJibGradleVersion
   407  			if test.expectedMinVersion != "" {
   408  				minVersion = test.expectedMinVersion
   409  			}
   410  			t.Override(&gradleBuildArgsFunc, getGradleBuildArgsFuncFake(t, minVersion))
   411  			command := GenerateGradleBuildArgs("testTask", test.image, &test.in, test.platforms, test.skipTests, test.pushImages, test.deps, test.r, test.insecureRegistries, false)
   412  			t.CheckDeepEqual(test.out, command)
   413  		})
   414  	}
   415  }
   416  
   417  func TestGradleArgs(t *testing.T) {
   418  	tests := []struct {
   419  		description string
   420  		jibArtifact latest.JibArtifact
   421  		expected    []string
   422  	}{
   423  		{
   424  			description: "single module",
   425  			jibArtifact: latest.JibArtifact{},
   426  			expected:    []string{"_skaffoldFailIfJibOutOfDate", "-Djib.requiredVersion=test-version", ":testTask"},
   427  		},
   428  		{
   429  			description: "multi module",
   430  			jibArtifact: latest.JibArtifact{Project: "module"},
   431  			expected:    []string{"_skaffoldFailIfJibOutOfDate", "-Djib.requiredVersion=test-version", ":module:testTask"},
   432  		},
   433  	}
   434  	for _, test := range tests {
   435  		args := gradleArgs(&test.jibArtifact, "testTask", "test-version")
   436  		testutil.CheckDeepEqual(t, test.expected, args)
   437  	}
   438  }
   439  
   440  func TestGradleBuildArgs(t *testing.T) {
   441  	tests := []struct {
   442  		description string
   443  		jibArtifact latest.JibArtifact
   444  		skipTests   bool
   445  		showColors  bool
   446  		expected    []string
   447  	}{
   448  		{
   449  			description: "single module",
   450  			jibArtifact: latest.JibArtifact{},
   451  			skipTests:   false,
   452  			showColors:  true,
   453  			expected:    []string{"-Djib.console=plain", "fake-gradleArgs-for-testTask"},
   454  		},
   455  		{
   456  			description: "single module skip tests",
   457  			jibArtifact: latest.JibArtifact{},
   458  			skipTests:   true,
   459  			showColors:  true,
   460  			expected:    []string{"-Djib.console=plain", "fake-gradleArgs-for-testTask", "-x", "test"},
   461  		},
   462  		{
   463  			description: "single module plain console",
   464  			jibArtifact: latest.JibArtifact{},
   465  			skipTests:   true,
   466  			showColors:  false,
   467  			expected:    []string{"--console=plain", "fake-gradleArgs-for-testTask", "-x", "test"},
   468  		},
   469  		{
   470  			description: "single module with extra flags",
   471  			jibArtifact: latest.JibArtifact{Flags: []string{"--flag1", "--flag2"}},
   472  			skipTests:   false,
   473  			showColors:  true,
   474  			expected:    []string{"-Djib.console=plain", "fake-gradleArgs-for-testTask", "--flag1", "--flag2"},
   475  		},
   476  		{
   477  			description: "multi module",
   478  			jibArtifact: latest.JibArtifact{Project: "module"},
   479  			skipTests:   false,
   480  			showColors:  true,
   481  			expected:    []string{"-Djib.console=plain", "fake-gradleArgs-for-module-for-testTask"},
   482  		},
   483  		{
   484  			description: "single module skip tests",
   485  			jibArtifact: latest.JibArtifact{Project: "module"},
   486  			skipTests:   true,
   487  			showColors:  true,
   488  			expected:    []string{"-Djib.console=plain", "fake-gradleArgs-for-module-for-testTask", "-x", "test"},
   489  		},
   490  		{
   491  			description: "multi module with extra flags",
   492  			jibArtifact: latest.JibArtifact{Project: "module", Flags: []string{"--flag1", "--flag2"}},
   493  			skipTests:   false,
   494  			showColors:  true,
   495  			expected:    []string{"-Djib.console=plain", "fake-gradleArgs-for-module-for-testTask", "--flag1", "--flag2"},
   496  		},
   497  	}
   498  	for _, test := range tests {
   499  		testutil.Run(t, test.description, func(t *testutil.T) {
   500  			t.Override(&gradleArgsFunc, getGradleArgsFuncFake(t, "test-version"))
   501  			args := gradleBuildArgs("testTask", &test.jibArtifact, test.skipTests, test.showColors, "test-version")
   502  			t.CheckDeepEqual(test.expected, args)
   503  		})
   504  	}
   505  }
   506  
   507  func getGradleArgsFuncFake(t *testutil.T, expectedMinimumVersion string) func(*latest.JibArtifact, string, string) []string {
   508  	return func(a *latest.JibArtifact, task string, minimumVersion string) []string {
   509  		t.CheckDeepEqual(expectedMinimumVersion, minimumVersion)
   510  		if a.Project == "" {
   511  			return []string{"fake-gradleArgs-for-" + task}
   512  		}
   513  		return []string{"fake-gradleArgs-for-" + a.Project + "-for-" + task}
   514  	}
   515  }
   516  
   517  // check that parameters are actually passed though
   518  func getGradleBuildArgsFuncFake(t *testutil.T, expectedMinimumVersion string) func(string, *latest.JibArtifact, bool, bool, string) []string {
   519  	return func(task string, a *latest.JibArtifact, skipTests, showColors bool, minimumVersion string) []string {
   520  		t.CheckDeepEqual(expectedMinimumVersion, minimumVersion)
   521  
   522  		testString := ""
   523  		if skipTests {
   524  			testString = "-skipTests"
   525  		}
   526  
   527  		if a.Project == "" {
   528  			return []string{"fake-gradleBuildArgs-for-" + task + testString}
   529  		}
   530  		return []string{"fake-gradleBuildArgs-for-" + a.Project + "-for-" + task + testString}
   531  	}
   532  }
   533  
   534  type mockConfig struct {
   535  	Config
   536  }
   537  
   538  func (c *mockConfig) GetInsecureRegistries() map[string]bool { return nil }
   539  
   540  type mockArtifactResolver struct {
   541  	m map[string]string
   542  }
   543  
   544  func (r mockArtifactResolver) GetImageTag(imageName string) (string, bool) {
   545  	val, found := r.m[imageName]
   546  	return val, found
   547  }