github.com/nathanielks/terraform@v0.6.1-0.20170509030759-13e1a62319dc/builtin/provisioners/chef/resource_provisioner_test.go (about)

     1  package chef
     2  
     3  import (
     4  	"fmt"
     5  	"path"
     6  	"testing"
     7  
     8  	"github.com/hashicorp/terraform/communicator"
     9  	"github.com/hashicorp/terraform/config"
    10  	"github.com/hashicorp/terraform/terraform"
    11  )
    12  
    13  func TestResourceProvisioner_impl(t *testing.T) {
    14  	var _ terraform.ResourceProvisioner = new(ResourceProvisioner)
    15  }
    16  
    17  func TestResourceProvider_Validate_good(t *testing.T) {
    18  	c := testConfig(t, map[string]interface{}{
    19  		"environment": "_default",
    20  		"node_name":   "nodename1",
    21  		"run_list":    []interface{}{"cookbook::recipe"},
    22  		"server_url":  "https://chef.local",
    23  		"user_name":   "bob",
    24  		"user_key":    "USER-KEY",
    25  	})
    26  	r := new(ResourceProvisioner)
    27  	warn, errs := r.Validate(c)
    28  	if len(warn) > 0 {
    29  		t.Fatalf("Warnings: %v", warn)
    30  	}
    31  	if len(errs) > 0 {
    32  		t.Fatalf("Errors: %v", errs)
    33  	}
    34  }
    35  
    36  func TestResourceProvider_Validate_bad(t *testing.T) {
    37  	c := testConfig(t, map[string]interface{}{
    38  		"invalid": "nope",
    39  	})
    40  	p := new(ResourceProvisioner)
    41  	warn, errs := p.Validate(c)
    42  	if len(warn) > 0 {
    43  		t.Fatalf("Warnings: %v", warn)
    44  	}
    45  	if len(errs) == 0 {
    46  		t.Fatalf("Should have errors")
    47  	}
    48  }
    49  
    50  // Test that the JSON attributes with an unknown value don't
    51  // validate.
    52  func TestResourceProvider_Validate_computedValues(t *testing.T) {
    53  	c := testConfig(t, map[string]interface{}{
    54  		"environment":     "_default",
    55  		"node_name":       "nodename1",
    56  		"run_list":        []interface{}{"cookbook::recipe"},
    57  		"server_url":      "https://chef.local",
    58  		"user_name":       "bob",
    59  		"user_key":        "USER-KEY",
    60  		"attributes_json": config.UnknownVariableValue,
    61  	})
    62  	r := new(ResourceProvisioner)
    63  	warn, errs := r.Validate(c)
    64  	if len(warn) > 0 {
    65  		t.Fatalf("Warnings: %v", warn)
    66  	}
    67  	if len(errs) > 0 {
    68  		t.Fatalf("Errors: %v", errs)
    69  	}
    70  }
    71  
    72  func testConfig(t *testing.T, c map[string]interface{}) *terraform.ResourceConfig {
    73  	r, err := config.NewRawConfig(c)
    74  	if err != nil {
    75  		t.Fatalf("bad: %s", err)
    76  	}
    77  
    78  	return terraform.NewResourceConfig(r)
    79  }
    80  
    81  func TestResourceProvider_runChefClient(t *testing.T) {
    82  	cases := map[string]struct {
    83  		Config   *terraform.ResourceConfig
    84  		ChefCmd  string
    85  		ConfDir  string
    86  		Commands map[string]bool
    87  	}{
    88  		"Sudo": {
    89  			Config: testConfig(t, map[string]interface{}{
    90  				"node_name":  "nodename1",
    91  				"run_list":   []interface{}{"cookbook::recipe"},
    92  				"server_url": "https://chef.local",
    93  				"user_name":  "bob",
    94  				"user_key":   "USER-KEY",
    95  			}),
    96  
    97  			ChefCmd: linuxChefCmd,
    98  
    99  			ConfDir: linuxConfDir,
   100  
   101  			Commands: map[string]bool{
   102  				fmt.Sprintf(`sudo %s -j %q -E "_default"`,
   103  					linuxChefCmd,
   104  					path.Join(linuxConfDir, "first-boot.json")): true,
   105  			},
   106  		},
   107  
   108  		"NoSudo": {
   109  			Config: testConfig(t, map[string]interface{}{
   110  				"node_name":    "nodename1",
   111  				"prevent_sudo": true,
   112  				"run_list":     []interface{}{"cookbook::recipe"},
   113  				"server_url":   "https://chef.local",
   114  				"user_name":    "bob",
   115  				"user_key":     "USER-KEY",
   116  			}),
   117  
   118  			ChefCmd: linuxChefCmd,
   119  
   120  			ConfDir: linuxConfDir,
   121  
   122  			Commands: map[string]bool{
   123  				fmt.Sprintf(`%s -j %q -E "_default"`,
   124  					linuxChefCmd,
   125  					path.Join(linuxConfDir, "first-boot.json")): true,
   126  			},
   127  		},
   128  
   129  		"Environment": {
   130  			Config: testConfig(t, map[string]interface{}{
   131  				"environment":  "production",
   132  				"node_name":    "nodename1",
   133  				"prevent_sudo": true,
   134  				"run_list":     []interface{}{"cookbook::recipe"},
   135  				"server_url":   "https://chef.local",
   136  				"user_name":    "bob",
   137  				"user_key":     "USER-KEY",
   138  			}),
   139  
   140  			ChefCmd: windowsChefCmd,
   141  
   142  			ConfDir: windowsConfDir,
   143  
   144  			Commands: map[string]bool{
   145  				fmt.Sprintf(`%s -j %q -E "production"`,
   146  					windowsChefCmd,
   147  					path.Join(windowsConfDir, "first-boot.json")): true,
   148  			},
   149  		},
   150  	}
   151  
   152  	r := new(ResourceProvisioner)
   153  	o := new(terraform.MockUIOutput)
   154  	c := new(communicator.MockCommunicator)
   155  
   156  	for k, tc := range cases {
   157  		c.Commands = tc.Commands
   158  
   159  		p, err := r.decodeConfig(tc.Config)
   160  		if err != nil {
   161  			t.Fatalf("Error: %v", err)
   162  		}
   163  
   164  		p.runChefClient = p.runChefClientFunc(tc.ChefCmd, tc.ConfDir)
   165  		p.useSudo = !p.PreventSudo
   166  
   167  		err = p.runChefClient(o, c)
   168  		if err != nil {
   169  			t.Fatalf("Test %q failed: %v", k, err)
   170  		}
   171  	}
   172  }
   173  
   174  func TestResourceProvider_fetchChefCertificates(t *testing.T) {
   175  	cases := map[string]struct {
   176  		Config   *terraform.ResourceConfig
   177  		KnifeCmd string
   178  		ConfDir  string
   179  		Commands map[string]bool
   180  	}{
   181  		"Sudo": {
   182  			Config: testConfig(t, map[string]interface{}{
   183  				"fetch_chef_certificates": true,
   184  				"node_name":               "nodename1",
   185  				"run_list":                []interface{}{"cookbook::recipe"},
   186  				"server_url":              "https://chef.local",
   187  				"user_name":               "bob",
   188  				"user_key":                "USER-KEY",
   189  			}),
   190  
   191  			KnifeCmd: linuxKnifeCmd,
   192  
   193  			ConfDir: linuxConfDir,
   194  
   195  			Commands: map[string]bool{
   196  				fmt.Sprintf(`sudo %s ssl fetch -c %s`,
   197  					linuxKnifeCmd,
   198  					path.Join(linuxConfDir, "client.rb")): true,
   199  			},
   200  		},
   201  
   202  		"NoSudo": {
   203  			Config: testConfig(t, map[string]interface{}{
   204  				"fetch_chef_certificates": true,
   205  				"node_name":               "nodename1",
   206  				"prevent_sudo":            true,
   207  				"run_list":                []interface{}{"cookbook::recipe"},
   208  				"server_url":              "https://chef.local",
   209  				"user_name":               "bob",
   210  				"user_key":                "USER-KEY",
   211  			}),
   212  
   213  			KnifeCmd: windowsKnifeCmd,
   214  
   215  			ConfDir: windowsConfDir,
   216  
   217  			Commands: map[string]bool{
   218  				fmt.Sprintf(`%s ssl fetch -c %s`,
   219  					windowsKnifeCmd,
   220  					path.Join(windowsConfDir, "client.rb")): true,
   221  			},
   222  		},
   223  	}
   224  
   225  	r := new(ResourceProvisioner)
   226  	o := new(terraform.MockUIOutput)
   227  	c := new(communicator.MockCommunicator)
   228  
   229  	for k, tc := range cases {
   230  		c.Commands = tc.Commands
   231  
   232  		p, err := r.decodeConfig(tc.Config)
   233  		if err != nil {
   234  			t.Fatalf("Error: %v", err)
   235  		}
   236  
   237  		p.fetchChefCertificates = p.fetchChefCertificatesFunc(tc.KnifeCmd, tc.ConfDir)
   238  		p.useSudo = !p.PreventSudo
   239  
   240  		err = p.fetchChefCertificates(o, c)
   241  		if err != nil {
   242  			t.Fatalf("Test %q failed: %v", k, err)
   243  		}
   244  	}
   245  }
   246  
   247  func TestResourceProvider_configureVaults(t *testing.T) {
   248  	cases := map[string]struct {
   249  		Config   *terraform.ResourceConfig
   250  		GemCmd   string
   251  		KnifeCmd string
   252  		ConfDir  string
   253  		Commands map[string]bool
   254  	}{
   255  		"Linux Vault string": {
   256  			Config: testConfig(t, map[string]interface{}{
   257  				"node_name":    "nodename1",
   258  				"prevent_sudo": true,
   259  				"run_list":     []interface{}{"cookbook::recipe"},
   260  				"server_url":   "https://chef.local",
   261  				"user_name":    "bob",
   262  				"user_key":     "USER-KEY",
   263  				"vault_json":   `{"vault1": "item1"}`,
   264  			}),
   265  
   266  			GemCmd:   linuxGemCmd,
   267  			KnifeCmd: linuxKnifeCmd,
   268  			ConfDir:  linuxConfDir,
   269  
   270  			Commands: map[string]bool{
   271  				fmt.Sprintf("%s install chef-vault", linuxGemCmd): true,
   272  				fmt.Sprintf("%s vault update vault1 item1 -C nodename1 -M client -c %s/client.rb "+
   273  					"-u bob --key %s/bob.pem", linuxKnifeCmd, linuxConfDir, linuxConfDir): true,
   274  			},
   275  		},
   276  
   277  		"Linux Vault []string": {
   278  			Config: testConfig(t, map[string]interface{}{
   279  				"fetch_chef_certificates": true,
   280  				"node_name":               "nodename1",
   281  				"prevent_sudo":            true,
   282  				"run_list":                []interface{}{"cookbook::recipe"},
   283  				"server_url":              "https://chef.local",
   284  				"user_name":               "bob",
   285  				"user_key":                "USER-KEY",
   286  				"vault_json":              `{"vault1": ["item1", "item2"]}`,
   287  			}),
   288  
   289  			GemCmd:   linuxGemCmd,
   290  			KnifeCmd: linuxKnifeCmd,
   291  			ConfDir:  linuxConfDir,
   292  
   293  			Commands: map[string]bool{
   294  				fmt.Sprintf("%s install chef-vault", linuxGemCmd): true,
   295  				fmt.Sprintf("%s vault update vault1 item1 -C nodename1 -M client -c %s/client.rb "+
   296  					"-u bob --key %s/bob.pem", linuxKnifeCmd, linuxConfDir, linuxConfDir): true,
   297  				fmt.Sprintf("%s vault update vault1 item2 -C nodename1 -M client -c %s/client.rb "+
   298  					"-u bob --key %s/bob.pem", linuxKnifeCmd, linuxConfDir, linuxConfDir): true,
   299  			},
   300  		},
   301  
   302  		"Windows Vault string": {
   303  			Config: testConfig(t, map[string]interface{}{
   304  				"node_name":    "nodename1",
   305  				"prevent_sudo": true,
   306  				"run_list":     []interface{}{"cookbook::recipe"},
   307  				"server_url":   "https://chef.local",
   308  				"user_name":    "bob",
   309  				"user_key":     "USER-KEY",
   310  				"vault_json":   `{"vault1": "item1"}`,
   311  			}),
   312  
   313  			GemCmd:   windowsGemCmd,
   314  			KnifeCmd: windowsKnifeCmd,
   315  			ConfDir:  windowsConfDir,
   316  
   317  			Commands: map[string]bool{
   318  				fmt.Sprintf("%s install chef-vault", windowsGemCmd): true,
   319  				fmt.Sprintf("%s vault update vault1 item1 -C nodename1 -M client -c %s/client.rb "+
   320  					"-u bob --key %s/bob.pem", windowsKnifeCmd, windowsConfDir, windowsConfDir): true,
   321  			},
   322  		},
   323  
   324  		"Windows Vault []string": {
   325  			Config: testConfig(t, map[string]interface{}{
   326  				"fetch_chef_certificates": true,
   327  				"node_name":               "nodename1",
   328  				"prevent_sudo":            true,
   329  				"run_list":                []interface{}{"cookbook::recipe"},
   330  				"server_url":              "https://chef.local",
   331  				"user_name":               "bob",
   332  				"user_key":                "USER-KEY",
   333  				"vault_json":              `{"vault1": ["item1", "item2"]}`,
   334  			}),
   335  
   336  			GemCmd:   windowsGemCmd,
   337  			KnifeCmd: windowsKnifeCmd,
   338  			ConfDir:  windowsConfDir,
   339  
   340  			Commands: map[string]bool{
   341  				fmt.Sprintf("%s install chef-vault", windowsGemCmd): true,
   342  				fmt.Sprintf("%s vault update vault1 item1 -C nodename1 -M client -c %s/client.rb "+
   343  					"-u bob --key %s/bob.pem", windowsKnifeCmd, windowsConfDir, windowsConfDir): true,
   344  				fmt.Sprintf("%s vault update vault1 item2 -C nodename1 -M client -c %s/client.rb "+
   345  					"-u bob --key %s/bob.pem", windowsKnifeCmd, windowsConfDir, windowsConfDir): true,
   346  			},
   347  		},
   348  	}
   349  
   350  	r := new(ResourceProvisioner)
   351  	o := new(terraform.MockUIOutput)
   352  	c := new(communicator.MockCommunicator)
   353  
   354  	for k, tc := range cases {
   355  		c.Commands = tc.Commands
   356  
   357  		p, err := r.decodeConfig(tc.Config)
   358  		if err != nil {
   359  			t.Fatalf("Error: %v", err)
   360  		}
   361  
   362  		p.configureVaults = p.configureVaultsFunc(tc.GemCmd, tc.KnifeCmd, tc.ConfDir)
   363  		p.useSudo = !p.PreventSudo
   364  
   365  		err = p.configureVaults(o, c)
   366  		if err != nil {
   367  			t.Fatalf("Test %q failed: %v", k, err)
   368  		}
   369  	}
   370  }