github.com/subuk/terraform@v0.6.14-0.20160317140351-de1567c2e732/command/untaint_test.go (about) 1 package command 2 3 import ( 4 "os" 5 "strings" 6 "testing" 7 8 "github.com/hashicorp/terraform/terraform" 9 "github.com/mitchellh/cli" 10 ) 11 12 func TestUntaint(t *testing.T) { 13 state := &terraform.State{ 14 Modules: []*terraform.ModuleState{ 15 &terraform.ModuleState{ 16 Path: []string{"root"}, 17 Resources: map[string]*terraform.ResourceState{ 18 "test_instance.foo": &terraform.ResourceState{ 19 Type: "test_instance", 20 Tainted: []*terraform.InstanceState{ 21 &terraform.InstanceState{ID: "bar"}, 22 }, 23 }, 24 }, 25 }, 26 }, 27 } 28 statePath := testStateFile(t, state) 29 30 ui := new(cli.MockUi) 31 c := &UntaintCommand{ 32 Meta: Meta{ 33 Ui: ui, 34 }, 35 } 36 37 args := []string{ 38 "-state", statePath, 39 "test_instance.foo", 40 } 41 if code := c.Run(args); code != 0 { 42 t.Fatalf("bad: %d\n\n%s", code, ui.ErrorWriter.String()) 43 } 44 45 expected := strings.TrimSpace(` 46 test_instance.foo: 47 ID = bar 48 `) 49 testStateOutput(t, statePath, expected) 50 } 51 52 func TestUntaint_indexRequired(t *testing.T) { 53 state := &terraform.State{ 54 Modules: []*terraform.ModuleState{ 55 &terraform.ModuleState{ 56 Path: []string{"root"}, 57 Resources: map[string]*terraform.ResourceState{ 58 "test_instance.foo": &terraform.ResourceState{ 59 Type: "test_instance", 60 Tainted: []*terraform.InstanceState{ 61 &terraform.InstanceState{ID: "bar"}, 62 &terraform.InstanceState{ID: "bar2"}, 63 }, 64 }, 65 }, 66 }, 67 }, 68 } 69 statePath := testStateFile(t, state) 70 71 ui := new(cli.MockUi) 72 c := &UntaintCommand{ 73 Meta: Meta{ 74 Ui: ui, 75 }, 76 } 77 78 args := []string{ 79 "-state", statePath, 80 "test_instance.foo", 81 } 82 if code := c.Run(args); code == 0 { 83 t.Fatalf("Expected non-zero exit. Output:\n\n%s", ui.OutputWriter.String()) 84 } 85 86 // Nothing should have gotten untainted 87 expected := strings.TrimSpace(` 88 test_instance.foo: (2 tainted) 89 ID = <not created> 90 Tainted ID 1 = bar 91 Tainted ID 2 = bar2 92 `) 93 testStateOutput(t, statePath, expected) 94 95 // Should have gotten an error message mentioning index 96 errOut := ui.ErrorWriter.String() 97 errContains := "please specify an index" 98 if !strings.Contains(errOut, errContains) { 99 t.Fatalf("Expected err output: %s, to contain: %s", errOut, errContains) 100 } 101 } 102 103 func TestUntaint_indexSpecified(t *testing.T) { 104 state := &terraform.State{ 105 Modules: []*terraform.ModuleState{ 106 &terraform.ModuleState{ 107 Path: []string{"root"}, 108 Resources: map[string]*terraform.ResourceState{ 109 "test_instance.foo": &terraform.ResourceState{ 110 Type: "test_instance", 111 Tainted: []*terraform.InstanceState{ 112 &terraform.InstanceState{ID: "bar"}, 113 &terraform.InstanceState{ID: "bar2"}, 114 }, 115 }, 116 }, 117 }, 118 }, 119 } 120 statePath := testStateFile(t, state) 121 122 ui := new(cli.MockUi) 123 c := &UntaintCommand{ 124 Meta: Meta{ 125 Ui: ui, 126 }, 127 } 128 129 args := []string{ 130 "-state", statePath, 131 "-index", "1", 132 "test_instance.foo", 133 } 134 if code := c.Run(args); code != 0 { 135 t.Fatalf("bad: %d\n\n%s", code, ui.ErrorWriter.String()) 136 } 137 138 // Nothing should have gotten untainted 139 expected := strings.TrimSpace(` 140 test_instance.foo: (1 tainted) 141 ID = bar2 142 Tainted ID 1 = bar 143 `) 144 testStateOutput(t, statePath, expected) 145 } 146 147 func TestUntaint_backup(t *testing.T) { 148 // Get a temp cwd 149 tmp, cwd := testCwd(t) 150 defer testFixCwd(t, tmp, cwd) 151 152 // Write the temp state 153 state := &terraform.State{ 154 Modules: []*terraform.ModuleState{ 155 &terraform.ModuleState{ 156 Path: []string{"root"}, 157 Resources: map[string]*terraform.ResourceState{ 158 "test_instance.foo": &terraform.ResourceState{ 159 Type: "test_instance", 160 Tainted: []*terraform.InstanceState{ 161 &terraform.InstanceState{ID: "bar"}, 162 }, 163 }, 164 }, 165 }, 166 }, 167 } 168 path := testStateFileDefault(t, state) 169 170 ui := new(cli.MockUi) 171 c := &UntaintCommand{ 172 Meta: Meta{ 173 Ui: ui, 174 }, 175 } 176 177 args := []string{ 178 "test_instance.foo", 179 } 180 if code := c.Run(args); code != 0 { 181 t.Fatalf("bad: %d\n\n%s", code, ui.ErrorWriter.String()) 182 } 183 184 // Backup is still tainted 185 testStateOutput(t, path+".backup", strings.TrimSpace(` 186 test_instance.foo: (1 tainted) 187 ID = <not created> 188 Tainted ID 1 = bar 189 `)) 190 191 // State is untainted 192 testStateOutput(t, path, strings.TrimSpace(` 193 test_instance.foo: 194 ID = bar 195 `)) 196 } 197 198 func TestUntaint_backupDisable(t *testing.T) { 199 // Get a temp cwd 200 tmp, cwd := testCwd(t) 201 defer testFixCwd(t, tmp, cwd) 202 203 // Write the temp state 204 state := &terraform.State{ 205 Modules: []*terraform.ModuleState{ 206 &terraform.ModuleState{ 207 Path: []string{"root"}, 208 Resources: map[string]*terraform.ResourceState{ 209 "test_instance.foo": &terraform.ResourceState{ 210 Type: "test_instance", 211 Tainted: []*terraform.InstanceState{ 212 &terraform.InstanceState{ID: "bar"}, 213 }, 214 }, 215 }, 216 }, 217 }, 218 } 219 path := testStateFileDefault(t, state) 220 221 ui := new(cli.MockUi) 222 c := &UntaintCommand{ 223 Meta: Meta{ 224 Ui: ui, 225 }, 226 } 227 228 args := []string{ 229 "-backup", "-", 230 "test_instance.foo", 231 } 232 if code := c.Run(args); code != 0 { 233 t.Fatalf("bad: %d\n\n%s", code, ui.ErrorWriter.String()) 234 } 235 236 if _, err := os.Stat(path + ".backup"); err == nil { 237 t.Fatal("backup path should not exist") 238 } 239 240 testStateOutput(t, path, strings.TrimSpace(` 241 test_instance.foo: 242 ID = bar 243 `)) 244 } 245 246 func TestUntaint_badState(t *testing.T) { 247 ui := new(cli.MockUi) 248 c := &UntaintCommand{ 249 Meta: Meta{ 250 Ui: ui, 251 }, 252 } 253 254 args := []string{ 255 "-state", "i-should-not-exist-ever", 256 "foo", 257 } 258 if code := c.Run(args); code != 1 { 259 t.Fatalf("bad: %d\n\n%s", code, ui.ErrorWriter.String()) 260 } 261 } 262 263 func TestUntaint_defaultState(t *testing.T) { 264 // Get a temp cwd 265 tmp, cwd := testCwd(t) 266 defer testFixCwd(t, tmp, cwd) 267 268 // Write the temp state 269 state := &terraform.State{ 270 Modules: []*terraform.ModuleState{ 271 &terraform.ModuleState{ 272 Path: []string{"root"}, 273 Resources: map[string]*terraform.ResourceState{ 274 "test_instance.foo": &terraform.ResourceState{ 275 Type: "test_instance", 276 Tainted: []*terraform.InstanceState{ 277 &terraform.InstanceState{ID: "bar"}, 278 }, 279 }, 280 }, 281 }, 282 }, 283 } 284 path := testStateFileDefault(t, state) 285 286 ui := new(cli.MockUi) 287 c := &UntaintCommand{ 288 Meta: Meta{ 289 Ui: ui, 290 }, 291 } 292 293 args := []string{ 294 "test_instance.foo", 295 } 296 if code := c.Run(args); code != 0 { 297 t.Fatalf("bad: %d\n\n%s", code, ui.ErrorWriter.String()) 298 } 299 300 testStateOutput(t, path, strings.TrimSpace(` 301 test_instance.foo: 302 ID = bar 303 `)) 304 } 305 306 func TestUntaint_missing(t *testing.T) { 307 state := &terraform.State{ 308 Modules: []*terraform.ModuleState{ 309 &terraform.ModuleState{ 310 Path: []string{"root"}, 311 Resources: map[string]*terraform.ResourceState{ 312 "test_instance.foo": &terraform.ResourceState{ 313 Type: "test_instance", 314 Tainted: []*terraform.InstanceState{ 315 &terraform.InstanceState{ID: "bar"}, 316 }, 317 }, 318 }, 319 }, 320 }, 321 } 322 statePath := testStateFile(t, state) 323 324 ui := new(cli.MockUi) 325 c := &UntaintCommand{ 326 Meta: Meta{ 327 Ui: ui, 328 }, 329 } 330 331 args := []string{ 332 "-state", statePath, 333 "test_instance.bar", 334 } 335 if code := c.Run(args); code == 0 { 336 t.Fatalf("bad: %d\n\n%s", code, ui.OutputWriter.String()) 337 } 338 } 339 340 func TestUntaint_missingAllow(t *testing.T) { 341 state := &terraform.State{ 342 Modules: []*terraform.ModuleState{ 343 &terraform.ModuleState{ 344 Path: []string{"root"}, 345 Resources: map[string]*terraform.ResourceState{ 346 "test_instance.foo": &terraform.ResourceState{ 347 Type: "test_instance", 348 Tainted: []*terraform.InstanceState{ 349 &terraform.InstanceState{ID: "bar"}, 350 }, 351 }, 352 }, 353 }, 354 }, 355 } 356 statePath := testStateFile(t, state) 357 358 ui := new(cli.MockUi) 359 c := &UntaintCommand{ 360 Meta: Meta{ 361 Ui: ui, 362 }, 363 } 364 365 args := []string{ 366 "-allow-missing", 367 "-state", statePath, 368 "test_instance.bar", 369 } 370 if code := c.Run(args); code != 0 { 371 t.Fatalf("bad: %d\n\n%s", code, ui.ErrorWriter.String()) 372 } 373 } 374 375 func TestUntaint_stateOut(t *testing.T) { 376 // Get a temp cwd 377 tmp, cwd := testCwd(t) 378 defer testFixCwd(t, tmp, cwd) 379 380 // Write the temp state 381 state := &terraform.State{ 382 Modules: []*terraform.ModuleState{ 383 &terraform.ModuleState{ 384 Path: []string{"root"}, 385 Resources: map[string]*terraform.ResourceState{ 386 "test_instance.foo": &terraform.ResourceState{ 387 Type: "test_instance", 388 Tainted: []*terraform.InstanceState{ 389 &terraform.InstanceState{ID: "bar"}, 390 }, 391 }, 392 }, 393 }, 394 }, 395 } 396 path := testStateFileDefault(t, state) 397 398 ui := new(cli.MockUi) 399 c := &UntaintCommand{ 400 Meta: Meta{ 401 Ui: ui, 402 }, 403 } 404 405 args := []string{ 406 "-state-out", "foo", 407 "test_instance.foo", 408 } 409 if code := c.Run(args); code != 0 { 410 t.Fatalf("bad: %d\n\n%s", code, ui.ErrorWriter.String()) 411 } 412 413 testStateOutput(t, path, strings.TrimSpace(` 414 test_instance.foo: (1 tainted) 415 ID = <not created> 416 Tainted ID 1 = bar 417 `)) 418 testStateOutput(t, "foo", strings.TrimSpace(` 419 test_instance.foo: 420 ID = bar 421 `)) 422 } 423 424 func TestUntaint_module(t *testing.T) { 425 state := &terraform.State{ 426 Modules: []*terraform.ModuleState{ 427 &terraform.ModuleState{ 428 Path: []string{"root"}, 429 Resources: map[string]*terraform.ResourceState{ 430 "test_instance.foo": &terraform.ResourceState{ 431 Type: "test_instance", 432 Tainted: []*terraform.InstanceState{ 433 &terraform.InstanceState{ID: "bar"}, 434 }, 435 }, 436 }, 437 }, 438 &terraform.ModuleState{ 439 Path: []string{"root", "child"}, 440 Resources: map[string]*terraform.ResourceState{ 441 "test_instance.blah": &terraform.ResourceState{ 442 Type: "test_instance", 443 Tainted: []*terraform.InstanceState{ 444 &terraform.InstanceState{ID: "bar"}, 445 }, 446 }, 447 }, 448 }, 449 }, 450 } 451 statePath := testStateFile(t, state) 452 453 ui := new(cli.MockUi) 454 c := &UntaintCommand{ 455 Meta: Meta{ 456 Ui: ui, 457 }, 458 } 459 460 args := []string{ 461 "-module=child", 462 "-state", statePath, 463 "test_instance.blah", 464 } 465 if code := c.Run(args); code != 0 { 466 t.Fatalf("bad: %d\n\n%s", code, ui.ErrorWriter.String()) 467 } 468 469 testStateOutput(t, statePath, strings.TrimSpace(` 470 test_instance.foo: (1 tainted) 471 ID = <not created> 472 Tainted ID 1 = bar 473 474 module.child: 475 test_instance.blah: 476 ID = bar 477 `)) 478 }