github.com/dacamp/packer@v0.10.2/provisioner/shell/provisioner_test.go (about)

     1  package shell
     2  
     3  import (
     4  	"github.com/mitchellh/packer/packer"
     5  	"io/ioutil"
     6  	"os"
     7  	"testing"
     8  	"strings"
     9  	"regexp"
    10  )
    11  
    12  func testConfig() map[string]interface{} {
    13  	return map[string]interface{}{
    14  		"inline": []interface{}{"foo", "bar"},
    15  	}
    16  }
    17  
    18  func TestProvisioner_Impl(t *testing.T) {
    19  	var raw interface{}
    20  	raw = &Provisioner{}
    21  	if _, ok := raw.(packer.Provisioner); !ok {
    22  		t.Fatalf("must be a Provisioner")
    23  	}
    24  }
    25  
    26  func TestProvisionerPrepare_Defaults(t *testing.T) {
    27  	var p Provisioner
    28  	config := testConfig()
    29  
    30  	err := p.Prepare(config)
    31  	if err != nil {
    32  		t.Fatalf("err: %s", err)
    33  	}
    34  
    35  	if p.config.RemotePath == "" {
    36  		t.Errorf("unexpected remote path: %s", p.config.RemotePath)
    37  	}
    38  }
    39  
    40  func TestProvisionerPrepare_InlineShebang(t *testing.T) {
    41  	config := testConfig()
    42  
    43  	delete(config, "inline_shebang")
    44  	p := new(Provisioner)
    45  	err := p.Prepare(config)
    46  	if err != nil {
    47  		t.Fatalf("should not have error: %s", err)
    48  	}
    49  
    50  	if p.config.InlineShebang != "/bin/sh -e" {
    51  		t.Fatalf("bad value: %s", p.config.InlineShebang)
    52  	}
    53  
    54  	// Test with a good one
    55  	config["inline_shebang"] = "foo"
    56  	p = new(Provisioner)
    57  	err = p.Prepare(config)
    58  	if err != nil {
    59  		t.Fatalf("should not have error: %s", err)
    60  	}
    61  
    62  	if p.config.InlineShebang != "foo" {
    63  		t.Fatalf("bad value: %s", p.config.InlineShebang)
    64  	}
    65  }
    66  
    67  func TestProvisionerPrepare_InvalidKey(t *testing.T) {
    68  	var p Provisioner
    69  	config := testConfig()
    70  
    71  	// Add a random key
    72  	config["i_should_not_be_valid"] = true
    73  	err := p.Prepare(config)
    74  	if err == nil {
    75  		t.Fatal("should have error")
    76  	}
    77  }
    78  
    79  func TestProvisionerPrepare_Script(t *testing.T) {
    80  	config := testConfig()
    81  	delete(config, "inline")
    82  
    83  	config["script"] = "/this/should/not/exist"
    84  	p := new(Provisioner)
    85  	err := p.Prepare(config)
    86  	if err == nil {
    87  		t.Fatal("should have error")
    88  	}
    89  
    90  	// Test with a good one
    91  	tf, err := ioutil.TempFile("", "packer")
    92  	if err != nil {
    93  		t.Fatalf("error tempfile: %s", err)
    94  	}
    95  	defer os.Remove(tf.Name())
    96  
    97  	config["script"] = tf.Name()
    98  	p = new(Provisioner)
    99  	err = p.Prepare(config)
   100  	if err != nil {
   101  		t.Fatalf("should not have error: %s", err)
   102  	}
   103  }
   104  
   105  func TestProvisionerPrepare_ScriptAndInline(t *testing.T) {
   106  	var p Provisioner
   107  	config := testConfig()
   108  
   109  	delete(config, "inline")
   110  	delete(config, "script")
   111  	err := p.Prepare(config)
   112  	if err == nil {
   113  		t.Fatal("should have error")
   114  	}
   115  
   116  	// Test with both
   117  	tf, err := ioutil.TempFile("", "packer")
   118  	if err != nil {
   119  		t.Fatalf("error tempfile: %s", err)
   120  	}
   121  	defer os.Remove(tf.Name())
   122  
   123  	config["inline"] = []interface{}{"foo"}
   124  	config["script"] = tf.Name()
   125  	err = p.Prepare(config)
   126  	if err == nil {
   127  		t.Fatal("should have error")
   128  	}
   129  }
   130  
   131  func TestProvisionerPrepare_ScriptAndScripts(t *testing.T) {
   132  	var p Provisioner
   133  	config := testConfig()
   134  
   135  	// Test with both
   136  	tf, err := ioutil.TempFile("", "packer")
   137  	if err != nil {
   138  		t.Fatalf("error tempfile: %s", err)
   139  	}
   140  	defer os.Remove(tf.Name())
   141  
   142  	config["inline"] = []interface{}{"foo"}
   143  	config["scripts"] = []string{tf.Name()}
   144  	err = p.Prepare(config)
   145  	if err == nil {
   146  		t.Fatal("should have error")
   147  	}
   148  }
   149  
   150  func TestProvisionerPrepare_Scripts(t *testing.T) {
   151  	config := testConfig()
   152  	delete(config, "inline")
   153  
   154  	config["scripts"] = []string{}
   155  	p := new(Provisioner)
   156  	err := p.Prepare(config)
   157  	if err == nil {
   158  		t.Fatal("should have error")
   159  	}
   160  
   161  	// Test with a good one
   162  	tf, err := ioutil.TempFile("", "packer")
   163  	if err != nil {
   164  		t.Fatalf("error tempfile: %s", err)
   165  	}
   166  	defer os.Remove(tf.Name())
   167  
   168  	config["scripts"] = []string{tf.Name()}
   169  	p = new(Provisioner)
   170  	err = p.Prepare(config)
   171  	if err != nil {
   172  		t.Fatalf("should not have error: %s", err)
   173  	}
   174  }
   175  
   176  func TestProvisionerPrepare_EnvironmentVars(t *testing.T) {
   177  	config := testConfig()
   178  
   179  	// Test with a bad case
   180  	config["environment_vars"] = []string{"badvar", "good=var"}
   181  	p := new(Provisioner)
   182  	err := p.Prepare(config)
   183  	if err == nil {
   184  		t.Fatal("should have error")
   185  	}
   186  
   187  	// Test with a trickier case
   188  	config["environment_vars"] = []string{"=bad"}
   189  	p = new(Provisioner)
   190  	err = p.Prepare(config)
   191  	if err == nil {
   192  		t.Fatal("should have error")
   193  	}
   194  
   195  	// Test with a good case
   196  	// Note: baz= is a real env variable, just empty
   197  	config["environment_vars"] = []string{"FOO=bar", "baz="}
   198  	p = new(Provisioner)
   199  	err = p.Prepare(config)
   200  	if err != nil {
   201  		t.Fatalf("should not have error: %s", err)
   202  	}
   203  }
   204  
   205  func TestProvisionerQuote_EnvironmentVars(t *testing.T) {
   206  	config := testConfig()
   207  
   208  	config["environment_vars"] = []string{"keyone=valueone", "keytwo=value\ntwo"}
   209  	p := new(Provisioner)
   210  	p.Prepare(config)
   211  
   212  	expectedValue := "keyone='valueone'"
   213  	if p.config.Vars[0] != expectedValue {
   214  		t.Fatalf("%s should be equal to %s", p.config.Vars[0], expectedValue)
   215  	}
   216  
   217  	expectedValue = "keytwo='value\ntwo'"
   218  	if p.config.Vars[1] != expectedValue {
   219  		t.Fatalf("%s should be equal to %s", p.config.Vars[1], expectedValue)
   220  	}
   221  }
   222  
   223  func TestProvisioner_RemoteFolderSetSuccessfully(t *testing.T) {
   224  	config := testConfig()
   225  
   226  	expectedRemoteFolder := "/example/path"
   227  	config["remote_folder"] = expectedRemoteFolder
   228  
   229  	p := new(Provisioner)
   230  	err := p.Prepare(config)
   231  	if err != nil {
   232  		t.Fatalf("should not have error: %s", err)
   233  	}
   234  
   235  	if !strings.Contains(p.config.RemotePath, expectedRemoteFolder) {
   236  		t.Fatalf("remote path does not contain remote_folder")
   237  	}
   238  }
   239  
   240  func TestProvisioner_RemoteFolderDefaultsToTmp(t *testing.T) {
   241  	config := testConfig()
   242  
   243  	p := new(Provisioner)
   244  	err := p.Prepare(config)
   245  	if err != nil {
   246  		t.Fatalf("should not have error: %s", err)
   247  	}
   248  
   249  	if p.config.RemoteFolder != "/tmp" {
   250  		t.Fatalf("remote_folder did not default to /tmp")
   251  	}
   252  
   253  	if !strings.Contains(p.config.RemotePath, "/tmp") {
   254  		t.Fatalf("remote path does not contain remote_folder")
   255  	}
   256  }
   257  
   258  func TestProvisioner_RemoteFileSetSuccessfully(t *testing.T) {
   259  	config := testConfig()
   260  
   261  	expectedRemoteFile := "example.sh"
   262  	config["remote_file"] = expectedRemoteFile
   263  
   264  	p := new(Provisioner)
   265  	err := p.Prepare(config)
   266  	if err != nil {
   267  		t.Fatalf("should not have error: %s", err)
   268  	}
   269  
   270  	if !strings.Contains(p.config.RemotePath, expectedRemoteFile) {
   271  		t.Fatalf("remote path does not contain remote_file")
   272  	}
   273  }
   274  
   275  func TestProvisioner_RemoteFileDefaultsToScriptnnnn(t *testing.T) {
   276  	config := testConfig()
   277  
   278  	p := new(Provisioner)
   279  	err := p.Prepare(config)
   280  	if err != nil {
   281  		t.Fatalf("should not have error: %s", err)
   282  	}
   283  
   284  	remoteFileRegex := regexp.MustCompile("script_[0-9]{4}.sh")
   285  
   286  	if !remoteFileRegex.MatchString(p.config.RemoteFile) {
   287  		t.Fatalf("remote_file did not default to script_nnnn.sh")
   288  	}
   289  
   290  	if !remoteFileRegex.MatchString(p.config.RemotePath) {
   291  		t.Fatalf("remote_path did not match script_nnnn.sh")
   292  	}
   293  }
   294  
   295  func TestProvisioner_RemotePathSetViaRemotePathAndRemoteFile(t *testing.T) {
   296  	config := testConfig()
   297  
   298  	expectedRemoteFile := "example.sh"
   299  	expectedRemoteFolder := "/example/path"
   300  	config["remote_file"] = expectedRemoteFile
   301  	config["remote_folder"] = expectedRemoteFolder
   302  
   303  	p := new(Provisioner)
   304  	err := p.Prepare(config)
   305  	if err != nil {
   306  		t.Fatalf("should not have error: %s", err)
   307  	}
   308  
   309  	if p.config.RemotePath != expectedRemoteFolder + "/" + expectedRemoteFile {
   310  		t.Fatalf("remote path does not contain remote_file")
   311  	}
   312  }
   313  
   314  func TestProvisioner_RemotePathOverridesRemotePathAndRemoteFile(t *testing.T) {
   315  	config := testConfig()
   316  
   317  	expectedRemoteFile := "example.sh"
   318  	expectedRemoteFolder := "/example/path"
   319  	expectedRemotePath := "/example/remote/path/script.sh"
   320  	config["remote_file"] = expectedRemoteFile
   321  	config["remote_folder"] = expectedRemoteFolder
   322  	config["remote_path"] = expectedRemotePath
   323  
   324  	p := new(Provisioner)
   325  	err := p.Prepare(config)
   326  	if err != nil {
   327  		t.Fatalf("should not have error: %s", err)
   328  	}
   329  
   330  	if p.config.RemotePath != expectedRemotePath {
   331  		t.Fatalf("remote path does not contain remote_path")
   332  	}
   333  }
   334  
   335  func TestProvisionerRemotePathDefaultsSuccessfully(t *testing.T) {
   336  	config := testConfig()
   337  
   338  	p := new(Provisioner)
   339  	err := p.Prepare(config)
   340  	if err != nil {
   341  		t.Fatalf("should not have error: %s", err)
   342  	}
   343  
   344  	remotePathRegex := regexp.MustCompile("/tmp/script_[0-9]{4}.sh")
   345  
   346  	if !remotePathRegex.MatchString(p.config.RemotePath) {
   347  		t.Fatalf("remote path does not match the expected default regex")
   348  	}
   349  }