github.com/loggregator/cli@v6.33.1-0.20180224010324-82334f081791+incompatible/actor/v3action/application_test.go (about) 1 package v3action_test 2 3 import ( 4 "errors" 5 "fmt" 6 "strings" 7 "time" 8 9 "code.cloudfoundry.org/cli/actor/actionerror" 10 . "code.cloudfoundry.org/cli/actor/v3action" 11 "code.cloudfoundry.org/cli/actor/v3action/v3actionfakes" 12 "code.cloudfoundry.org/cli/api/cloudcontroller/ccerror" 13 "code.cloudfoundry.org/cli/api/cloudcontroller/ccv3" 14 "code.cloudfoundry.org/cli/api/cloudcontroller/ccv3/constant" 15 16 . "github.com/onsi/ginkgo" 17 . "github.com/onsi/gomega" 18 ) 19 20 var _ = Describe("Application Actions", func() { 21 var ( 22 actor *Actor 23 fakeCloudControllerClient *v3actionfakes.FakeCloudControllerClient 24 fakeConfig *v3actionfakes.FakeConfig 25 ) 26 27 BeforeEach(func() { 28 fakeCloudControllerClient = new(v3actionfakes.FakeCloudControllerClient) 29 fakeConfig = new(v3actionfakes.FakeConfig) 30 actor = NewActor(fakeCloudControllerClient, fakeConfig, nil, nil) 31 }) 32 33 Describe("DeleteApplicationByNameAndSpace", func() { 34 var ( 35 warnings Warnings 36 executeErr error 37 ) 38 39 JustBeforeEach(func() { 40 warnings, executeErr = actor.DeleteApplicationByNameAndSpace("some-app", "some-space-guid") 41 }) 42 43 Context("when looking up the app guid fails", func() { 44 BeforeEach(func() { 45 fakeCloudControllerClient.GetApplicationsReturns([]ccv3.Application{}, ccv3.Warnings{"some-get-app-warning"}, errors.New("some-get-app-error")) 46 }) 47 48 It("returns the warnings and error", func() { 49 Expect(warnings).To(ConsistOf("some-get-app-warning")) 50 Expect(executeErr).To(MatchError("some-get-app-error")) 51 }) 52 }) 53 54 Context("when looking up the app guid succeeds", func() { 55 BeforeEach(func() { 56 fakeCloudControllerClient.GetApplicationsReturns([]ccv3.Application{ccv3.Application{Name: "some-app", GUID: "abc123"}}, ccv3.Warnings{"some-get-app-warning"}, nil) 57 }) 58 59 Context("when sending the delete fails", func() { 60 BeforeEach(func() { 61 fakeCloudControllerClient.DeleteApplicationReturns("", ccv3.Warnings{"some-delete-app-warning"}, errors.New("some-delete-app-error")) 62 }) 63 64 It("returns the warnings and error", func() { 65 Expect(warnings).To(ConsistOf("some-get-app-warning", "some-delete-app-warning")) 66 Expect(executeErr).To(MatchError("some-delete-app-error")) 67 }) 68 }) 69 70 Context("when sending the delete succeeds", func() { 71 BeforeEach(func() { 72 fakeCloudControllerClient.DeleteApplicationReturns("/some-job-url", ccv3.Warnings{"some-delete-app-warning"}, nil) 73 }) 74 75 Context("when polling fails", func() { 76 BeforeEach(func() { 77 fakeCloudControllerClient.PollJobReturns(ccv3.Warnings{"some-poll-warning"}, errors.New("some-poll-error")) 78 }) 79 80 It("returns the warnings and poll error", func() { 81 Expect(warnings).To(ConsistOf("some-get-app-warning", "some-delete-app-warning", "some-poll-warning")) 82 Expect(executeErr).To(MatchError("some-poll-error")) 83 }) 84 }) 85 86 Context("when polling succeeds", func() { 87 BeforeEach(func() { 88 fakeCloudControllerClient.PollJobReturns(ccv3.Warnings{"some-poll-warning"}, nil) 89 }) 90 91 It("returns all the warnings and no error", func() { 92 Expect(warnings).To(ConsistOf("some-get-app-warning", "some-delete-app-warning", "some-poll-warning")) 93 Expect(executeErr).ToNot(HaveOccurred()) 94 }) 95 }) 96 }) 97 }) 98 }) 99 100 Describe("GetApplicationByNameAndSpace", func() { 101 Context("when the app exists", func() { 102 BeforeEach(func() { 103 fakeCloudControllerClient.GetApplicationsReturns( 104 []ccv3.Application{ 105 { 106 Name: "some-app-name", 107 GUID: "some-app-guid", 108 }, 109 }, 110 ccv3.Warnings{"some-warning"}, 111 nil, 112 ) 113 }) 114 115 It("returns the application and warnings", func() { 116 app, warnings, err := actor.GetApplicationByNameAndSpace("some-app-name", "some-space-guid") 117 Expect(err).ToNot(HaveOccurred()) 118 Expect(app).To(Equal(Application{ 119 Name: "some-app-name", 120 GUID: "some-app-guid", 121 })) 122 Expect(warnings).To(Equal(Warnings{"some-warning"})) 123 124 Expect(fakeCloudControllerClient.GetApplicationsCallCount()).To(Equal(1)) 125 Expect(fakeCloudControllerClient.GetApplicationsArgsForCall(0)).To(ConsistOf( 126 ccv3.Query{Key: ccv3.NameFilter, Values: []string{"some-app-name"}}, 127 ccv3.Query{Key: ccv3.SpaceGUIDFilter, Values: []string{"some-space-guid"}}, 128 )) 129 }) 130 }) 131 132 Context("when the cloud controller client returns an error", func() { 133 var expectedError error 134 135 BeforeEach(func() { 136 expectedError = errors.New("I am a CloudControllerClient Error") 137 fakeCloudControllerClient.GetApplicationsReturns( 138 []ccv3.Application{}, 139 ccv3.Warnings{"some-warning"}, 140 expectedError) 141 }) 142 143 It("returns the warnings and the error", func() { 144 _, warnings, err := actor.GetApplicationByNameAndSpace("some-app-name", "some-space-guid") 145 Expect(warnings).To(ConsistOf("some-warning")) 146 Expect(err).To(MatchError(expectedError)) 147 }) 148 }) 149 150 Context("when the app does not exist", func() { 151 BeforeEach(func() { 152 fakeCloudControllerClient.GetApplicationsReturns( 153 []ccv3.Application{}, 154 ccv3.Warnings{"some-warning"}, 155 nil, 156 ) 157 }) 158 159 It("returns an ApplicationNotFoundError and the warnings", func() { 160 _, warnings, err := actor.GetApplicationByNameAndSpace("some-app-name", "some-space-guid") 161 Expect(warnings).To(ConsistOf("some-warning")) 162 Expect(err).To(MatchError(actionerror.ApplicationNotFoundError{Name: "some-app-name"})) 163 }) 164 }) 165 }) 166 167 Describe("GetApplicationsBySpace", func() { 168 Context("when the there are applications in the space", func() { 169 BeforeEach(func() { 170 fakeCloudControllerClient.GetApplicationsReturns( 171 []ccv3.Application{ 172 { 173 GUID: "some-app-guid-1", 174 Name: "some-app-1", 175 }, 176 { 177 GUID: "some-app-guid-2", 178 Name: "some-app-2", 179 }, 180 }, 181 ccv3.Warnings{"warning-1", "warning-2"}, 182 nil, 183 ) 184 }) 185 186 It("returns the application and warnings", func() { 187 apps, warnings, err := actor.GetApplicationsBySpace("some-space-guid") 188 Expect(err).ToNot(HaveOccurred()) 189 Expect(apps).To(ConsistOf( 190 Application{ 191 GUID: "some-app-guid-1", 192 Name: "some-app-1", 193 }, 194 Application{ 195 GUID: "some-app-guid-2", 196 Name: "some-app-2", 197 }, 198 )) 199 Expect(warnings).To(ConsistOf("warning-1", "warning-2")) 200 201 Expect(fakeCloudControllerClient.GetApplicationsCallCount()).To(Equal(1)) 202 Expect(fakeCloudControllerClient.GetApplicationsArgsForCall(0)).To(ConsistOf( 203 ccv3.Query{Key: ccv3.SpaceGUIDFilter, Values: []string{"some-space-guid"}}, 204 )) 205 }) 206 }) 207 208 Context("when the cloud controller client returns an error", func() { 209 var expectedError error 210 211 BeforeEach(func() { 212 expectedError = errors.New("I am a CloudControllerClient Error") 213 fakeCloudControllerClient.GetApplicationsReturns( 214 []ccv3.Application{}, 215 ccv3.Warnings{"some-warning"}, 216 expectedError) 217 }) 218 219 It("returns the error and warnings", func() { 220 _, warnings, err := actor.GetApplicationsBySpace("some-space-guid") 221 Expect(warnings).To(ConsistOf("some-warning")) 222 Expect(err).To(MatchError(expectedError)) 223 }) 224 }) 225 }) 226 227 Describe("CreateApplicationInSpace", func() { 228 var ( 229 application Application 230 warnings Warnings 231 err error 232 ) 233 234 JustBeforeEach(func() { 235 application, warnings, err = actor.CreateApplicationInSpace(Application{ 236 Name: "some-app-name", 237 LifecycleType: constant.BuildpackAppLifecycleType, 238 LifecycleBuildpacks: []string{"buildpack-1", "buildpack-2"}, 239 }, "some-space-guid") 240 }) 241 242 Context("when the app successfully gets created", func() { 243 BeforeEach(func() { 244 fakeCloudControllerClient.CreateApplicationReturns( 245 ccv3.Application{ 246 Name: "some-app-name", 247 GUID: "some-app-guid", 248 LifecycleType: constant.BuildpackAppLifecycleType, 249 LifecycleBuildpacks: []string{"buildpack-1", "buildpack-2"}, 250 }, 251 ccv3.Warnings{"some-warning"}, 252 nil, 253 ) 254 }) 255 256 It("creates and returns the application and warnings", func() { 257 Expect(err).ToNot(HaveOccurred()) 258 Expect(application).To(Equal(Application{ 259 Name: "some-app-name", 260 GUID: "some-app-guid", 261 LifecycleType: constant.BuildpackAppLifecycleType, 262 LifecycleBuildpacks: []string{"buildpack-1", "buildpack-2"}, 263 })) 264 Expect(warnings).To(ConsistOf("some-warning")) 265 266 Expect(fakeCloudControllerClient.CreateApplicationCallCount()).To(Equal(1)) 267 Expect(fakeCloudControllerClient.CreateApplicationArgsForCall(0)).To(Equal(ccv3.Application{ 268 Name: "some-app-name", 269 Relationships: ccv3.Relationships{ 270 constant.SpaceRelationship: ccv3.Relationship{GUID: "some-space-guid"}, 271 }, 272 LifecycleType: constant.BuildpackAppLifecycleType, 273 LifecycleBuildpacks: []string{"buildpack-1", "buildpack-2"}, 274 })) 275 }) 276 }) 277 278 Context("when the cc client returns an error", func() { 279 var expectedError error 280 281 BeforeEach(func() { 282 expectedError = errors.New("I am a CloudControllerClient Error") 283 fakeCloudControllerClient.CreateApplicationReturns( 284 ccv3.Application{}, 285 ccv3.Warnings{"some-warning"}, 286 expectedError, 287 ) 288 }) 289 290 It("raises the error and warnings", func() { 291 Expect(err).To(MatchError(expectedError)) 292 Expect(warnings).To(ConsistOf("some-warning")) 293 }) 294 }) 295 296 Context("when the cc client returns an NameNotUniqueInSpaceError", func() { 297 BeforeEach(func() { 298 fakeCloudControllerClient.CreateApplicationReturns( 299 ccv3.Application{}, 300 ccv3.Warnings{"some-warning"}, 301 ccerror.NameNotUniqueInSpaceError{}, 302 ) 303 }) 304 305 It("returns the ApplicationAlreadyExistsError and warnings", func() { 306 Expect(err).To(MatchError(actionerror.ApplicationAlreadyExistsError{Name: "some-app-name"})) 307 Expect(warnings).To(ConsistOf("some-warning")) 308 }) 309 }) 310 }) 311 312 Describe("UpdateApplication", func() { 313 var ( 314 application Application 315 warnings Warnings 316 err error 317 ) 318 319 JustBeforeEach(func() { 320 application, warnings, err = actor.UpdateApplication(Application{ 321 GUID: "some-app-guid", 322 LifecycleType: constant.BuildpackAppLifecycleType, 323 LifecycleBuildpacks: []string{"buildpack-1", "buildpack-2"}, 324 }) 325 }) 326 327 Context("when the app successfully gets updated", func() { 328 BeforeEach(func() { 329 fakeCloudControllerClient.UpdateApplicationReturns( 330 ccv3.Application{ 331 GUID: "some-app-guid", 332 LifecycleType: constant.BuildpackAppLifecycleType, 333 LifecycleBuildpacks: []string{"buildpack-1", "buildpack-2"}, 334 }, 335 ccv3.Warnings{"some-warning"}, 336 nil, 337 ) 338 }) 339 340 It("creates and returns the application and warnings", func() { 341 Expect(err).ToNot(HaveOccurred()) 342 Expect(application).To(Equal(Application{ 343 GUID: "some-app-guid", 344 LifecycleType: constant.BuildpackAppLifecycleType, 345 LifecycleBuildpacks: []string{"buildpack-1", "buildpack-2"}, 346 })) 347 Expect(warnings).To(ConsistOf("some-warning")) 348 349 Expect(fakeCloudControllerClient.UpdateApplicationCallCount()).To(Equal(1)) 350 Expect(fakeCloudControllerClient.UpdateApplicationArgsForCall(0)).To(Equal(ccv3.Application{ 351 GUID: "some-app-guid", 352 LifecycleType: constant.BuildpackAppLifecycleType, 353 LifecycleBuildpacks: []string{"buildpack-1", "buildpack-2"}, 354 })) 355 }) 356 }) 357 358 Context("when the cc client returns an error", func() { 359 var expectedError error 360 361 BeforeEach(func() { 362 expectedError = errors.New("I am a CloudControllerClient Error") 363 fakeCloudControllerClient.UpdateApplicationReturns( 364 ccv3.Application{}, 365 ccv3.Warnings{"some-warning"}, 366 expectedError, 367 ) 368 }) 369 370 It("raises the error and warnings", func() { 371 Expect(err).To(MatchError(expectedError)) 372 Expect(warnings).To(ConsistOf("some-warning")) 373 }) 374 }) 375 }) 376 377 Describe("PollStart", func() { 378 var warningsChannel chan Warnings 379 var allWarnings Warnings 380 var funcDone chan interface{} 381 382 BeforeEach(func() { 383 warningsChannel = make(chan Warnings) 384 funcDone = make(chan interface{}) 385 allWarnings = Warnings{} 386 go func() { 387 for { 388 select { 389 case warnings := <-warningsChannel: 390 allWarnings = append(allWarnings, warnings...) 391 case <-funcDone: 392 return 393 } 394 } 395 }() 396 }) 397 398 Context("when getting the application processes fails", func() { 399 BeforeEach(func() { 400 fakeCloudControllerClient.GetApplicationProcessesReturns(nil, ccv3.Warnings{"get-app-warning-1", "get-app-warning-2"}, errors.New("some-error")) 401 }) 402 403 It("returns the error and all warnings", func() { 404 err := actor.PollStart("some-guid", warningsChannel) 405 funcDone <- nil 406 Expect(allWarnings).To(ConsistOf("get-app-warning-1", "get-app-warning-2")) 407 Expect(err).To(MatchError(errors.New("some-error"))) 408 }) 409 }) 410 411 Context("when getting the application processes succeeds", func() { 412 var processes []ccv3.Process 413 414 BeforeEach(func() { 415 fakeConfig.StartupTimeoutReturns(time.Second) 416 fakeConfig.PollingIntervalReturns(0) 417 }) 418 419 JustBeforeEach(func() { 420 fakeCloudControllerClient.GetApplicationProcessesReturns( 421 processes, 422 ccv3.Warnings{"get-app-warning-1"}, nil) 423 }) 424 425 Context("when there is a single process", func() { 426 BeforeEach(func() { 427 processes = []ccv3.Process{{GUID: "abc123"}} 428 }) 429 430 Context("when the polling times out", func() { 431 BeforeEach(func() { 432 fakeConfig.StartupTimeoutReturns(time.Millisecond) 433 fakeConfig.PollingIntervalReturns(time.Millisecond * 2) 434 fakeCloudControllerClient.GetProcessInstancesReturns( 435 []ccv3.ProcessInstance{{State: constant.ProcessInstanceStarting}}, 436 ccv3.Warnings{"get-process-warning-1", "get-process-warning-2"}, 437 nil, 438 ) 439 }) 440 441 It("returns the timeout error", func() { 442 err := actor.PollStart("some-guid", warningsChannel) 443 funcDone <- nil 444 445 Expect(allWarnings).To(ConsistOf("get-app-warning-1", "get-process-warning-1", "get-process-warning-2")) 446 Expect(err).To(MatchError(actionerror.StartupTimeoutError{})) 447 }) 448 449 It("gets polling and timeout values from the config", func() { 450 actor.PollStart("some-guid", warningsChannel) 451 funcDone <- nil 452 453 Expect(fakeConfig.StartupTimeoutCallCount()).To(Equal(1)) 454 Expect(fakeConfig.PollingIntervalCallCount()).To(Equal(1)) 455 }) 456 }) 457 458 Context("when getting the process instances errors", func() { 459 BeforeEach(func() { 460 fakeCloudControllerClient.GetProcessInstancesReturns( 461 nil, 462 ccv3.Warnings{"get-process-warning-1", "get-process-warning-2"}, 463 errors.New("some-error"), 464 ) 465 }) 466 467 It("returns the error", func() { 468 err := actor.PollStart("some-guid", warningsChannel) 469 funcDone <- nil 470 471 Expect(allWarnings).To(ConsistOf("get-app-warning-1", "get-process-warning-1", "get-process-warning-2")) 472 Expect(err).To(MatchError("some-error")) 473 }) 474 }) 475 476 Context("when getting the process instances succeeds", func() { 477 var ( 478 initialInstanceStates []ccv3.ProcessInstance 479 eventualInstanceStates []ccv3.ProcessInstance 480 pollStartErr error 481 processInstanceCallCount int 482 ) 483 484 BeforeEach(func() { 485 processInstanceCallCount = 0 486 }) 487 488 JustBeforeEach(func() { 489 fakeCloudControllerClient.GetProcessInstancesStub = func(processGuid string) ([]ccv3.ProcessInstance, ccv3.Warnings, error) { 490 defer func() { processInstanceCallCount++ }() 491 if processInstanceCallCount == 0 { 492 return initialInstanceStates, 493 ccv3.Warnings{"get-process-warning-1", "get-process-warning-2"}, 494 nil 495 } else { 496 return eventualInstanceStates, 497 ccv3.Warnings{fmt.Sprintf("get-process-warning-%d", processInstanceCallCount+2)}, 498 nil 499 } 500 } 501 502 pollStartErr = actor.PollStart("some-guid", warningsChannel) 503 funcDone <- nil 504 }) 505 506 Context("when there are no process instances", func() { 507 BeforeEach(func() { 508 initialInstanceStates = []ccv3.ProcessInstance{} 509 eventualInstanceStates = []ccv3.ProcessInstance{} 510 }) 511 512 It("should not return an error", func() { 513 Expect(pollStartErr).NotTo(HaveOccurred()) 514 }) 515 516 It("should only call GetProcessInstances once before exiting", func() { 517 Expect(processInstanceCallCount).To(Equal(1)) 518 }) 519 520 It("should return correct warnings", func() { 521 Expect(allWarnings).To(ConsistOf("get-app-warning-1", "get-process-warning-1", "get-process-warning-2")) 522 }) 523 }) 524 525 Context("when all instances become running by the second call", func() { 526 BeforeEach(func() { 527 initialInstanceStates = []ccv3.ProcessInstance{{State: constant.ProcessInstanceStarting}, {State: constant.ProcessInstanceStarting}} 528 eventualInstanceStates = []ccv3.ProcessInstance{{State: constant.ProcessInstanceRunning}, {State: constant.ProcessInstanceRunning}} 529 }) 530 531 It("should not return an error", func() { 532 Expect(pollStartErr).NotTo(HaveOccurred()) 533 }) 534 535 It("should call GetProcessInstances twice", func() { 536 Expect(processInstanceCallCount).To(Equal(2)) 537 }) 538 539 It("should return correct warnings", func() { 540 Expect(allWarnings).To(ConsistOf("get-app-warning-1", "get-process-warning-1", "get-process-warning-2", "get-process-warning-3")) 541 }) 542 }) 543 544 Context("when at least one instance has become running by the second call", func() { 545 BeforeEach(func() { 546 initialInstanceStates = []ccv3.ProcessInstance{{State: constant.ProcessInstanceStarting}, {State: constant.ProcessInstanceStarting}, {State: constant.ProcessInstanceStarting}} 547 eventualInstanceStates = []ccv3.ProcessInstance{{State: constant.ProcessInstanceStarting}, {State: constant.ProcessInstanceStarting}, {State: constant.ProcessInstanceRunning}} 548 }) 549 550 It("should not return an error", func() { 551 Expect(pollStartErr).NotTo(HaveOccurred()) 552 }) 553 554 It("should call GetProcessInstances twice", func() { 555 Expect(processInstanceCallCount).To(Equal(2)) 556 }) 557 558 It("should return correct warnings", func() { 559 Expect(len(allWarnings)).To(Equal(4)) 560 Expect(allWarnings).To(ConsistOf("get-app-warning-1", "get-process-warning-1", "get-process-warning-2", "get-process-warning-3")) 561 }) 562 }) 563 564 Context("when all of the instances have crashed by the second call", func() { 565 BeforeEach(func() { 566 initialInstanceStates = []ccv3.ProcessInstance{{State: constant.ProcessInstanceStarting}, {State: constant.ProcessInstanceStarting}, {State: constant.ProcessInstanceStarting}} 567 eventualInstanceStates = []ccv3.ProcessInstance{{State: constant.ProcessInstanceCrashed}, {State: constant.ProcessInstanceCrashed}, {State: constant.ProcessInstanceCrashed}} 568 }) 569 570 It("should not return an error", func() { 571 Expect(pollStartErr).NotTo(HaveOccurred()) 572 }) 573 574 It("should call GetProcessInstances twice", func() { 575 Expect(processInstanceCallCount).To(Equal(2)) 576 }) 577 578 It("should return correct warnings", func() { 579 Expect(len(allWarnings)).To(Equal(4)) 580 Expect(allWarnings).To(ConsistOf("get-app-warning-1", "get-process-warning-1", "get-process-warning-2", "get-process-warning-3")) 581 }) 582 }) 583 }) 584 }) 585 586 Context("where there are multiple processes", func() { 587 var ( 588 pollStartErr error 589 processInstanceCallCount int 590 ) 591 592 BeforeEach(func() { 593 processInstanceCallCount = 0 594 fakeConfig.StartupTimeoutReturns(time.Millisecond) 595 fakeConfig.PollingIntervalReturns(time.Millisecond * 2) 596 }) 597 598 JustBeforeEach(func() { 599 fakeCloudControllerClient.GetProcessInstancesStub = func(processGuid string) ([]ccv3.ProcessInstance, ccv3.Warnings, error) { 600 defer func() { processInstanceCallCount++ }() 601 if strings.HasPrefix(processGuid, "good") { 602 return []ccv3.ProcessInstance{ccv3.ProcessInstance{State: constant.ProcessInstanceRunning}}, nil, nil 603 } else { 604 return []ccv3.ProcessInstance{ccv3.ProcessInstance{State: constant.ProcessInstanceStarting}}, nil, nil 605 } 606 } 607 608 pollStartErr = actor.PollStart("some-guid", warningsChannel) 609 funcDone <- nil 610 }) 611 612 Context("when none of the processes are ready", func() { 613 BeforeEach(func() { 614 processes = []ccv3.Process{{GUID: "bad-1"}, {GUID: "bad-2"}} 615 }) 616 617 It("returns the timeout error", func() { 618 Expect(pollStartErr).To(MatchError(actionerror.StartupTimeoutError{})) 619 }) 620 621 }) 622 623 Context("when some of the processes are ready", func() { 624 BeforeEach(func() { 625 processes = []ccv3.Process{{GUID: "bad-1"}, {GUID: "good-1"}} 626 }) 627 628 It("returns the timeout error", func() { 629 Expect(pollStartErr).To(MatchError(actionerror.StartupTimeoutError{})) 630 }) 631 }) 632 633 Context("when all of the processes are ready", func() { 634 BeforeEach(func() { 635 processes = []ccv3.Process{{GUID: "good-1"}, {GUID: "good-2"}} 636 }) 637 638 It("returns nil", func() { 639 Expect(pollStartErr).ToNot(HaveOccurred()) 640 }) 641 }) 642 }) 643 }) 644 }) 645 646 Describe("StopApplication", func() { 647 Context("when there are no client errors", func() { 648 BeforeEach(func() { 649 fakeCloudControllerClient.StopApplicationReturns( 650 ccv3.Application{GUID: "some-app-guid"}, 651 ccv3.Warnings{"stop-application-warning"}, 652 nil, 653 ) 654 }) 655 656 It("stops the application", func() { 657 warnings, err := actor.StopApplication("some-app-guid") 658 659 Expect(err).ToNot(HaveOccurred()) 660 Expect(warnings).To(ConsistOf("stop-application-warning")) 661 662 Expect(fakeCloudControllerClient.StopApplicationCallCount()).To(Equal(1)) 663 Expect(fakeCloudControllerClient.StopApplicationArgsForCall(0)).To(Equal("some-app-guid")) 664 }) 665 }) 666 667 Context("when stopping the application fails", func() { 668 var expectedErr error 669 BeforeEach(func() { 670 expectedErr = errors.New("some set stop-application error") 671 fakeCloudControllerClient.StopApplicationReturns( 672 ccv3.Application{}, 673 ccv3.Warnings{"stop-application-warning"}, 674 expectedErr, 675 ) 676 }) 677 678 It("returns the error", func() { 679 warnings, err := actor.StopApplication("some-app-guid") 680 681 Expect(err).To(Equal(expectedErr)) 682 Expect(warnings).To(ConsistOf("stop-application-warning")) 683 }) 684 }) 685 }) 686 687 Describe("StartApplication", func() { 688 Context("when there are no client errors", func() { 689 BeforeEach(func() { 690 fakeCloudControllerClient.StartApplicationReturns( 691 ccv3.Application{GUID: "some-app-guid"}, 692 ccv3.Warnings{"start-application-warning"}, 693 nil, 694 ) 695 }) 696 697 It("starts the application", func() { 698 app, warnings, err := actor.StartApplication("some-app-guid") 699 700 Expect(err).ToNot(HaveOccurred()) 701 Expect(warnings).To(ConsistOf("start-application-warning")) 702 Expect(app).To(Equal(Application{GUID: "some-app-guid"})) 703 704 Expect(fakeCloudControllerClient.StartApplicationCallCount()).To(Equal(1)) 705 Expect(fakeCloudControllerClient.StartApplicationArgsForCall(0)).To(Equal("some-app-guid")) 706 }) 707 }) 708 709 Context("when starting the application fails", func() { 710 var expectedErr error 711 BeforeEach(func() { 712 expectedErr = errors.New("some set start-application error") 713 fakeCloudControllerClient.StartApplicationReturns( 714 ccv3.Application{}, 715 ccv3.Warnings{"start-application-warning"}, 716 expectedErr, 717 ) 718 }) 719 720 It("returns the error", func() { 721 _, warnings, err := actor.StartApplication("some-app-guid") 722 723 Expect(err).To(Equal(expectedErr)) 724 Expect(warnings).To(ConsistOf("start-application-warning")) 725 }) 726 }) 727 }) 728 })