From e091687770d516417ca43368505eb1b23c4a7368 Mon Sep 17 00:00:00 2001 From: Haroon-Dweikat-Ntx Date: Wed, 8 Jan 2025 17:34:42 +0200 Subject: [PATCH] protection policy linear retention and auto rollup retention test cases, and add Check Destroy --- ...ata_source_nutanix_protection_policy_v2.go | 8 - .../services/datapoliciesv2/helper_test.go | 18 ++ ...rce_nutanix_protection_policies_v2_test.go | 256 +++++++++++++++++- 3 files changed, 272 insertions(+), 10 deletions(-) diff --git a/nutanix/services/datapoliciesv2/data_source_nutanix_protection_policy_v2.go b/nutanix/services/datapoliciesv2/data_source_nutanix_protection_policy_v2.go index 2562a8be..523adff3 100644 --- a/nutanix/services/datapoliciesv2/data_source_nutanix_protection_policy_v2.go +++ b/nutanix/services/datapoliciesv2/data_source_nutanix_protection_policy_v2.go @@ -2,9 +2,6 @@ package datapoliciesv2 import ( "context" - "encoding/json" - "log" - "github.com/hashicorp/terraform-plugin-sdk/v2/diag" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/nutanix/ntnx-api-golang-clients/datapolicies-go-client/v4/models/common/v1/response" @@ -131,11 +128,8 @@ func schemaForLinks() *schema.Schema { // flatten funcs func flattenLinks(links []response.ApiLink) []map[string]interface{} { - aJSON, _ := json.MarshalIndent(links, "", " ") - log.Println("[DEBUG] Links: ", string(aJSON)) if len(links) > 0 { linkList := make([]map[string]interface{}, 0) - for _, link := range links { linkMap := make(map[string]interface{}) if link.Rel != nil { @@ -147,8 +141,6 @@ func flattenLinks(links []response.ApiLink) []map[string]interface{} { linkList = append(linkList, linkMap) } - aJSON, _ = json.MarshalIndent(linkList, "", " ") - log.Println("[DEBUG] Flattened Links: ", string(aJSON)) return linkList } return nil diff --git a/nutanix/services/datapoliciesv2/helper_test.go b/nutanix/services/datapoliciesv2/helper_test.go index 6ebebcc2..5fb36719 100644 --- a/nutanix/services/datapoliciesv2/helper_test.go +++ b/nutanix/services/datapoliciesv2/helper_test.go @@ -4,6 +4,9 @@ import ( "fmt" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + conns "github.com/terraform-providers/terraform-provider-nutanix/nutanix" + acc "github.com/terraform-providers/terraform-provider-nutanix/nutanix/acctest" + "github.com/terraform-providers/terraform-provider-nutanix/utils" "strconv" ) @@ -58,3 +61,18 @@ func checkAttributeLengthEqual(resourceName, attribute string, expectedLength in return nil } } + +func testProtectionPolicyV2CheckDestroy(state *terraform.State) error { + conn := acc.TestAccProvider.Meta().(*conns.Client) + client := conn.DataPoliciesAPI.ProtectionPolicies + for _, rs := range state.RootModule().Resources { + if rs.Type != resourceNameProtectionPolicy { + continue + } + _, err := client.GetProtectionPolicyById(utils.StringPtr(rs.Primary.ID)) + if err == nil { + return fmt.Errorf("protection policy still exists") + } + } + return nil +} diff --git a/nutanix/services/datapoliciesv2/resource_nutanix_protection_policies_v2_test.go b/nutanix/services/datapoliciesv2/resource_nutanix_protection_policies_v2_test.go index aad9ff74..d1eadab8 100644 --- a/nutanix/services/datapoliciesv2/resource_nutanix_protection_policies_v2_test.go +++ b/nutanix/services/datapoliciesv2/resource_nutanix_protection_policies_v2_test.go @@ -19,8 +19,9 @@ func TestAccV2NutanixProtectionPolicyResource_Basic(t *testing.T) { updateDescription := "terraform test protection policy CRUD update" resource.Test(t, resource.TestCase{ - PreCheck: func() { acc.TestAccFoundationPreCheck(t) }, - Providers: acc.TestAccProviders, + PreCheck: func() { acc.TestAccFoundationPreCheck(t) }, + Providers: acc.TestAccProviders, + CheckDestroy: testProtectionPolicyV2CheckDestroy, Steps: []resource.TestStep{ { Config: testProtectionPolicyResourceConfig(name, description), @@ -87,6 +88,97 @@ func TestAccV2NutanixProtectionPolicyResource_Basic(t *testing.T) { }) } +func TestAccV2NutanixProtectionPolicyResource_LinearRetention(t *testing.T) { + r := acctest.RandInt() + name := fmt.Sprintf("tf-test-protection-policy-%d", r) + description := "terraform test protection policy CRUD" + + resource.Test(t, resource.TestCase{ + PreCheck: func() { acc.TestAccFoundationPreCheck(t) }, + Providers: acc.TestAccProviders, + CheckDestroy: testProtectionPolicyV2CheckDestroy, + Steps: []resource.TestStep{ + { + Config: testProtectionPolicyResourceConfigLinearRetention(name, description), + Check: resource.ComposeTestCheckFunc( + resource.TestCheckResourceAttrSet(resourceNameProtectionPolicy, "ext_id"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "name", name), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "description", description), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.source_location_label", "0"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.remote_location_label", "1"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.schedule.0.recovery_point_objective_time_seconds", "7200"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.schedule.0.recovery_point_type", "CRASH_CONSISTENT"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.schedule.0.retention.0.linear_retention.0.local", "1"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.schedule.0.retention.0.linear_retention.0.remote", "1"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.source_location_label", "1"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.remote_location_label", "0"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.schedule.0.recovery_point_objective_time_seconds", "7200"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.schedule.0.recovery_point_type", "CRASH_CONSISTENT"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.schedule.0.retention.0.linear_retention.0.local", "1"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.schedule.0.retention.0.linear_retention.0.remote", "1"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_locations.0.label", "0"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_locations.0.is_primary", "true"), + resource.TestCheckResourceAttrSet(resourceNameProtectionPolicy, "replication_locations.0.domain_manager_ext_id"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_locations.1.label", "1"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_locations.1.is_primary", "false"), + resource.TestCheckResourceAttrSet(resourceNameProtectionPolicy, "replication_locations.1.domain_manager_ext_id"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "category_ids.#", "2"), + ), + }, + }, + }) +} + +func TestAccV2NutanixProtectionPolicyResource_AutoRollupRetention(t *testing.T) { + r := acctest.RandInt() + name := fmt.Sprintf("tf-test-protection-policy-%d", r) + description := "terraform test protection policy CRUD auto rollup retention" + + resource.Test(t, resource.TestCase{ + PreCheck: func() { acc.TestAccFoundationPreCheck(t) }, + Providers: acc.TestAccProviders, + CheckDestroy: testProtectionPolicyV2CheckDestroy, + Steps: []resource.TestStep{ + + { + Config: testProtectionPolicyResourceConfigAutoRollupRetention(name, description), + Check: resource.ComposeTestCheckFunc( + resource.TestCheckResourceAttrSet(resourceNameProtectionPolicy, "ext_id"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "name", name), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "description", description), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.source_location_label", "source"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.remote_location_label", "target"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.schedule.0.recovery_point_objective_time_seconds", "60"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.schedule.0.recovery_point_type", "CRASH_CONSISTENT"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.schedule.0.sync_replication_auto_suspend_timeout_seconds", "20"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.schedule.0.retention.0.auto_rollup_retention.0.local.0.frequency", "2"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.schedule.0.retention.0.auto_rollup_retention.0.local.0.snapshot_interval_type", "WEEKLY"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.schedule.0.retention.0.auto_rollup_retention.0.remote.0.frequency", "1"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.schedule.0.retention.0.auto_rollup_retention.0.remote.0.snapshot_interval_type", "DAILY"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.0.schedule.0.start_time", "18h:10m"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.source_location_label", "target"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.remote_location_label", "source"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.schedule.0.recovery_point_objective_time_seconds", "60"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.schedule.0.recovery_point_type", "CRASH_CONSISTENT"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.schedule.0.sync_replication_auto_suspend_timeout_seconds", "30"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.schedule.0.retention.0.auto_rollup_retention.0.local.0.frequency", "1"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.schedule.0.retention.0.auto_rollup_retention.0.local.0.snapshot_interval_type", "DAILY"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.schedule.0.retention.0.auto_rollup_retention.0.remote.0.frequency", "2"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.schedule.0.retention.0.auto_rollup_retention.0.remote.0.snapshot_interval_type", "WEEKLY"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_configurations.1.schedule.0.start_time", "18h:10m"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_locations.0.label", "source"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_locations.0.is_primary", "true"), + resource.TestCheckResourceAttrSet(resourceNameProtectionPolicy, "replication_locations.0.domain_manager_ext_id"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_locations.1.domain_manager_ext_id", testVars.ProtectionPolicies.DomainManagerExtID), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_locations.1.is_primary", "false"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "replication_locations.1.label", "target"), + resource.TestCheckResourceAttr(resourceNameProtectionPolicy, "category_ids.#", "2"), + ), + }, + }, + }) +} + func testProtectionPolicyResourceConfig(name, description string) string { return fmt.Sprintf(` # List domain Managers @@ -230,3 +322,163 @@ resource "nutanix_protection_policy_v2" "test" { } `, name, description, filepath) } + +func testProtectionPolicyResourceConfigLinearRetention(name, description string) string { + return fmt.Sprintf(` +# List domain Managers +data "nutanix_domain_managers_v2" "pcs" {} + +# List categories +data "nutanix_categories_v2" "categories" {} + +# list Clusters +data "nutanix_clusters_v2" "clusters" {} + +locals { + clusterExtId = [ + for cluster in data.nutanix_clusters_v2.clusters.cluster_entities : + cluster.ext_id if cluster.config[0].cluster_function[0] != "PRISM_CENTRAL" + ][0] + config = jsondecode(file("%[3]s")) + data_policies = local.config.data_policies +} + +resource "nutanix_protection_policy_v2" "test" { + name = "%[1]s" + description = "%[2]s" + + replication_configurations { + source_location_label = "0" + remote_location_label = "1" + schedule { + recovery_point_objective_time_seconds = 7200 + recovery_point_type = "CRASH_CONSISTENT" + retention { + linear_retention { + local = 1 + remote = 1 + } + } + } + } + replication_configurations { + source_location_label = "1" + remote_location_label = "0" + schedule { + recovery_point_objective_time_seconds = 7200 + recovery_point_type = "CRASH_CONSISTENT" + retention { + linear_retention { + local = 1 + remote = 1 + } + } + } + } + + replication_locations { + domain_manager_ext_id = data.nutanix_domain_managers_v2.pcs.domain_managers[0].ext_id + label = "0" + is_primary = true + replication_sub_location { + cluster_ext_ids { + cluster_ext_ids = [local.clusterExtId] + } + } + } + replication_locations { + domain_manager_ext_id = local.data_policies.domain_manager_ext_id + label = "1" + is_primary = false + } + + category_ids = [ + data.nutanix_categories_v2.categories.categories.0.ext_id, data.nutanix_categories_v2.categories.categories.1.ext_id + ] +}`, name, description, filepath) +} + +func testProtectionPolicyResourceConfigAutoRollupRetention(name, description string) string { + return fmt.Sprintf(` +# List domain Managers +data "nutanix_domain_managers_v2" "pcs" {} + +# List categories +data "nutanix_categories_v2" "categories" {} + +# list Clusters +data "nutanix_clusters_v2" "clusters" {} + +locals { + clusterExtId = [ + for cluster in data.nutanix_clusters_v2.clusters.cluster_entities : + cluster.ext_id if cluster.config[0].cluster_function[0] != "PRISM_CENTRAL" + ][0] + config = jsondecode(file("%[3]s")) + data_policies = local.config.data_policies +} + +resource "nutanix_protection_policy_v2" "test" { + name = "%[1]s" + description = "%[2]s" + +replication_configurations { + source_location_label = "source" + remote_location_label = "target" + schedule { + recovery_point_objective_time_seconds = 60 + recovery_point_type = "CRASH_CONSISTENT" + sync_replication_auto_suspend_timeout_seconds = 20 + start_time = "18h:10m" + retention { + auto_rollup_retention { + local { + snapshot_interval_type = "WEEKLY" + frequency = 2 + } + remote { + snapshot_interval_type = "DAILY" + frequency = 1 + } + } + } + } + } + replication_configurations { + source_location_label = "target" + remote_location_label = "source" + schedule { + recovery_point_objective_time_seconds = 60 + recovery_point_type = "CRASH_CONSISTENT" + sync_replication_auto_suspend_timeout_seconds = 30 + start_time = "18h:10m" + retention { + auto_rollup_retention { + local { + snapshot_interval_type = "DAILY" + frequency = 1 + } + remote { + snapshot_interval_type = "WEEKLY" + frequency = 2 + } + } + } + } + } + + replication_locations { + domain_manager_ext_id = data.nutanix_domain_managers_v2.pcs.domain_managers[0].ext_id + label = "source" + is_primary = true + } + replication_locations { + domain_manager_ext_id = local.data_policies.domain_manager_ext_id + label = "target" + is_primary = false + } + + category_ids = [data.nutanix_categories_v2.categories.categories.0.ext_id, data.nutanix_categories_v2.categories.categories.1.ext_id] +} +`, name, description, filepath) +}