From 5cbe66085db46321d91b2be5c1a878c5dc1c238e Mon Sep 17 00:00:00 2001 From: Anna Khmelnitsky Date: Wed, 1 Sep 2021 01:11:10 +0000 Subject: [PATCH] Introduces map data for ns groups and ns services Such data source builds a name to uuids map of the whole table. This map can be referenced in configuration to obtain object uuids at a cost of single roudtrip to NSX, which improves apply and refresh time at scale. Signed-off-by: Anna Khmelnitsky --- nsxt/data_source_nsxt_ns_groups.go | 62 +++++++++++++++++++++++ nsxt/data_source_nsxt_ns_groups_test.go | 58 +++++++++++++++++++++ nsxt/data_source_nsxt_ns_services.go | 62 +++++++++++++++++++++++ nsxt/data_source_nsxt_ns_services_test.go | 58 +++++++++++++++++++++ nsxt/provider.go | 2 + website/docs/d/ns_groups.html.markdown | 36 +++++++++++++ website/docs/d/ns_services.html.markdown | 42 +++++++++++++++ 7 files changed, 320 insertions(+) create mode 100644 nsxt/data_source_nsxt_ns_groups.go create mode 100644 nsxt/data_source_nsxt_ns_groups_test.go create mode 100644 nsxt/data_source_nsxt_ns_services.go create mode 100644 nsxt/data_source_nsxt_ns_services_test.go create mode 100644 website/docs/d/ns_groups.html.markdown create mode 100644 website/docs/d/ns_services.html.markdown diff --git a/nsxt/data_source_nsxt_ns_groups.go b/nsxt/data_source_nsxt_ns_groups.go new file mode 100644 index 000000000..bcb486fda --- /dev/null +++ b/nsxt/data_source_nsxt_ns_groups.go @@ -0,0 +1,62 @@ +/* Copyright © 2017 VMware, Inc. All Rights Reserved. + SPDX-License-Identifier: MPL-2.0 */ + +package nsxt + +import ( + "fmt" + + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" +) + +func dataSourceNsxtNsGroups() *schema.Resource { + return &schema.Resource{ + Read: dataSourceNsxtNsGroupsRead, + + Schema: map[string]*schema.Schema{ + "items": { + Type: schema.TypeMap, + Description: "Mapping of group UUID by display name", + Computed: true, + Elem: &schema.Schema{ + Type: schema.TypeString, + }, + }, + }, + } +} + +func dataSourceNsxtNsGroupsRead(d *schema.ResourceData, m interface{}) error { + nsxClient := m.(nsxtClients).NsxtClient + if nsxClient == nil { + return dataSourceNotSupportedError() + } + + // Get by full name + groupMap := make(map[string]string) + lister := func(info *paginationInfo) error { + objList, _, err := nsxClient.GroupingObjectsApi.ListNSGroups(nsxClient.Context, info.LocalVarOptionals) + if err != nil { + return fmt.Errorf("Error while reading NS groups: %v", err) + } + info.PageCount = int64(len(objList.Results)) + info.TotalCount = objList.ResultCount + info.Cursor = objList.Cursor + + // go over the list to find the correct one + for _, objInList := range objList.Results { + groupMap[objInList.DisplayName] = objInList.Id + } + return nil + } + + _, err := handlePagination(lister) + if err != nil { + return err + } + + d.SetId(newUUID()) + d.Set("items", groupMap) + + return nil +} diff --git a/nsxt/data_source_nsxt_ns_groups_test.go b/nsxt/data_source_nsxt_ns_groups_test.go new file mode 100644 index 000000000..6fb559b6e --- /dev/null +++ b/nsxt/data_source_nsxt_ns_groups_test.go @@ -0,0 +1,58 @@ +/* Copyright © 2017 VMware, Inc. All Rights Reserved. + SPDX-License-Identifier: MPL-2.0 */ + +package nsxt + +import ( + "fmt" + "testing" + + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" +) + +func TestAccDataSourceNsxtNsGroups_basic(t *testing.T) { + groupName := getAccTestDataSourceName() + testResourceName := "data.nsxt_ns_groups.test" + // in order to verify correct functionality, we compare fetching by name with regular data source + // and fetching using the map data source with same name + // in order to verify map fetching with pair comparison, we use an extra resource + checkDataSourceName := "data.nsxt_ns_group.check" + checkResourceName := "nsxt_ns_group.check" + + resource.ParallelTest(t, resource.TestCase{ + PreCheck: func() { testAccOnlyLocalManager(t); testAccTestMP(t); testAccPreCheck(t) }, + Providers: testAccProviders, + CheckDestroy: func(state *terraform.State) error { + return testAccDataSourceNsxtNsGroupDeleteByName(groupName) + }, + Steps: []resource.TestStep{ + { + PreConfig: func() { + if err := testAccDataSourceNsxtNsGroupCreate(groupName); err != nil { + panic(err) + } + }, + Config: testAccNSXNsGroupsReadTemplate(groupName), + Check: resource.ComposeTestCheckFunc( + resource.TestCheckResourceAttrSet(testResourceName, "id"), + resource.TestCheckResourceAttrPair(checkResourceName, "display_name", checkDataSourceName, "id"), + ), + }, + }, + }) +} + +func testAccNSXNsGroupsReadTemplate(groupName string) string { + return fmt.Sprintf(` +data "nsxt_ns_groups" "test" { +} + +data "nsxt_ns_group" "check" { + display_name = "%s" +} + +resource "nsxt_ns_group" "check" { + display_name = data.nsxt_ns_groups.test.items["%s"] +}`, groupName, groupName) +} diff --git a/nsxt/data_source_nsxt_ns_services.go b/nsxt/data_source_nsxt_ns_services.go new file mode 100644 index 000000000..a3f92bb08 --- /dev/null +++ b/nsxt/data_source_nsxt_ns_services.go @@ -0,0 +1,62 @@ +/* Copyright © 2017 VMware, Inc. All Rights Reserved. + SPDX-License-Identifier: MPL-2.0 */ + +package nsxt + +import ( + "fmt" + + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" +) + +func dataSourceNsxtNsServices() *schema.Resource { + return &schema.Resource{ + Read: dataSourceNsxtNsServicesRead, + + Schema: map[string]*schema.Schema{ + "items": { + Type: schema.TypeMap, + Description: "Mapping of service UUID by display name", + Computed: true, + Elem: &schema.Schema{ + Type: schema.TypeString, + }, + }, + }, + } +} + +func dataSourceNsxtNsServicesRead(d *schema.ResourceData, m interface{}) error { + nsxClient := m.(nsxtClients).NsxtClient + if nsxClient == nil { + return dataSourceNotSupportedError() + } + + // Get by full name + serviceMap := make(map[string]string) + lister := func(info *paginationInfo) error { + objList, _, err := nsxClient.GroupingObjectsApi.ListNSServices(nsxClient.Context, info.LocalVarOptionals) + if err != nil { + return fmt.Errorf("Error while reading NS services: %v", err) + } + info.PageCount = int64(len(objList.Results)) + info.TotalCount = objList.ResultCount + info.Cursor = objList.Cursor + + // go over the list to find the correct one + for _, objInList := range objList.Results { + serviceMap[objInList.DisplayName] = objInList.Id + } + return nil + } + + _, err := handlePagination(lister) + if err != nil { + return err + } + + d.SetId(newUUID()) + d.Set("items", serviceMap) + + return nil +} diff --git a/nsxt/data_source_nsxt_ns_services_test.go b/nsxt/data_source_nsxt_ns_services_test.go new file mode 100644 index 000000000..163231c77 --- /dev/null +++ b/nsxt/data_source_nsxt_ns_services_test.go @@ -0,0 +1,58 @@ +/* Copyright © 2017 VMware, Inc. All Rights Reserved. + SPDX-License-Identifier: MPL-2.0 */ + +package nsxt + +import ( + "fmt" + "testing" + + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" +) + +func TestAccDataSourceNsxtNsServices_basic(t *testing.T) { + serviceName := getAccTestDataSourceName() + testResourceName := "data.nsxt_ns_services.test" + // in order to verify correct functionality, we compare fetching by name with regular data source + // and fetching using the map data source with same name + // in order to verify map fetching with pair comparison, we use an extra resource + checkDataSourceName := "data.nsxt_ns_service.check" + checkResourceName := "nsxt_ns_group.check" + + resource.ParallelTest(t, resource.TestCase{ + PreCheck: func() { testAccOnlyLocalManager(t); testAccTestMP(t); testAccPreCheck(t) }, + Providers: testAccProviders, + CheckDestroy: func(state *terraform.State) error { + return testAccDataSourceNsxtNsServiceDeleteByName(serviceName) + }, + Steps: []resource.TestStep{ + { + PreConfig: func() { + if err := testAccDataSourceNsxtNsServiceCreate(serviceName); err != nil { + panic(err) + } + }, + Config: testAccNSXNsServicesReadTemplate(serviceName), + Check: resource.ComposeTestCheckFunc( + resource.TestCheckResourceAttrSet(testResourceName, "id"), + resource.TestCheckResourceAttrPair(checkResourceName, "display_name", checkDataSourceName, "id"), + ), + }, + }, + }) +} + +func testAccNSXNsServicesReadTemplate(serviceName string) string { + return fmt.Sprintf(` +data "nsxt_ns_services" "test" { +} + +data "nsxt_ns_service" "check" { + display_name = "%s" +} + +resource "nsxt_ns_group" "check" { + display_name = data.nsxt_ns_services.test.items["%s"] +}`, serviceName, serviceName) +} diff --git a/nsxt/provider.go b/nsxt/provider.go index cd95e9271..314492891 100644 --- a/nsxt/provider.go +++ b/nsxt/provider.go @@ -203,7 +203,9 @@ func Provider() *schema.Provider { "nsxt_logical_tier1_router": dataSourceNsxtLogicalTier1Router(), "nsxt_mac_pool": dataSourceNsxtMacPool(), "nsxt_ns_group": dataSourceNsxtNsGroup(), + "nsxt_ns_groups": dataSourceNsxtNsGroups(), "nsxt_ns_service": dataSourceNsxtNsService(), + "nsxt_ns_services": dataSourceNsxtNsServices(), "nsxt_edge_cluster": dataSourceNsxtEdgeCluster(), "nsxt_certificate": dataSourceNsxtCertificate(), "nsxt_ip_pool": dataSourceNsxtIPPool(), diff --git a/website/docs/d/ns_groups.html.markdown b/website/docs/d/ns_groups.html.markdown new file mode 100644 index 000000000..829f2a360 --- /dev/null +++ b/website/docs/d/ns_groups.html.markdown @@ -0,0 +1,36 @@ +--- +subcategory: "Manager" +layout: "nsxt" +page_title: "NSXT: ns_groups" +description: A networking and security groups data source. This data source builds "display name to id" map representation of the whole table. +--- + +# nsxt_ns_groups + +This data source builds a "name to uuid" map of the whole NS Group table. Such map can be referenced in configuration to obtain object uuids by display name at a cost of single roudtrip to NSX, which improves apply and refresh +time at scale, compared to multiple instances of `nsxt_ns_group` data source. + +## Example Usage + +```hcl +data "nsxt_ns_group" "map" { +} + +resource "nsxt_firewall_section" "s1" { + display_name = "section1" + + applied_to { + target_type = "NSGroup" + target_id = data.nsxt_ns_groups.map.items["group1"] + } + + section_type = "LAYER3" +} + +``` + +## Attributes Reference + +In addition to arguments listed above, the following attributes are exported: + +* `items` - Map of ns group uuids keyed by display name. diff --git a/website/docs/d/ns_services.html.markdown b/website/docs/d/ns_services.html.markdown new file mode 100644 index 000000000..a221a8aea --- /dev/null +++ b/website/docs/d/ns_services.html.markdown @@ -0,0 +1,42 @@ +--- +subcategory: "Manager" +layout: "nsxt" +page_title: "NSXT: ns_services" +description: A networking and security services data source. This data source builds "display name to id" map representation of the whole table. +--- + +# nsxt_ns_services + +This data source builds a "name to uuid" map of the whole NS Services table. Such map can be referenced in configuration to obtain object uuids by display name at a cost of single roudtrip to NSX, which improves apply and refresh +time at scale, compared to multiple instances of `nsxt_ns_service` data source. + +## Example Usage + +```hcl +data "nsxt_ns_service" "map" { +} + +resource "nsxt_firewall_section" "s1" { + display_name = "section1" + + rule { + display_name = "in_rule" + action = "DROP" + direction = "IN" + + service { + target_type = "NSService" + target_id = data.nsxt_ns_services.map.items["service1"] + } + } + + section_type = "LAYER3" +} + +``` + +## Attributes Reference + +In addition to arguments listed above, the following attributes are exported: + +* `items` - Map of ns service uuids keyed by display name.