github.com/cloudfoundry-attic/cli-with-i18n@v6.32.1-0.20171002233121-7401370d3b85+incompatible/api/cloudcontroller/ccv2/security_group_test.go (about) 1 package ccv2_test 2 3 import ( 4 "net/http" 5 6 "code.cloudfoundry.org/cli/api/cloudcontroller/ccerror" 7 . "code.cloudfoundry.org/cli/api/cloudcontroller/ccv2" 8 . "github.com/onsi/ginkgo" 9 . "github.com/onsi/gomega" 10 . "github.com/onsi/gomega/ghttp" 11 ) 12 13 var _ = Describe("Security Groups", func() { 14 var client *Client 15 16 BeforeEach(func() { 17 client = NewTestClient() 18 }) 19 20 Describe("AssociateSpaceWithRunningSecurityGroup", func() { 21 Context("when no errors are encountered", func() { 22 BeforeEach(func() { 23 response := `{}` 24 server.AppendHandlers( 25 CombineHandlers( 26 VerifyRequest(http.MethodPut, "/v2/security_groups/security-group-guid/spaces/space-guid"), 27 RespondWith(http.StatusOK, response, http.Header{"X-Cf-Warnings": {"warning-1"}}), 28 )) 29 }) 30 31 It("returns all warnings", func() { 32 warnings, err := client.AssociateSpaceWithRunningSecurityGroup("security-group-guid", "space-guid") 33 34 Expect(err).NotTo(HaveOccurred()) 35 Expect(warnings).To(ConsistOf("warning-1")) 36 }) 37 }) 38 39 Context("when an error is encountered", func() { 40 BeforeEach(func() { 41 response := `{ 42 "code": 10001, 43 "description": "Some Error", 44 "error_code": "CF-SomeError" 45 }` 46 server.AppendHandlers( 47 CombineHandlers( 48 VerifyRequest(http.MethodPut, "/v2/security_groups/security-group-guid/spaces/space-guid"), 49 RespondWith(http.StatusTeapot, response, http.Header{"X-Cf-Warnings": {"warning-1, warning-2"}}), 50 )) 51 }) 52 53 It("returns an error and all warnings", func() { 54 warnings, err := client.AssociateSpaceWithRunningSecurityGroup("security-group-guid", "space-guid") 55 56 Expect(err).To(MatchError(ccerror.V2UnexpectedResponseError{ 57 ResponseCode: http.StatusTeapot, 58 V2ErrorResponse: ccerror.V2ErrorResponse{ 59 Code: 10001, 60 Description: "Some Error", 61 ErrorCode: "CF-SomeError", 62 }, 63 })) 64 Expect(warnings).To(ConsistOf("warning-1", "warning-2")) 65 }) 66 }) 67 }) 68 69 Describe("AssociateSpaceWithStagingSecurityGroup", func() { 70 Context("when no errors are encountered", func() { 71 BeforeEach(func() { 72 response := `{}` 73 server.AppendHandlers( 74 CombineHandlers( 75 VerifyRequest(http.MethodPut, "/v2/security_groups/security-group-guid/staging_spaces/space-guid"), 76 RespondWith(http.StatusOK, response, http.Header{"X-Cf-Warnings": {"warning-1"}}), 77 )) 78 }) 79 80 It("returns all warnings", func() { 81 warnings, err := client.AssociateSpaceWithStagingSecurityGroup("security-group-guid", "space-guid") 82 83 Expect(err).NotTo(HaveOccurred()) 84 Expect(warnings).To(ConsistOf("warning-1")) 85 }) 86 }) 87 88 Context("when an error is encountered", func() { 89 BeforeEach(func() { 90 response := `{ 91 "code": 10001, 92 "description": "Some Error", 93 "error_code": "CF-SomeError" 94 }` 95 server.AppendHandlers( 96 CombineHandlers( 97 VerifyRequest(http.MethodPut, "/v2/security_groups/security-group-guid/staging_spaces/space-guid"), 98 RespondWith(http.StatusTeapot, response, http.Header{"X-Cf-Warnings": {"warning-1, warning-2"}}), 99 )) 100 }) 101 102 It("returns an error and all warnings", func() { 103 warnings, err := client.AssociateSpaceWithStagingSecurityGroup("security-group-guid", "space-guid") 104 105 Expect(err).To(MatchError(ccerror.V2UnexpectedResponseError{ 106 ResponseCode: http.StatusTeapot, 107 V2ErrorResponse: ccerror.V2ErrorResponse{ 108 Code: 10001, 109 Description: "Some Error", 110 ErrorCode: "CF-SomeError", 111 }, 112 })) 113 Expect(warnings).To(ConsistOf("warning-1", "warning-2")) 114 }) 115 }) 116 }) 117 118 Describe("GetSecurityGroups", func() { 119 Context("when no errors are encountered", func() { 120 Context("when results are paginated", func() { 121 BeforeEach(func() { 122 response1 := `{ 123 "next_url": "/v2/security_groups?q=some-query:some-value&page=2", 124 "resources": [ 125 { 126 "metadata": { 127 "guid": "security-group-guid-1", 128 "url": "/v2/security_groups/security-group-guid-1" 129 }, 130 "entity": { 131 "name": "security-group-1", 132 "rules": [ 133 ], 134 "running_default": false, 135 "staging_default": true, 136 "spaces_url": "/v2/security_groups/security-group-guid-1/spaces" 137 } 138 } 139 ] 140 }` 141 response2 := `{ 142 "next_url": null, 143 "resources": [ 144 { 145 "metadata": { 146 "guid": "security-group-guid-2", 147 "url": "/v2/security_groups/security-group-guid-2" 148 }, 149 "entity": { 150 "name": "security-group-2", 151 "rules": [ 152 ], 153 "running_default": true, 154 "staging_default": false, 155 "spaces_url": "/v2/security_groups/security-group-guid-2/spaces" 156 } 157 } 158 ] 159 }` 160 server.AppendHandlers( 161 CombineHandlers( 162 VerifyRequest(http.MethodGet, "/v2/security_groups", "q=some-query:some-value"), 163 RespondWith(http.StatusOK, response1, http.Header{"X-Cf-Warnings": {"warning-1"}}), 164 )) 165 server.AppendHandlers( 166 CombineHandlers( 167 VerifyRequest(http.MethodGet, "/v2/security_groups", "q=some-query:some-value&page=2"), 168 RespondWith(http.StatusOK, response2, http.Header{"X-Cf-Warnings": {"warning-2"}}), 169 )) 170 }) 171 172 It("returns paginated results and all warnings", func() { 173 securityGroups, warnings, err := client.GetSecurityGroups(Query{ 174 Filter: "some-query", 175 Operator: EqualOperator, 176 Values: []string{"some-value"}, 177 }) 178 179 Expect(err).NotTo(HaveOccurred()) 180 Expect(securityGroups).To(Equal([]SecurityGroup{ 181 { 182 GUID: "security-group-guid-1", 183 Name: "security-group-1", 184 Rules: []SecurityGroupRule{}, 185 RunningDefault: false, 186 StagingDefault: true, 187 }, 188 { 189 GUID: "security-group-guid-2", 190 Name: "security-group-2", 191 Rules: []SecurityGroupRule{}, 192 RunningDefault: true, 193 StagingDefault: false, 194 }, 195 })) 196 Expect(warnings).To(ConsistOf("warning-1", "warning-2")) 197 }) 198 }) 199 }) 200 201 Context("when an error is encountered", func() { 202 BeforeEach(func() { 203 response := `{ 204 "code": 10001, 205 "description": "Some Error", 206 "error_code": "CF-SomeError" 207 }` 208 server.AppendHandlers( 209 CombineHandlers( 210 VerifyRequest(http.MethodGet, "/v2/security_groups"), 211 RespondWith(http.StatusTeapot, response, http.Header{"X-Cf-Warnings": {"warning-1, warning-2"}}), 212 )) 213 }) 214 215 It("returns an error and all warnings", func() { 216 _, warnings, err := client.GetSecurityGroups() 217 218 Expect(err).To(MatchError(ccerror.V2UnexpectedResponseError{ 219 ResponseCode: http.StatusTeapot, 220 V2ErrorResponse: ccerror.V2ErrorResponse{ 221 Code: 10001, 222 Description: "Some Error", 223 ErrorCode: "CF-SomeError", 224 }, 225 })) 226 Expect(warnings).To(ConsistOf("warning-1", "warning-2")) 227 }) 228 }) 229 }) 230 231 Describe("GetSpaceRunningSecurityGroupsBySpace", func() { 232 Context("when the space exists", func() { 233 BeforeEach(func() { 234 response1 := `{ 235 "next_url": "/v2/spaces/some-space-guid/security_groups?q=some-query:some-value&page=2", 236 "resources": [ 237 { 238 "metadata": { 239 "guid": "running-security-group-guid-1", 240 "updated_at": null 241 }, 242 "entity": { 243 "name": "running-security-group-name-1", 244 "rules": [ 245 { 246 "protocol": "udp", 247 "ports": "8080", 248 "description": "description-1", 249 "destination": "198.41.191.47/1" 250 }, 251 { 252 "protocol": "tcp", 253 "ports": "80,443", 254 "description": "description-2", 255 "destination": "254.41.191.47-254.44.255.255" 256 } 257 ] 258 } 259 }, 260 { 261 "metadata": { 262 "guid": "running-security-group-guid-2", 263 "updated_at": null 264 }, 265 "entity": { 266 "name": "running-security-group-name-2", 267 "rules": [ 268 { 269 "protocol": "udp", 270 "ports": "8080", 271 "description": "description-3", 272 "destination": "198.41.191.47/24" 273 }, 274 { 275 "protocol": "tcp", 276 "ports": "80,443", 277 "description": "description-4", 278 "destination": "254.41.191.4-254.44.255.4" 279 } 280 ] 281 } 282 } 283 ] 284 }` 285 response2 := `{ 286 "next_url": null, 287 "resources": [ 288 { 289 "metadata": { 290 "guid": "running-security-group-guid-3", 291 "updated_at": null 292 }, 293 "entity": { 294 "name": "running-security-group-name-3", 295 "rules": [ 296 { 297 "protocol": "udp", 298 "ports": "32767", 299 "description": "description-5", 300 "destination": "127.0.0.1/32" 301 }, 302 { 303 "protocol": "tcp", 304 "ports": "8008,4443", 305 "description": "description-6", 306 "destination": "254.41.191.0-254.44.255.1" 307 } 308 ] 309 } 310 } 311 ] 312 }` 313 server.AppendHandlers( 314 CombineHandlers( 315 VerifyRequest(http.MethodGet, "/v2/spaces/some-space-guid/security_groups", "q=some-query:some-value"), 316 RespondWith(http.StatusOK, response1, http.Header{"X-Cf-Warnings": {"this is a warning"}}), 317 ), 318 ) 319 server.AppendHandlers( 320 CombineHandlers( 321 VerifyRequest(http.MethodGet, "/v2/spaces/some-space-guid/security_groups", "q=some-query:some-value&page=2"), 322 RespondWith(http.StatusOK, response2, http.Header{"X-Cf-Warnings": {"this is another warning"}}), 323 ), 324 ) 325 }) 326 327 It("returns the running security groups and all warnings", func() { 328 securityGroups, warnings, err := client.GetSpaceRunningSecurityGroupsBySpace("some-space-guid", Query{ 329 Filter: "some-query", 330 Operator: EqualOperator, 331 Values: []string{"some-value"}, 332 }) 333 Expect(err).NotTo(HaveOccurred()) 334 Expect(warnings).To(ConsistOf("this is a warning", "this is another warning")) 335 Expect(securityGroups).To(ConsistOf( 336 SecurityGroup{ 337 Name: "running-security-group-name-1", 338 GUID: "running-security-group-guid-1", 339 Rules: []SecurityGroupRule{ 340 { 341 Protocol: "udp", 342 Ports: "8080", 343 Description: "description-1", 344 Destination: "198.41.191.47/1", 345 }, 346 { 347 Protocol: "tcp", 348 Ports: "80,443", 349 Description: "description-2", 350 Destination: "254.41.191.47-254.44.255.255", 351 }, 352 }, 353 }, 354 SecurityGroup{ 355 Name: "running-security-group-name-2", 356 GUID: "running-security-group-guid-2", 357 Rules: []SecurityGroupRule{ 358 { 359 Protocol: "udp", 360 Ports: "8080", 361 Description: "description-3", 362 Destination: "198.41.191.47/24", 363 }, 364 { 365 Protocol: "tcp", 366 Ports: "80,443", 367 Description: "description-4", 368 Destination: "254.41.191.4-254.44.255.4", 369 }, 370 }, 371 }, 372 SecurityGroup{ 373 Name: "running-security-group-name-3", 374 GUID: "running-security-group-guid-3", 375 Rules: []SecurityGroupRule{ 376 { 377 Protocol: "udp", 378 Ports: "32767", 379 Description: "description-5", 380 Destination: "127.0.0.1/32", 381 }, 382 { 383 Protocol: "tcp", 384 Ports: "8008,4443", 385 Description: "description-6", 386 Destination: "254.41.191.0-254.44.255.1", 387 }, 388 }, 389 }, 390 )) 391 }) 392 }) 393 394 Context("when the client returns an error", func() { 395 BeforeEach(func() { 396 response := `{ 397 "code": 40004, 398 "description": "The space could not be found: some-space-guid", 399 "error_code": "CF-SpaceNotFound" 400 }` 401 server.AppendHandlers( 402 CombineHandlers( 403 VerifyRequest(http.MethodGet, "/v2/spaces/some-space-guid/security_groups"), 404 RespondWith(http.StatusNotFound, response, http.Header{"X-Cf-Warnings": {"this is a warning"}}), 405 ), 406 ) 407 }) 408 409 It("returns the error and warnings", func() { 410 securityGroups, warnings, err := client.GetSpaceRunningSecurityGroupsBySpace("some-space-guid") 411 Expect(err).To(MatchError(ccerror.ResourceNotFoundError{ 412 Message: "The space could not be found: some-space-guid", 413 })) 414 Expect(warnings).To(ConsistOf(Warnings{"this is a warning"})) 415 Expect(securityGroups).To(BeEmpty()) 416 }) 417 }) 418 }) 419 420 Describe("GetSpaceStagingSecurityGroupsBySpace", func() { 421 Context("when the space exists", func() { 422 BeforeEach(func() { 423 response1 := `{ 424 "next_url": "/v2/spaces/some-space-guid/staging_security_groups?q=some-query:some-value&page=2", 425 "resources": [ 426 { 427 "metadata": { 428 "guid": "staging-security-group-guid-1", 429 "updated_at": null 430 }, 431 "entity": { 432 "name": "staging-security-group-name-1", 433 "rules": [ 434 { 435 "protocol": "udp", 436 "ports": "8080", 437 "description": "description-1", 438 "destination": "198.41.191.47/1" 439 }, 440 { 441 "protocol": "tcp", 442 "ports": "80,443", 443 "description": "description-2", 444 "destination": "254.41.191.47-254.44.255.255" 445 } 446 ] 447 } 448 }, 449 { 450 "metadata": { 451 "guid": "staging-security-group-guid-2", 452 "updated_at": null 453 }, 454 "entity": { 455 "name": "staging-security-group-name-2", 456 "rules": [ 457 { 458 "protocol": "udp", 459 "ports": "8080", 460 "description": "description-3", 461 "destination": "198.41.191.47/24" 462 }, 463 { 464 "protocol": "tcp", 465 "ports": "80,443", 466 "description": "description-4", 467 "destination": "254.41.191.4-254.44.255.4" 468 } 469 ] 470 } 471 } 472 ] 473 }` 474 response2 := `{ 475 "next_url": null, 476 "resources": [ 477 { 478 "metadata": { 479 "guid": "staging-security-group-guid-3", 480 "updated_at": null 481 }, 482 "entity": { 483 "name": "staging-security-group-name-3", 484 "rules": [ 485 { 486 "protocol": "udp", 487 "ports": "32767", 488 "description": "description-5", 489 "destination": "127.0.0.1/32" 490 }, 491 { 492 "protocol": "tcp", 493 "ports": "8008,4443", 494 "description": "description-6", 495 "destination": "254.41.191.0-254.44.255.1" 496 } 497 ] 498 } 499 } 500 ] 501 }` 502 server.AppendHandlers( 503 CombineHandlers( 504 VerifyRequest(http.MethodGet, "/v2/spaces/some-space-guid/staging_security_groups", "q=some-query:some-value"), 505 RespondWith(http.StatusOK, response1, http.Header{"X-Cf-Warnings": {"this is a warning"}}), 506 ), 507 ) 508 server.AppendHandlers( 509 CombineHandlers( 510 VerifyRequest(http.MethodGet, "/v2/spaces/some-space-guid/staging_security_groups", "q=some-query:some-value&page=2"), 511 RespondWith(http.StatusOK, response2, http.Header{"X-Cf-Warnings": {"this is another warning"}}), 512 ), 513 ) 514 }) 515 516 It("returns the staging security groups and all warnings", func() { 517 securityGroups, warnings, err := client.GetSpaceStagingSecurityGroupsBySpace("some-space-guid", Query{ 518 Filter: "some-query", 519 Operator: EqualOperator, 520 Values: []string{"some-value"}, 521 }) 522 Expect(err).NotTo(HaveOccurred()) 523 Expect(warnings).To(ConsistOf("this is a warning", "this is another warning")) 524 Expect(securityGroups).To(ConsistOf( 525 SecurityGroup{ 526 Name: "staging-security-group-name-1", 527 GUID: "staging-security-group-guid-1", 528 Rules: []SecurityGroupRule{ 529 { 530 Protocol: "udp", 531 Ports: "8080", 532 Description: "description-1", 533 Destination: "198.41.191.47/1", 534 }, 535 { 536 Protocol: "tcp", 537 Ports: "80,443", 538 Description: "description-2", 539 Destination: "254.41.191.47-254.44.255.255", 540 }, 541 }, 542 }, 543 SecurityGroup{ 544 Name: "staging-security-group-name-2", 545 GUID: "staging-security-group-guid-2", 546 Rules: []SecurityGroupRule{ 547 { 548 Protocol: "udp", 549 Ports: "8080", 550 Description: "description-3", 551 Destination: "198.41.191.47/24", 552 }, 553 { 554 Protocol: "tcp", 555 Ports: "80,443", 556 Description: "description-4", 557 Destination: "254.41.191.4-254.44.255.4", 558 }, 559 }, 560 }, 561 SecurityGroup{ 562 Name: "staging-security-group-name-3", 563 GUID: "staging-security-group-guid-3", 564 Rules: []SecurityGroupRule{ 565 { 566 Protocol: "udp", 567 Ports: "32767", 568 Description: "description-5", 569 Destination: "127.0.0.1/32", 570 }, 571 { 572 Protocol: "tcp", 573 Ports: "8008,4443", 574 Description: "description-6", 575 Destination: "254.41.191.0-254.44.255.1", 576 }, 577 }, 578 }, 579 )) 580 }) 581 }) 582 583 Context("when the client returns an error", func() { 584 BeforeEach(func() { 585 response := `{ 586 "code": 40004, 587 "description": "The space could not be found: some-space-guid", 588 "error_code": "CF-SpaceNotFound" 589 }` 590 server.AppendHandlers( 591 CombineHandlers( 592 VerifyRequest(http.MethodGet, "/v2/spaces/some-space-guid/staging_security_groups"), 593 RespondWith(http.StatusNotFound, response, http.Header{"X-Cf-Warnings": {"this is a warning"}}), 594 ), 595 ) 596 }) 597 598 It("returns the error and warnings", func() { 599 securityGroups, warnings, err := client.GetSpaceStagingSecurityGroupsBySpace("some-space-guid") 600 Expect(err).To(MatchError(ccerror.ResourceNotFoundError{ 601 Message: "The space could not be found: some-space-guid", 602 })) 603 Expect(warnings).To(ConsistOf(Warnings{"this is a warning"})) 604 Expect(securityGroups).To(BeEmpty()) 605 }) 606 }) 607 }) 608 609 Describe("RemoveSpaceFromRunningSecurityGroup", func() { 610 var ( 611 warnings Warnings 612 err error 613 ) 614 615 JustBeforeEach(func() { 616 warnings, err = client.RemoveSpaceFromRunningSecurityGroup("security-group-guid", "space-guid") 617 }) 618 619 Context("when the client call is successful", func() { 620 BeforeEach(func() { 621 server.AppendHandlers( 622 CombineHandlers( 623 VerifyRequest(http.MethodDelete, "/v2/security_groups/security-group-guid/spaces/space-guid"), 624 RespondWith(http.StatusOK, nil, http.Header{"X-Cf-Warnings": {"warning-1"}}), 625 )) 626 }) 627 628 It("returns all warnings", func() { 629 Expect(err).ToNot(HaveOccurred()) 630 Expect(warnings).To(ConsistOf(Warnings{"warning-1"})) 631 }) 632 }) 633 634 Context("when the client call is unsuccessful", func() { 635 BeforeEach(func() { 636 response := `{ 637 "code": 10001, 638 "description": "Some Error", 639 "error_code": "CF-SomeError" 640 }` 641 server.AppendHandlers( 642 CombineHandlers( 643 VerifyRequest(http.MethodDelete, "/v2/security_groups/security-group-guid/spaces/space-guid"), 644 RespondWith(http.StatusTeapot, response, http.Header{"X-Cf-Warnings": {"warning-1"}}), 645 )) 646 }) 647 648 It("returns the error and all warnings", func() { 649 Expect(err).To(MatchError(ccerror.V2UnexpectedResponseError{ 650 ResponseCode: http.StatusTeapot, 651 V2ErrorResponse: ccerror.V2ErrorResponse{ 652 Code: 10001, 653 Description: "Some Error", 654 ErrorCode: "CF-SomeError", 655 }, 656 })) 657 Expect(warnings).To(ConsistOf("warning-1")) 658 }) 659 }) 660 }) 661 662 Describe("RemoveSpaceFromStagingSecurityGroup", func() { 663 var ( 664 warnings Warnings 665 err error 666 ) 667 668 JustBeforeEach(func() { 669 warnings, err = client.RemoveSpaceFromStagingSecurityGroup("security-group-guid", "space-guid") 670 }) 671 672 Context("when the client call is successful", func() { 673 BeforeEach(func() { 674 server.AppendHandlers( 675 CombineHandlers( 676 VerifyRequest(http.MethodDelete, "/v2/security_groups/security-group-guid/staging_spaces/space-guid"), 677 RespondWith(http.StatusOK, nil, http.Header{"X-Cf-Warnings": {"warning-1"}}), 678 )) 679 }) 680 681 It("returns all warnings", func() { 682 Expect(err).ToNot(HaveOccurred()) 683 Expect(warnings).To(ConsistOf(Warnings{"warning-1"})) 684 }) 685 }) 686 687 Context("when the client call is unsuccessful", func() { 688 BeforeEach(func() { 689 response := `{ 690 "code": 10001, 691 "description": "Some Error", 692 "error_code": "CF-SomeError" 693 }` 694 server.AppendHandlers( 695 CombineHandlers( 696 VerifyRequest(http.MethodDelete, "/v2/security_groups/security-group-guid/staging_spaces/space-guid"), 697 RespondWith(http.StatusTeapot, response, http.Header{"X-Cf-Warnings": {"warning-1"}}), 698 )) 699 }) 700 701 It("returns the error and all warnings", func() { 702 Expect(err).To(MatchError(ccerror.V2UnexpectedResponseError{ 703 ResponseCode: http.StatusTeapot, 704 V2ErrorResponse: ccerror.V2ErrorResponse{ 705 Code: 10001, 706 Description: "Some Error", 707 ErrorCode: "CF-SomeError", 708 }, 709 })) 710 Expect(warnings).To(ConsistOf("warning-1")) 711 }) 712 }) 713 }) 714 })