github.com/openshift/source-to-image@v1.4.1-0.20240516041539-bf52fc02204e/test/integration/dockerfile/dockerfile_test.go (about)

     1  //go:build integration
     2  // +build integration
     3  
     4  package dockerfile
     5  
     6  import (
     7  	"bytes"
     8  	"io/ioutil"
     9  	"os"
    10  	"path/filepath"
    11  	"regexp"
    12  	"strings"
    13  	"testing"
    14  
    15  	"github.com/moby/buildkit/frontend/dockerfile/parser"
    16  
    17  	"github.com/openshift/source-to-image/pkg/api"
    18  	"github.com/openshift/source-to-image/pkg/build"
    19  	"github.com/openshift/source-to-image/pkg/build/strategies"
    20  	"github.com/openshift/source-to-image/pkg/scm/git"
    21  )
    22  
    23  func TestDockerfileBuild(t *testing.T) {
    24  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
    25  	if err != nil {
    26  		t.Errorf("Unable to create temporary directory: %v", err)
    27  	}
    28  	defer os.RemoveAll(tempdir)
    29  
    30  	config := &api.Config{
    31  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
    32  		AssembleUser: "",
    33  		ImageWorkDir: "",
    34  		Source:       git.MustParse("https://github.com/sclorg/nodejs-ex"),
    35  		ScriptsURL:   "",
    36  		Injections:   api.VolumeList{},
    37  		Destination:  "",
    38  
    39  		Environment: api.EnvironmentList{},
    40  		Labels:      map[string]string{},
    41  
    42  		AsDockerfile: tempdir + string(os.PathSeparator) + "MyDockerfile",
    43  	}
    44  	expected := []string{
    45  		"(?m)^FROM docker.io/centos/nodejs-8-centos7",
    46  		"\"io.openshift.s2i.build.commit.date\"",
    47  		"\"io.openshift.s2i.build.commit.id\"",
    48  		"\"io.openshift.s2i.build.commit.ref\"",
    49  		"\"io.openshift.s2i.build.commit.message\"",
    50  		"\"io.openshift.s2i.build.source-location\"",
    51  		"\"io.openshift.s2i.build.image\"=\"docker.io/centos/nodejs-8-centos7\"",
    52  		"\"io.openshift.s2i.build.commit.author\"",
    53  		"(?m)^COPY upload/src /tmp/src",
    54  		"(?m)^RUN chown -R 1001:0.* /tmp/src",
    55  		// Ensure we are using the default image user when running assemble
    56  		"(?m)^USER 1001\n.+\n.+\nRUN /usr/libexec/s2i/assemble",
    57  		"(?m)^CMD /usr/libexec/s2i/run",
    58  	}
    59  	expectedFiles := []string{
    60  		filepath.Join(tempdir, "upload/src/server.js"),
    61  		filepath.Join(tempdir, "MyDockerfile"),
    62  	}
    63  	runDockerfileTest(t, config, expected, nil, expectedFiles, false)
    64  }
    65  
    66  func TestDockerfileBuildDefaultDockerfile(t *testing.T) {
    67  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
    68  	if err != nil {
    69  		t.Errorf("Unable to create temporary directory: %v", err)
    70  	}
    71  	defer os.RemoveAll(tempdir)
    72  
    73  	config := &api.Config{
    74  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
    75  		AssembleUser: "",
    76  		ImageWorkDir: "",
    77  		Source:       git.MustParse("https://github.com/sclorg/nodejs-ex"),
    78  		ScriptsURL:   "",
    79  		Injections:   api.VolumeList{},
    80  		Destination:  "",
    81  
    82  		Environment: api.EnvironmentList{},
    83  		Labels:      map[string]string{},
    84  
    85  		AsDockerfile: tempdir + string(os.PathSeparator),
    86  	}
    87  	expected := []string{
    88  		"(?m)^FROM docker.io/centos/nodejs-8-centos7",
    89  		"\"io.openshift.s2i.build.commit.date\"",
    90  		"\"io.openshift.s2i.build.commit.id\"",
    91  		"\"io.openshift.s2i.build.commit.ref\"",
    92  		"\"io.openshift.s2i.build.commit.message\"",
    93  		"\"io.openshift.s2i.build.source-location\"",
    94  		"\"io.openshift.s2i.build.image\"=\"docker.io/centos/nodejs-8-centos7\"",
    95  		"\"io.openshift.s2i.build.commit.author\"",
    96  		"(?m)^COPY upload/src /tmp/src",
    97  		"(?m)^RUN chown -R 1001:0.* /tmp/src",
    98  		"(?m)^RUN /usr/libexec/s2i/assemble",
    99  		"(?m)^CMD /usr/libexec/s2i/run",
   100  	}
   101  	expectedFiles := []string{
   102  		filepath.Join(tempdir, "upload/src/server.js"),
   103  		filepath.Join(tempdir, "Dockerfile"),
   104  	}
   105  	runDockerfileTest(t, config, expected, nil, expectedFiles, false)
   106  }
   107  
   108  func TestDockerfileBuildEnv(t *testing.T) {
   109  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   110  	if err != nil {
   111  		t.Errorf("Unable to create temporary directory: %v", err)
   112  	}
   113  	defer os.RemoveAll(tempdir)
   114  
   115  	config := &api.Config{
   116  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
   117  		AssembleUser: "",
   118  		ImageWorkDir: "",
   119  		Source:       git.MustParse("https://github.com/sclorg/nodejs-ex"),
   120  		ScriptsURL:   "",
   121  		Injections:   api.VolumeList{},
   122  		Destination:  "",
   123  
   124  		Environment: api.EnvironmentList{
   125  			{
   126  				Name:  "key1",
   127  				Value: "value1",
   128  			},
   129  			{
   130  				Name:  "key2",
   131  				Value: "value2",
   132  			},
   133  		},
   134  		Labels: map[string]string{},
   135  
   136  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   137  	}
   138  
   139  	expected := []string{
   140  		"key1=\"value1\"",
   141  		"key2=\"value2\"",
   142  	}
   143  	runDockerfileTest(t, config, expected, nil, nil, false)
   144  }
   145  
   146  func TestDockerfileBuildLabels(t *testing.T) {
   147  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   148  	if err != nil {
   149  		t.Errorf("Unable to create temporary directory: %v", err)
   150  	}
   151  	defer os.RemoveAll(tempdir)
   152  
   153  	config := &api.Config{
   154  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
   155  		AssembleUser: "",
   156  		ImageWorkDir: "",
   157  		Source:       git.MustParse("https://github.com/sclorg/nodejs-ex"),
   158  		ScriptsURL:   "image:///scripts",
   159  		Injections:   api.VolumeList{},
   160  		Destination:  "/destination",
   161  
   162  		Environment: api.EnvironmentList{},
   163  		Labels: map[string]string{"label1": "value1",
   164  			"label2":                               "value2",
   165  			"io.openshift.s2i.build.commit.author": "shadowman"},
   166  
   167  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   168  	}
   169  	expected := []string{
   170  		"\"io.openshift.s2i.scripts-url\"=\"image:///scripts\"",
   171  		"\"io.openshift.s2i.destination\"=\"/destination\"",
   172  		"\"io.openshift.s2i.build.commit.date\"",
   173  		"\"io.openshift.s2i.build.commit.id\"",
   174  		"\"io.openshift.s2i.build.commit.ref\"",
   175  		"\"io.openshift.s2i.build.commit.message\"",
   176  		"\"io.openshift.s2i.build.source-location\"",
   177  		"\"io.openshift.s2i.build.image\"=\"docker.io/centos/nodejs-8-centos7\"",
   178  		"\"io.openshift.s2i.build.commit.author\"=\"shadowman\"",
   179  		"\"label1\"=\"value1\"",
   180  		"\"label2\"=\"value2\"",
   181  	}
   182  	runDockerfileTest(t, config, expected, nil, nil, false)
   183  }
   184  
   185  func TestDockerfileBuildInjections(t *testing.T) {
   186  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   187  	if err != nil {
   188  		t.Errorf("Unable to create temporary directory: %v", err)
   189  	}
   190  	defer os.RemoveAll(tempdir)
   191  
   192  	injection1 := filepath.Join(tempdir, "injection1")
   193  	err = os.Mkdir(injection1, 0777)
   194  	if err != nil {
   195  		t.Errorf("Unable to create injection dir: %v", err)
   196  	}
   197  
   198  	for i := 0; i < 3; i++ {
   199  		_, err = ioutil.TempFile(injection1, "injectfile-")
   200  		if err != nil {
   201  			t.Errorf("Unable to create injection file: %v", err)
   202  		}
   203  	}
   204  
   205  	injection2 := filepath.Join(tempdir, "injection2")
   206  	err = os.Mkdir(injection2, 0777)
   207  	if err != nil {
   208  		t.Errorf("Unable to create injection dir: %v", err)
   209  	}
   210  	_, err = ioutil.TempFile(injection2, "injectfile-2")
   211  	if err != nil {
   212  		t.Errorf("Unable to create injection file: %v", err)
   213  	}
   214  
   215  	config := &api.Config{
   216  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
   217  		AssembleUser: "",
   218  		ImageWorkDir: "/workdir",
   219  		Source:       git.MustParse("https://github.com/sclorg/nodejs-ex"),
   220  		ScriptsURL:   "",
   221  		Injections: api.VolumeList{
   222  			{
   223  				Source:      injection1,
   224  				Destination: "injection1",
   225  				Keep:        false,
   226  			},
   227  			{
   228  				Source:      injection2,
   229  				Destination: "/destination/injection2",
   230  				Keep:        true,
   231  			},
   232  		},
   233  		Destination: "",
   234  
   235  		Environment: api.EnvironmentList{},
   236  		Labels:      map[string]string{},
   237  
   238  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   239  	}
   240  
   241  	// strip the C: from windows paths because it's not valid in the middle of a path
   242  	// like upload/injections/C:/tempdir/injection1
   243  	trimmedInjection1 := filepath.ToSlash(strings.TrimPrefix(injection1, filepath.VolumeName(injection1)))
   244  	trimmedInjection2 := filepath.ToSlash(strings.TrimPrefix(injection2, filepath.VolumeName(injection2)))
   245  
   246  	expected := []string{
   247  		"(?m)^COPY upload/injections" + trimmedInjection1 + " /workdir/injection1",
   248  		"(?m)^RUN chown -R 1001:0.* /workdir/injection1",
   249  		"(?m)^COPY upload/injections" + trimmedInjection2 + " /destination/injection2",
   250  		"(?m)^RUN chown -R 1001:0.* /destination/injection2",
   251  		"(?m)^RUN rm /workdir/injection1/injectfile-",
   252  		"    rm /workdir/injection1/injectfile-",
   253  	}
   254  	notExpected := []string{
   255  		"rm -rf /destination/injection2",
   256  	}
   257  	expectedFiles := []string{
   258  		filepath.Join(tempdir, "upload/src/server.js"),
   259  		filepath.Join(tempdir, "upload/injections"+trimmedInjection1),
   260  		filepath.Join(tempdir, "upload/injections"+trimmedInjection2),
   261  	}
   262  	runDockerfileTest(t, config, expected, notExpected, expectedFiles, false)
   263  }
   264  
   265  func TestDockerfileBuildScriptsURLAssemble(t *testing.T) {
   266  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   267  	if err != nil {
   268  		t.Errorf("Unable to create temporary directory: %v", err)
   269  	}
   270  	defer os.RemoveAll(tempdir)
   271  
   272  	assemble := filepath.Join(tempdir, "assemble")
   273  	_, err = os.OpenFile(assemble, os.O_RDONLY|os.O_CREATE, 0666)
   274  	if err != nil {
   275  		t.Errorf("Unable to create assemble file: %v", err)
   276  	}
   277  
   278  	config := &api.Config{
   279  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
   280  		AssembleUser: "",
   281  		ImageWorkDir: "",
   282  		Source:       git.MustParse("https://github.com/sclorg/nodejs-ex"),
   283  		ScriptsURL:   "file://" + filepath.ToSlash(tempdir),
   284  		Injections:   api.VolumeList{},
   285  		Destination:  "/destination",
   286  
   287  		Environment: api.EnvironmentList{},
   288  		Labels:      map[string]string{},
   289  
   290  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   291  	}
   292  	expected := []string{
   293  		"(?m)^COPY upload/scripts /destination/scripts",
   294  		"(?m)^RUN chown -R 1001:0.* /destination/scripts",
   295  		"(?m)^RUN /destination/scripts/assemble",
   296  		"(?m)^CMD /usr/libexec/s2i/run",
   297  	}
   298  	expectedFiles := []string{
   299  		filepath.Join(tempdir, "upload/src/server.js"),
   300  		filepath.Join(tempdir, "upload/scripts/assemble"),
   301  	}
   302  	runDockerfileTest(t, config, expected, nil, expectedFiles, false)
   303  }
   304  
   305  func TestDockerfileBuildScriptsURLRun(t *testing.T) {
   306  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   307  	if err != nil {
   308  		t.Errorf("Unable to create temporary directory: %v", err)
   309  	}
   310  	defer os.RemoveAll(tempdir)
   311  
   312  	run := filepath.Join(tempdir, "run")
   313  	_, err = os.OpenFile(run, os.O_RDONLY|os.O_CREATE, 0666)
   314  	if err != nil {
   315  		t.Errorf("Unable to create run file: %v", err)
   316  	}
   317  
   318  	config := &api.Config{
   319  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
   320  		AssembleUser: "",
   321  		ImageWorkDir: "",
   322  		Source:       git.MustParse("https://github.com/sclorg/nodejs-ex"),
   323  		ScriptsURL:   "file://" + filepath.ToSlash(tempdir),
   324  		Injections:   api.VolumeList{},
   325  		Destination:  "/destination",
   326  
   327  		Environment: api.EnvironmentList{},
   328  		Labels:      map[string]string{},
   329  
   330  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   331  	}
   332  	expected := []string{
   333  		"(?m)^COPY upload/scripts /destination/scripts",
   334  		"(?m)^RUN chown -R 1001:0.* /destination/scripts",
   335  		"(?m)^RUN /usr/libexec/s2i/assemble",
   336  		"(?m)^CMD /destination/scripts/run",
   337  	}
   338  	expectedFiles := []string{
   339  		filepath.Join(tempdir, "upload/src/server.js"),
   340  		filepath.Join(tempdir, "upload/scripts/run"),
   341  	}
   342  	runDockerfileTest(t, config, expected, nil, expectedFiles, false)
   343  }
   344  
   345  func TestDockerfileBuildScriptsURLNone(t *testing.T) {
   346  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   347  	if err != nil {
   348  		t.Errorf("Unable to create temporary directory: %v", err)
   349  	}
   350  	defer os.RemoveAll(tempdir)
   351  
   352  	config := &api.Config{
   353  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
   354  		AssembleUser: "",
   355  		ImageWorkDir: "",
   356  		Source:       git.MustParse("https://github.com/sclorg/nodejs-ex"),
   357  		ScriptsURL:   "file://" + filepath.ToSlash(tempdir),
   358  		Injections:   api.VolumeList{},
   359  		Destination:  "/destination",
   360  
   361  		Environment: api.EnvironmentList{},
   362  		Labels:      map[string]string{},
   363  
   364  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   365  	}
   366  	runDockerfileTest(t, config, nil, nil, nil, true)
   367  }
   368  
   369  func TestDockerfileBuildSourceScriptsAssemble(t *testing.T) {
   370  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   371  	if err != nil {
   372  		t.Errorf("Unable to create temporary directory: %v", err)
   373  	}
   374  	defer os.RemoveAll(tempdir)
   375  
   376  	sourcecode := filepath.Join(tempdir, "sourcecode")
   377  	sourcescripts := filepath.Join(sourcecode, ".s2i", "bin")
   378  	err = os.MkdirAll(sourcescripts, 0777)
   379  	if err != nil {
   380  		t.Errorf("Unable to create injection dir: %v", err)
   381  	}
   382  
   383  	assemble := filepath.Join(sourcescripts, "assemble")
   384  	_, err = os.OpenFile(assemble, os.O_RDONLY|os.O_CREATE, 0666)
   385  	if err != nil {
   386  		t.Errorf("Unable to create assemble file: %v", err)
   387  	}
   388  
   389  	config := &api.Config{
   390  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
   391  		AssembleUser: "",
   392  		ImageWorkDir: "",
   393  		Source:       git.MustParse("file:///" + filepath.ToSlash(sourcecode)),
   394  		ForceCopy:    true,
   395  		ScriptsURL:   "",
   396  		Injections:   api.VolumeList{},
   397  		Destination:  "/destination",
   398  
   399  		Environment: api.EnvironmentList{},
   400  		Labels:      map[string]string{},
   401  
   402  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   403  	}
   404  	expected := []string{
   405  		"(?m)^COPY upload/scripts /destination/scripts",
   406  		"(?m)^RUN chown -R 1001:0.* /destination/scripts",
   407  		"(?m)^RUN /destination/scripts/assemble",
   408  		"(?m)^CMD /usr/libexec/s2i/run",
   409  	}
   410  	expectedFiles := []string{
   411  		filepath.Join(tempdir, "upload/scripts/assemble"),
   412  	}
   413  	runDockerfileTest(t, config, expected, nil, expectedFiles, false)
   414  }
   415  
   416  func TestDockerfileBuildSourceScriptsRun(t *testing.T) {
   417  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   418  	if err != nil {
   419  		t.Errorf("Unable to create temporary directory: %v", err)
   420  	}
   421  	defer os.RemoveAll(tempdir)
   422  
   423  	sourcecode := filepath.Join(tempdir, "sourcecode")
   424  	sourcescripts := filepath.Join(sourcecode, ".s2i", "bin")
   425  	err = os.MkdirAll(sourcescripts, 0777)
   426  	if err != nil {
   427  		t.Errorf("Unable to create injection dir: %v", err)
   428  	}
   429  
   430  	run := filepath.Join(sourcescripts, "run")
   431  	_, err = os.OpenFile(run, os.O_RDONLY|os.O_CREATE, 0666)
   432  	if err != nil {
   433  		t.Errorf("Unable to create run file: %v", err)
   434  	}
   435  
   436  	config := &api.Config{
   437  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
   438  		AssembleUser: "",
   439  		ImageWorkDir: "",
   440  		Source:       git.MustParse("file:///" + filepath.ToSlash(sourcecode)),
   441  		ForceCopy:    true,
   442  		ScriptsURL:   "",
   443  		Injections:   api.VolumeList{},
   444  		Destination:  "/destination",
   445  
   446  		Environment: api.EnvironmentList{},
   447  		Labels:      map[string]string{},
   448  
   449  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   450  	}
   451  	expected := []string{
   452  		"(?m)^COPY upload/scripts /destination/scripts",
   453  		"(?m)^RUN chown -R 1001:0.* /destination/scripts",
   454  		"(?m)^RUN /usr/libexec/s2i/assemble",
   455  		"(?m)^CMD /destination/scripts/run",
   456  	}
   457  	expectedFiles := []string{
   458  		filepath.Join(tempdir, "upload/scripts/run"),
   459  	}
   460  	runDockerfileTest(t, config, expected, nil, expectedFiles, false)
   461  }
   462  
   463  // TestDockerfileBuildScriptsURLImage tests the behavior if the ScriptsURL
   464  // is set to an image:// URL. In this case we blind trust that the image
   465  // contains all of the s2i scripts at the given directory, regardless
   466  // of what is contained in the source.
   467  func TestDockerfileBuildScriptsURLImage(t *testing.T) {
   468  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   469  	if err != nil {
   470  		t.Errorf("Unable to create temporary directory: %v", err)
   471  	}
   472  	defer os.RemoveAll(tempdir)
   473  
   474  	sourcecode := filepath.Join(tempdir, "sourcecode")
   475  	sourcescripts := filepath.Join(sourcecode, ".s2i", "bin")
   476  	err = os.MkdirAll(sourcescripts, 0777)
   477  	if err != nil {
   478  		t.Errorf("Unable to create injection dir: %v", err)
   479  	}
   480  
   481  	assemble := filepath.Join(sourcescripts, "assemble")
   482  	_, err = os.OpenFile(assemble, os.O_RDONLY|os.O_CREATE, 0666)
   483  	if err != nil {
   484  		t.Errorf("Unable to create assemble file: %v", err)
   485  	}
   486  
   487  	config := &api.Config{
   488  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
   489  		AssembleUser: "",
   490  		ImageWorkDir: "",
   491  		Source:       git.MustParse("file:///" + filepath.ToSlash(sourcecode)),
   492  		ForceCopy:    true,
   493  		ScriptsURL:   "image:///usr/custom/s2i",
   494  		Injections:   api.VolumeList{},
   495  		Destination:  "/destination",
   496  
   497  		Environment: api.EnvironmentList{},
   498  		Labels:      map[string]string{},
   499  
   500  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   501  	}
   502  	expected := []string{
   503  		"(?m)^RUN /usr/custom/s2i/assemble",
   504  		"(?m)^CMD /usr/custom/s2i/run",
   505  	}
   506  	notExpected := []string{
   507  		"(?m)^COPY upload/scripts /destination/scripts",
   508  		"(?m)^RUN chown -R 1001:0.* /destination/scripts",
   509  		"(?m)^RUN /destination/scripts/assemble",
   510  	}
   511  	runDockerfileTest(t, config, expected, notExpected, nil, false)
   512  }
   513  
   514  func TestDockerfileBuildImageScriptsURLAssemble(t *testing.T) {
   515  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   516  	if err != nil {
   517  		t.Errorf("Unable to create temporary directory: %v", err)
   518  	}
   519  	defer os.RemoveAll(tempdir)
   520  
   521  	assemble := filepath.Join(tempdir, "assemble")
   522  	_, err = os.OpenFile(assemble, os.O_RDONLY|os.O_CREATE, 0666)
   523  	if err != nil {
   524  		t.Errorf("Unable to create assemble file: %v", err)
   525  	}
   526  
   527  	config := &api.Config{
   528  		BuilderImage:    "docker.io/centos/nodejs-8-centos7",
   529  		AssembleUser:    "",
   530  		ImageWorkDir:    "",
   531  		Source:          git.MustParse("https://github.com/sclorg/nodejs-ex"),
   532  		ImageScriptsURL: "file://" + filepath.ToSlash(tempdir),
   533  		Injections:      api.VolumeList{},
   534  		Destination:     "/destination",
   535  
   536  		Environment: api.EnvironmentList{},
   537  		Labels:      map[string]string{},
   538  
   539  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   540  	}
   541  	expected := []string{
   542  		"(?m)^COPY upload/scripts /destination/scripts",
   543  		"(?m)^RUN chown -R 1001:0.* /destination/scripts",
   544  		"(?m)^RUN /destination/scripts/assemble",
   545  		"(?m)^CMD /usr/libexec/s2i/run",
   546  	}
   547  	expectedFiles := []string{
   548  		filepath.Join(tempdir, "upload/src/server.js"),
   549  		filepath.Join(tempdir, "upload/scripts/assemble"),
   550  	}
   551  	runDockerfileTest(t, config, expected, nil, expectedFiles, false)
   552  }
   553  
   554  func TestDockerfileBuildImageScriptsURLRun(t *testing.T) {
   555  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   556  	if err != nil {
   557  		t.Errorf("Unable to create temporary directory: %v", err)
   558  	}
   559  	defer os.RemoveAll(tempdir)
   560  
   561  	run := filepath.Join(tempdir, "run")
   562  	_, err = os.OpenFile(run, os.O_RDONLY|os.O_CREATE, 0666)
   563  	if err != nil {
   564  		t.Errorf("Unable to create run file: %v", err)
   565  	}
   566  
   567  	config := &api.Config{
   568  		BuilderImage:    "docker.io/centos/nodejs-8-centos7",
   569  		AssembleUser:    "",
   570  		ImageWorkDir:    "",
   571  		Source:          git.MustParse("https://github.com/sclorg/nodejs-ex"),
   572  		ImageScriptsURL: "file://" + filepath.ToSlash(tempdir),
   573  		Injections:      api.VolumeList{},
   574  		Destination:     "/destination",
   575  
   576  		Environment: api.EnvironmentList{},
   577  		Labels:      map[string]string{},
   578  
   579  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   580  	}
   581  	expected := []string{
   582  		"(?m)^COPY upload/scripts /destination/scripts",
   583  		"(?m)^RUN chown -R 1001:0.* /destination/scripts",
   584  		"(?m)^RUN /usr/libexec/s2i/assemble",
   585  		"(?m)^CMD /destination/scripts/run",
   586  	}
   587  	expectedFiles := []string{
   588  		filepath.Join(tempdir, "upload/src/server.js"),
   589  		filepath.Join(tempdir, "upload/scripts/run"),
   590  	}
   591  	runDockerfileTest(t, config, expected, nil, expectedFiles, false)
   592  }
   593  
   594  func TestDockerfileBuildImageScriptsURLImage(t *testing.T) {
   595  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   596  	if err != nil {
   597  		t.Errorf("Unable to create temporary directory: %v", err)
   598  	}
   599  	defer os.RemoveAll(tempdir)
   600  
   601  	sourcecode := filepath.Join(tempdir, "sourcecode")
   602  	sourcescripts := filepath.Join(sourcecode, ".s2i", "bin")
   603  	err = os.MkdirAll(sourcescripts, 0777)
   604  	if err != nil {
   605  		t.Errorf("Unable to create injection dir: %v", err)
   606  	}
   607  
   608  	assemble := filepath.Join(sourcescripts, "assemble")
   609  	_, err = os.OpenFile(assemble, os.O_RDONLY|os.O_CREATE, 0666)
   610  	if err != nil {
   611  		t.Errorf("Unable to create assemble file: %v", err)
   612  	}
   613  
   614  	config := &api.Config{
   615  		BuilderImage:    "docker.io/centos/nodejs-8-centos7",
   616  		AssembleUser:    "",
   617  		ImageWorkDir:    "",
   618  		Source:          git.MustParse("file:///" + filepath.ToSlash(sourcecode)),
   619  		ForceCopy:       true,
   620  		ImageScriptsURL: "image:///usr/custom/s2i",
   621  		Injections:      api.VolumeList{},
   622  		Destination:     "/destination",
   623  
   624  		Environment: api.EnvironmentList{},
   625  		Labels:      map[string]string{},
   626  
   627  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   628  	}
   629  	expected := []string{
   630  		"(?m)^COPY upload/scripts /destination/scripts",
   631  		"(?m)^RUN chown -R 1001:0.* /destination/scripts",
   632  		"(?m)^RUN /destination/scripts/assemble",
   633  		"(?m)^CMD /usr/custom/s2i/run",
   634  	}
   635  	expectedFiles := []string{
   636  		filepath.Join(tempdir, "upload/scripts/assemble"),
   637  	}
   638  	runDockerfileTest(t, config, expected, nil, expectedFiles, false)
   639  }
   640  
   641  func TestDockerfileBuildScriptsAndImageURL(t *testing.T) {
   642  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   643  	if err != nil {
   644  		t.Errorf("Unable to create temporary directory: %v", err)
   645  	}
   646  	defer os.RemoveAll(tempdir)
   647  
   648  	assemble := filepath.Join(tempdir, "assemble")
   649  	_, err = os.OpenFile(assemble, os.O_RDONLY|os.O_CREATE, 0666)
   650  	if err != nil {
   651  		t.Errorf("Unable to create assemble file: %v", err)
   652  	}
   653  
   654  	config := &api.Config{
   655  		BuilderImage:    "docker.io/centos/nodejs-8-centos7",
   656  		AssembleUser:    "",
   657  		ImageWorkDir:    "",
   658  		Source:          git.MustParse("https://github.com/sclorg/nodejs-ex"),
   659  		ScriptsURL:      "file://" + filepath.ToSlash(tempdir),
   660  		ImageScriptsURL: "image:///usr/some/dir",
   661  		Injections:      api.VolumeList{},
   662  		Destination:     "/destination",
   663  
   664  		Environment: api.EnvironmentList{},
   665  		Labels:      map[string]string{},
   666  
   667  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   668  	}
   669  	expected := []string{
   670  		"(?m)^COPY upload/scripts /destination/scripts",
   671  		"(?m)^RUN chown -R 1001:0.* /destination/scripts",
   672  		"(?m)^RUN /destination/scripts/assemble",
   673  		"(?m)^CMD /usr/some/dir/run",
   674  	}
   675  	expectedFiles := []string{
   676  		filepath.Join(tempdir, "upload/src/server.js"),
   677  		filepath.Join(tempdir, "upload/scripts/assemble"),
   678  	}
   679  	runDockerfileTest(t, config, expected, nil, expectedFiles, false)
   680  }
   681  
   682  // TestDockerfileBuildScriptsAndImageURLConflicts tests if both
   683  // the ScriptsURL and ImageScriptsURL point to a non-image directory.
   684  // In this event, the ScriptsURL value should take precedence.
   685  func TestDockerfileBuildScriptsAndImageURLConflicts(t *testing.T) {
   686  	scriptsTempDir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   687  	if err != nil {
   688  		t.Errorf("Unable to create temporary directory: %v", err)
   689  	}
   690  	defer os.RemoveAll(scriptsTempDir)
   691  
   692  	imageTempDir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   693  	if err != nil {
   694  		t.Errorf("Unable to create temporary directory: %v", err)
   695  	}
   696  	defer os.RemoveAll(imageTempDir)
   697  
   698  	outputDir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   699  	if err != nil {
   700  		t.Errorf("Unable to create temporary directory: %v", err)
   701  	}
   702  	defer os.RemoveAll(outputDir)
   703  
   704  	scriptsAssemble := filepath.Join(scriptsTempDir, "assemble")
   705  	assembleData := []byte("#!/bin/bash\necho \"Hello World!\"")
   706  	err = ioutil.WriteFile(scriptsAssemble, assembleData, 0666)
   707  	if err != nil {
   708  		t.Errorf("Unable to create image assemble file: %v", err)
   709  	}
   710  
   711  	imageAssemble := filepath.Join(imageTempDir, "assemble")
   712  	_, err = os.OpenFile(imageAssemble, os.O_RDONLY|os.O_CREATE, 0666)
   713  	if err != nil {
   714  		t.Errorf("Unable to create assemble file: %v", err)
   715  	}
   716  
   717  	config := &api.Config{
   718  		BuilderImage:    "docker.io/centos/nodejs-8-centos7",
   719  		AssembleUser:    "",
   720  		ImageWorkDir:    "",
   721  		Source:          git.MustParse("https://github.com/sclorg/nodejs-ex"),
   722  		ScriptsURL:      "file://" + filepath.ToSlash(scriptsTempDir),
   723  		ImageScriptsURL: "file://" + filepath.ToSlash(imageTempDir),
   724  		Injections:      api.VolumeList{},
   725  		Destination:     "/destination",
   726  
   727  		Environment: api.EnvironmentList{},
   728  		Labels:      map[string]string{},
   729  
   730  		AsDockerfile: filepath.Join(outputDir, "Dockerfile"),
   731  	}
   732  	expected := []string{
   733  		"(?m)^COPY upload/scripts /destination/scripts",
   734  		"(?m)^RUN chown -R 1001:0.* /destination/scripts",
   735  		"(?m)^RUN /destination/scripts/assemble",
   736  		"(?m)^CMD /usr/libexec/s2i/run",
   737  	}
   738  	expectedFiles := []string{
   739  		filepath.Join(outputDir, "upload/src/server.js"),
   740  		filepath.Join(outputDir, "upload/scripts/assemble"),
   741  	}
   742  	runDockerfileTest(t, config, expected, nil, expectedFiles, false)
   743  	dockerfileAssemble, err := ioutil.ReadFile(filepath.Join(outputDir, "upload/scripts/assemble"))
   744  	if err != nil {
   745  		t.Errorf("Failed to read uploaded assemble script: %v", err)
   746  	}
   747  	if string(dockerfileAssemble) != string(assembleData) {
   748  		t.Errorf("Expected uploaded assemble script:\n\n%s\n\nto be:\n\n%s", dockerfileAssemble, assembleData)
   749  	}
   750  }
   751  
   752  func TestDockerfileIncrementalBuild(t *testing.T) {
   753  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   754  	if err != nil {
   755  		t.Errorf("Unable to create temporary directory: %v", err)
   756  	}
   757  	defer os.RemoveAll(tempdir)
   758  
   759  	config := &api.Config{
   760  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
   761  		AssembleUser: "",
   762  		ImageWorkDir: "",
   763  		Incremental:  true,
   764  		Source:       git.MustParse("https://github.com/sclorg/nodejs-ex"),
   765  		ScriptsURL:   "",
   766  		Tag:          "test:tag",
   767  		Injections:   api.VolumeList{},
   768  		Destination:  "",
   769  
   770  		Environment: api.EnvironmentList{},
   771  		Labels:      map[string]string{},
   772  
   773  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   774  	}
   775  
   776  	expected := []string{
   777  		"(?m)^FROM test:tag as cached\n#.+\nUSER 1001",
   778  		"(?m)^RUN if \\[ -s /usr/libexec/s2i/save-artifacts \\]; then /usr/libexec/s2i/save-artifacts > /tmp/artifacts.tar; else touch /tmp/artifacts.tar; fi",
   779  		"(?m)^FROM docker.io/centos/nodejs-8-centos7",
   780  		"(?m)^COPY --from=cached /tmp/artifacts.tar /tmp/artifacts.tar",
   781  		"(?m)^RUN chown -R 1001:0.* /tmp/artifacts.tar",
   782  		"if \\[ -s /tmp/artifacts.tar \\]; then mkdir -p /tmp/artifacts; tar -xf /tmp/artifacts.tar -C /tmp/artifacts; fi",
   783  		"rm /tmp/artifacts.tar",
   784  		"(?m)^COPY upload/src /tmp/src",
   785  		"(?m)^RUN chown -R 1001:0.* /tmp/src",
   786  		"(?m)^RUN /usr/libexec/s2i/assemble",
   787  		"(?m)^CMD /usr/libexec/s2i/run",
   788  	}
   789  
   790  	runDockerfileTest(t, config, expected, nil, nil, false)
   791  }
   792  
   793  func TestDockerfileIncrementalSourceSave(t *testing.T) {
   794  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   795  	if err != nil {
   796  		t.Errorf("Unable to create temporary directory: %v", err)
   797  	}
   798  	defer os.RemoveAll(tempdir)
   799  
   800  	sourcecode := filepath.Join(tempdir, "sourcecode")
   801  	sourcescripts := filepath.Join(sourcecode, ".s2i", "bin")
   802  	err = os.MkdirAll(sourcescripts, 0777)
   803  	if err != nil {
   804  		t.Errorf("Unable to create injection dir: %v", err)
   805  	}
   806  
   807  	saveArtifacts := filepath.Join(sourcescripts, "save-artifacts")
   808  	_, err = os.OpenFile(saveArtifacts, os.O_RDONLY|os.O_CREATE, 0666)
   809  	if err != nil {
   810  		t.Errorf("Unable to create save-artifacts file: %v", err)
   811  	}
   812  
   813  	config := &api.Config{
   814  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
   815  		AssembleUser: "",
   816  		ImageWorkDir: "",
   817  		Incremental:  true,
   818  		Source:       git.MustParse("file:///" + filepath.ToSlash(sourcecode)),
   819  		ScriptsURL:   "",
   820  		Tag:          "test:tag",
   821  		Injections:   api.VolumeList{},
   822  		Destination:  "/destination",
   823  
   824  		Environment: api.EnvironmentList{},
   825  		Labels:      map[string]string{},
   826  
   827  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   828  	}
   829  
   830  	expected := []string{
   831  		"(?m)^FROM test:tag as cached\n#.+\nUSER root\n",
   832  		"(?m)^COPY upload/scripts/save-artifacts /destination/scripts/save-artifacts",
   833  		"(?m)^RUN chown .*1001:0 /destination/scripts/save-artifacts",
   834  		"(?m)^USER 1001\nRUN if \\[ -s /destination/scripts/save-artifacts \\]; then /destination/scripts/save-artifacts > /tmp/artifacts.tar;",
   835  		"(?m)^FROM docker.io/centos/nodejs-8-centos7",
   836  		"mkdir -p /destination/artifacts",
   837  		"tar -xf /tmp/artifacts.tar -C /destination/artifacts",
   838  		"(?m)^RUN /usr/libexec/s2i/assemble",
   839  		"(?m)^CMD /usr/libexec/s2i/run",
   840  	}
   841  	expectedFiles := []string{
   842  		filepath.Join(tempdir, "upload/scripts/save-artifacts"),
   843  	}
   844  
   845  	runDockerfileTest(t, config, expected, nil, expectedFiles, false)
   846  }
   847  
   848  func TestDockerfileIncrementalSaveURL(t *testing.T) {
   849  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   850  	if err != nil {
   851  		t.Errorf("Unable to create temporary directory: %v", err)
   852  	}
   853  	defer os.RemoveAll(tempdir)
   854  
   855  	saveArtifacts := filepath.Join(tempdir, "save-artifacts")
   856  	_, err = os.OpenFile(saveArtifacts, os.O_RDONLY|os.O_CREATE, 0666)
   857  	if err != nil {
   858  		t.Errorf("Unable to create save-artifacts file: %v", err)
   859  	}
   860  
   861  	config := &api.Config{
   862  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
   863  		AssembleUser: "",
   864  		ImageWorkDir: "",
   865  		Incremental:  true,
   866  		Source:       git.MustParse("https://github.com/sclorg/nodejs-ex"),
   867  		ScriptsURL:   "file://" + filepath.ToSlash(tempdir),
   868  		Tag:          "test:tag",
   869  		Injections:   api.VolumeList{},
   870  		Destination:  "/destination",
   871  
   872  		Environment: api.EnvironmentList{},
   873  		Labels:      map[string]string{},
   874  
   875  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   876  	}
   877  
   878  	expected := []string{
   879  		"(?m)^FROM test:tag as cached\n#.+\nUSER root\n",
   880  		"(?m)^COPY upload/scripts/save-artifacts /destination/scripts/save-artifacts",
   881  		"(?m)^RUN chown 1001:0 /destination/scripts/save-artifacts",
   882  		"(?m)^USER 1001\nRUN if \\[ -s /destination/scripts/save-artifacts \\]; then /destination/scripts/save-artifacts > /tmp/artifacts.tar;",
   883  		"(?m)^FROM docker.io/centos/nodejs-8-centos7",
   884  		"mkdir -p /destination/artifacts",
   885  		"tar -xf /tmp/artifacts.tar -C /destination/artifacts",
   886  		"(?m)^RUN /usr/libexec/s2i/assemble",
   887  		"(?m)^CMD /usr/libexec/s2i/run",
   888  	}
   889  	expectedFiles := []string{
   890  		filepath.Join(tempdir, "upload/scripts/save-artifacts"),
   891  	}
   892  
   893  	runDockerfileTest(t, config, expected, nil, expectedFiles, false)
   894  }
   895  
   896  func TestDockerfileIncrementalTag(t *testing.T) {
   897  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   898  	if err != nil {
   899  		t.Errorf("Unable to create temporary directory: %v", err)
   900  	}
   901  	defer os.RemoveAll(tempdir)
   902  
   903  	config := &api.Config{
   904  		BuilderImage:       "docker.io/centos/nodejs-8-centos7",
   905  		AssembleUser:       "",
   906  		ImageWorkDir:       "",
   907  		Incremental:        true,
   908  		Source:             git.MustParse("https://github.com/sclorg/nodejs-ex"),
   909  		Tag:                "test:tag",
   910  		IncrementalFromTag: "incremental:tag",
   911  
   912  		Environment: api.EnvironmentList{},
   913  		Labels:      map[string]string{},
   914  
   915  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   916  	}
   917  
   918  	expected := []string{
   919  		"(?m)^FROM incremental:tag as cached",
   920  		"/usr/libexec/s2i/save-artifacts > /tmp/artifacts.tar",
   921  		"(?m)^FROM docker.io/centos/nodejs-8-centos7",
   922  		"mkdir -p /tmp/artifacts",
   923  		"tar -xf /tmp/artifacts.tar -C /tmp/artifacts",
   924  		"rm /tmp/artifacts.tar",
   925  		"(?m)^RUN /usr/libexec/s2i/assemble",
   926  		"(?m)^CMD /usr/libexec/s2i/run",
   927  	}
   928  
   929  	runDockerfileTest(t, config, expected, nil, nil, false)
   930  }
   931  
   932  func TestDockerfileIncrementalAssembleUser(t *testing.T) {
   933  	tempdir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   934  	if err != nil {
   935  		t.Errorf("Unable to create temporary directory: %v", err)
   936  	}
   937  	defer os.RemoveAll(tempdir)
   938  
   939  	config := &api.Config{
   940  		BuilderImage: "docker.io/centos/nodejs-8-centos7",
   941  		AssembleUser: "2250",
   942  		ImageWorkDir: "",
   943  		Incremental:  true,
   944  		Source:       git.MustParse("https://github.com/sclorg/nodejs-ex"),
   945  		Tag:          "test:tag",
   946  		Environment:  api.EnvironmentList{},
   947  		Labels:       map[string]string{},
   948  
   949  		AsDockerfile: filepath.Join(tempdir, "Dockerfile"),
   950  	}
   951  
   952  	expected := []string{
   953  		"(?m)^FROM test:tag as cached\n#.+\nUSER 2250",
   954  		"/usr/libexec/s2i/save-artifacts > /tmp/artifacts.tar",
   955  		"(?m)^FROM docker.io/centos/nodejs-8-centos7",
   956  		"(?m)^COPY --from=cached /tmp/artifacts.tar /tmp/artifacts.tar",
   957  		"(?m)^RUN chown -R 2250:0 .*/tmp/artifacts.tar",
   958  		"mkdir -p /tmp/artifacts",
   959  		"tar -xf /tmp/artifacts.tar -C /tmp/artifacts",
   960  		"rm /tmp/artifacts.tar",
   961  		"(?m)^RUN /usr/libexec/s2i/assemble",
   962  		"(?m)^CMD /usr/libexec/s2i/run",
   963  	}
   964  
   965  	runDockerfileTest(t, config, expected, nil, nil, false)
   966  }
   967  
   968  func TestDockerfileLocalSource(t *testing.T) {
   969  	localTempDir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   970  	if err != nil {
   971  		t.Errorf("Unable to create temporary directory: %v", err)
   972  	}
   973  	defer os.RemoveAll(localTempDir)
   974  
   975  	outputDir, err := ioutil.TempDir("", "s2i-dockerfiletest-dir")
   976  	if err != nil {
   977  		t.Errorf("Unable to create temporary directory: %v", err)
   978  	}
   979  	defer os.RemoveAll(outputDir)
   980  
   981  	config := &api.Config{
   982  		BuilderImage: "sti_test/sti-fake",
   983  		Source:       git.MustParse("file:///" + filepath.ToSlash(localTempDir)),
   984  		AsDockerfile: filepath.Join(outputDir, "Dockerfile"),
   985  	}
   986  
   987  	dirTree := []string{
   988  		"foo/bar",
   989  		"foo/baz/foobar",
   990  	}
   991  	for _, dirName := range dirTree {
   992  		err = os.MkdirAll(filepath.Join(localTempDir, dirName), 0777)
   993  		if err != nil {
   994  			t.Errorf("Unable to create dir: %v", err)
   995  		}
   996  	}
   997  
   998  	fileTree := []string{
   999  		"foo/a_file",
  1000  		"foo/bar/a_file",
  1001  		"foo/bar/another_file",
  1002  		"foo/baz/foobar/a_file",
  1003  	}
  1004  	for _, fileName := range fileTree {
  1005  		dummyContent := []byte("Hello World!")
  1006  		err = ioutil.WriteFile(filepath.Join(localTempDir, fileName), dummyContent, 0666)
  1007  		if err != nil {
  1008  			t.Errorf("Unable to create file: %v", err)
  1009  		}
  1010  	}
  1011  
  1012  	expectedFiles := []string{
  1013  		filepath.Join(outputDir, "upload/src/foo/a_file"),
  1014  		filepath.Join(outputDir, "upload/src/foo/bar"),
  1015  		filepath.Join(outputDir, "upload/src/foo/bar/a_file"),
  1016  		filepath.Join(outputDir, "upload/src/foo/bar/another_file"),
  1017  		filepath.Join(outputDir, "upload/src/foo/baz/foobar"),
  1018  		filepath.Join(outputDir, "upload/src/foo/baz/foobar/a_file"),
  1019  	}
  1020  
  1021  	runDockerfileTest(t, config, nil, nil, expectedFiles, false)
  1022  
  1023  	s2iignore := filepath.Join(localTempDir, ".s2iignore")
  1024  	s2iignoreDate := []byte("dummy\n#skip_file\nfoo/bar/another_file\nfoo/baz/foobar")
  1025  	err = ioutil.WriteFile(s2iignore, s2iignoreDate, 0666)
  1026  	if err != nil {
  1027  		t.Errorf("Unable to create .s2iignore file: %v", err)
  1028  	}
  1029  
  1030  	expectedFiles = []string{
  1031  		filepath.Join(outputDir, "upload/src/foo/a_file"),
  1032  		filepath.Join(outputDir, "upload/src/foo/bar"),
  1033  		filepath.Join(outputDir, "upload/src/foo/bar/a_file"),
  1034  	}
  1035  
  1036  	runDockerfileTest(t, config, nil, nil, expectedFiles, false)
  1037  }
  1038  
  1039  func runDockerfileTest(t *testing.T, config *api.Config, expected []string, notExpected []string, expectedFiles []string, expectFailure bool) {
  1040  
  1041  	b, _, err := strategies.Strategy(nil, config, build.Overrides{})
  1042  	if err != nil {
  1043  		t.Fatalf("Cannot create a new builder.")
  1044  	}
  1045  	resp, err := b.Build(config)
  1046  	if expectFailure {
  1047  		if err == nil || resp.Success {
  1048  			t.Errorf("The build succeded when it should have failed. Success: %t, error: %v", resp.Success, err)
  1049  		}
  1050  		return
  1051  	}
  1052  	if err != nil {
  1053  		t.Fatalf("An error occurred during the build: %v", err)
  1054  	}
  1055  	if !resp.Success {
  1056  		t.Fatalf("The build failed when it should have succeeded.")
  1057  	}
  1058  
  1059  	filebytes, err := ioutil.ReadFile(config.AsDockerfile)
  1060  	if err != nil {
  1061  		t.Fatalf("An error occurred reading the dockerfile: %v", err)
  1062  	}
  1063  	dockerfile := string(filebytes)
  1064  
  1065  	buf := bytes.NewBuffer(filebytes)
  1066  	_, err = parser.Parse(buf)
  1067  	if err != nil {
  1068  		t.Fatalf("An error occurred parsing the dockerfile: %v\n%s", err, dockerfile)
  1069  	}
  1070  
  1071  	for _, s := range expected {
  1072  		reg, err := regexp.Compile(s)
  1073  		if err != nil {
  1074  			t.Fatalf("failed to compile regex %q: %v", s, err)
  1075  		}
  1076  		if !reg.MatchString(dockerfile) {
  1077  			t.Fatalf("Expected dockerfile to contain %s, it did not: \n%s", s, dockerfile)
  1078  		}
  1079  	}
  1080  	for _, s := range notExpected {
  1081  		reg, err := regexp.Compile(s)
  1082  		if err != nil {
  1083  			t.Fatalf("failed to compile regex %q: %v", s, err)
  1084  		}
  1085  		if reg.MatchString(dockerfile) {
  1086  			t.Fatalf("Expected dockerfile not to contain %s, it did: \n%s", s, dockerfile)
  1087  		}
  1088  	}
  1089  	for _, f := range expectedFiles {
  1090  		if _, err := os.Stat(f); os.IsNotExist(err) {
  1091  			t.Fatalf("Did not find expected file %s, ", f)
  1092  		}
  1093  	}
  1094  }