diff --git a/ibm/service/power/ibm_pi_constants.go b/ibm/service/power/ibm_pi_constants.go index 5845e15552..f7d49cd2d7 100644 --- a/ibm/service/power/ibm_pi_constants.go +++ b/ibm/service/power/ibm_pi_constants.go @@ -29,6 +29,7 @@ const ( Arg_NetworkName = "pi_network_name" Arg_PIInstanceSharedProcessorPool = "pi_shared_processor_pool" Arg_PlacementGroupName = "pi_placement_group_name" + Arg_PlacementGroupPolicy = "pi_placement_group_policy" Arg_PVMInstanceActionType = "pi_action" Arg_PVMInstanceHealthStatus = "pi_health_status" Arg_PVMInstanceId = "pi_instance_id" @@ -320,9 +321,15 @@ const ( Attr_WWN = "wwn" OS_IBMI = "ibmi" + // Affinty Values + Affinity = "affinity" + AntiAffinity = "anti-affinity" + // States State_Active = "active" State_ACTIVE = "ACTIVE" + State_Added = "added" + State_Adding = "adding" State_Available = "available" State_BUILD = "BUILD" State_Creating = "creating" diff --git a/ibm/service/power/resource_ibm_pi_instance.go b/ibm/service/power/resource_ibm_pi_instance.go index 21f982f706..43d83d41fd 100644 --- a/ibm/service/power/resource_ibm_pi_instance.go +++ b/ibm/service/power/resource_ibm_pi_instance.go @@ -12,7 +12,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" st "github.com/IBM-Cloud/power-go-client/clients/instance" @@ -184,7 +184,6 @@ func ResourceIBMPIInstance() *schema.Resource { }, helpers.PIPlacementGroupID: { Type: schema.TypeString, - Computed: true, Optional: true, Description: "Placement group ID", }, @@ -788,12 +787,17 @@ func resourceIBMPIInstanceUpdate(ctx context.Context, d *schema.ResourceData, me body := &models.PlacementGroupServer{ ID: &instanceID, } - _, err := pgClient.DeleteMember(placementGroupID, body) + pgID, err := pgClient.DeleteMember(placementGroupID, body) if err != nil { // ignore delete member error where the server is already not in the PG if !strings.Contains(err.Error(), "is not part of placement-group") { return diag.FromErr(err) } + } else { + _, err = isWaitForPIInstancePlacementGroupDelete(ctx, pgClient, *pgID.ID, instanceID) + if err != nil { + return diag.FromErr(err) + } } } @@ -803,9 +807,14 @@ func resourceIBMPIInstanceUpdate(ctx context.Context, d *schema.ResourceData, me body := &models.PlacementGroupServer{ ID: &instanceID, } - _, err := pgClient.AddMember(placementGroupID, body) + pgID, err := pgClient.AddMember(placementGroupID, body) if err != nil { return diag.FromErr(err) + } else { + _, err = isWaitForPIInstancePlacementGroupAdd(ctx, pgClient, *pgID.ID, instanceID) + if err != nil { + return diag.FromErr(err) + } } } } @@ -877,7 +886,7 @@ func isWaitForPIInstanceDeleted(ctx context.Context, client *st.IBMPIInstanceCli log.Printf("Waiting for (%s) to be deleted.", id) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"retry", helpers.PIInstanceDeleting}, Target: []string{helpers.PIInstanceNotFound}, Refresh: isPIInstanceDeleteRefreshFunc(client, id), @@ -889,7 +898,7 @@ func isWaitForPIInstanceDeleted(ctx context.Context, client *st.IBMPIInstanceCli return stateConf.WaitForStateContext(ctx) } -func isPIInstanceDeleteRefreshFunc(client *st.IBMPIInstanceClient, id string) resource.StateRefreshFunc { +func isPIInstanceDeleteRefreshFunc(client *st.IBMPIInstanceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { pvm, err := client.Get(id) if err != nil { @@ -908,7 +917,7 @@ func isWaitForPIInstanceAvailable(ctx context.Context, client *st.IBMPIInstanceC queryTimeOut = warningTimeOut } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"PENDING", helpers.PIInstanceBuilding, helpers.PIInstanceHealthWarning}, Target: []string{helpers.PIInstanceAvailable, helpers.PIInstanceHealthOk, "ERROR", "", "SHUTOFF"}, Refresh: isPIInstanceRefreshFunc(client, id, instanceReadyStatus), @@ -920,7 +929,7 @@ func isWaitForPIInstanceAvailable(ctx context.Context, client *st.IBMPIInstanceC return stateConf.WaitForStateContext(ctx) } -func isPIInstanceRefreshFunc(client *st.IBMPIInstanceClient, id, instanceReadyStatus string) resource.StateRefreshFunc { +func isPIInstanceRefreshFunc(client *st.IBMPIInstanceClient, id, instanceReadyStatus string) retry.StateRefreshFunc { return func() (interface{}, string, error) { pvm, err := client.Get(id) @@ -944,12 +953,76 @@ func isPIInstanceRefreshFunc(client *st.IBMPIInstanceClient, id, instanceReadySt } } +func isWaitForPIInstancePlacementGroupAdd(ctx context.Context, client *st.IBMPIPlacementGroupClient, pgID string, id string) (interface{}, error) { + log.Printf("Waiting for PIInstance Placement Group (%s) to be updated ", id) + + queryTimeOut := activeTimeOut + + stateConf := &retry.StateChangeConf{ + Pending: []string{State_Adding}, + Target: []string{State_Added}, + Refresh: isPIInstancePlacementGroupAddRefreshFunc(client, pgID, id), + Delay: 30 * time.Second, + MinTimeout: queryTimeOut, + Timeout: 10 * time.Minute, + } + + return stateConf.WaitForStateContext(ctx) +} + +func isPIInstancePlacementGroupAddRefreshFunc(client *st.IBMPIPlacementGroupClient, pgID string, id string) retry.StateRefreshFunc { + return func() (interface{}, string, error) { + pg, err := client.Get(pgID) + if err != nil { + return nil, "", err + } + for _, x := range pg.Members { + if x == id { + return pg, State_Added, nil + } + } + return pg, State_Adding, nil + } +} + +func isWaitForPIInstancePlacementGroupDelete(ctx context.Context, client *st.IBMPIPlacementGroupClient, pgID string, id string) (interface{}, error) { + log.Printf("Waiting for PIInstance Placement Group (%s) to be updated ", id) + + queryTimeOut := activeTimeOut + + stateConf := &retry.StateChangeConf{ + Pending: []string{State_Deleting}, + Target: []string{State_Deleted}, + Refresh: isPIInstancePlacementGroupDeleteRefreshFunc(client, pgID, id), + Delay: 30 * time.Second, + MinTimeout: queryTimeOut, + Timeout: 10 * time.Minute, + } + + return stateConf.WaitForStateContext(ctx) +} + +func isPIInstancePlacementGroupDeleteRefreshFunc(client *st.IBMPIPlacementGroupClient, pgID string, id string) retry.StateRefreshFunc { + return func() (interface{}, string, error) { + pg, err := client.Get(pgID) + if err != nil { + return nil, "", err + } + for _, x := range pg.Members { + if x == id { + return pg, State_Deleting, nil + } + } + return pg, State_Deleted, nil + } +} + func isWaitForPIInstanceSoftwareLicenses(ctx context.Context, client *st.IBMPIInstanceClient, id string, softwareLicenses *models.SoftwareLicenses) (interface{}, error) { log.Printf("Waiting for PIInstance Software Licenses (%s) to be updated ", id) queryTimeOut := activeTimeOut - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"notdone"}, Target: []string{"done"}, Refresh: isPIInstanceSoftwareLicensesRefreshFunc(client, id, softwareLicenses), @@ -961,7 +1034,7 @@ func isWaitForPIInstanceSoftwareLicenses(ctx context.Context, client *st.IBMPIIn return stateConf.WaitForStateContext(ctx) } -func isPIInstanceSoftwareLicensesRefreshFunc(client *st.IBMPIInstanceClient, id string, softwareLicenses *models.SoftwareLicenses) resource.StateRefreshFunc { +func isPIInstanceSoftwareLicensesRefreshFunc(client *st.IBMPIInstanceClient, id string, softwareLicenses *models.SoftwareLicenses) retry.StateRefreshFunc { return func() (interface{}, string, error) { pvm, err := client.Get(id) @@ -1005,7 +1078,7 @@ func isWaitForPIInstanceShutoff(ctx context.Context, client *st.IBMPIInstanceCli queryTimeOut = warningTimeOut } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{StatusPending, helpers.PIInstanceBuilding, helpers.PIInstanceHealthWarning}, Target: []string{helpers.PIInstanceHealthOk, StatusError, "", StatusShutoff}, Refresh: isPIInstanceShutoffRefreshFunc(client, id, instanceReadyStatus), @@ -1016,7 +1089,8 @@ func isWaitForPIInstanceShutoff(ctx context.Context, client *st.IBMPIInstanceCli return stateConf.WaitForStateContext(ctx) } -func isPIInstanceShutoffRefreshFunc(client *st.IBMPIInstanceClient, id, instanceReadyStatus string) resource.StateRefreshFunc { + +func isPIInstanceShutoffRefreshFunc(client *st.IBMPIInstanceClient, id, instanceReadyStatus string) retry.StateRefreshFunc { return func() (interface{}, string, error) { pvm, err := client.Get(id) @@ -1051,7 +1125,7 @@ func encodeBase64(userData string) string { func isWaitForPIInstanceStopped(ctx context.Context, client *st.IBMPIInstanceClient, id string) (interface{}, error) { log.Printf("Waiting for PIInstance (%s) to be stopped and powered off ", id) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"STOPPING", "RESIZE", "VERIFY_RESIZE", helpers.PIInstanceHealthWarning}, Target: []string{"OK", "SHUTOFF"}, Refresh: isPIInstanceRefreshFuncOff(client, id), @@ -1063,7 +1137,7 @@ func isWaitForPIInstanceStopped(ctx context.Context, client *st.IBMPIInstanceCli return stateConf.WaitForStateContext(ctx) } -func isPIInstanceRefreshFuncOff(client *st.IBMPIInstanceClient, id string) resource.StateRefreshFunc { +func isPIInstanceRefreshFuncOff(client *st.IBMPIInstanceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { log.Printf("Calling the check Refresh status of the pvm instance %s", id) @@ -1094,7 +1168,6 @@ func stopLparForResourceChange(ctx context.Context, client *st.IBMPIInstanceClie } // Start the lpar - func startLparAfterResourceChange(ctx context.Context, client *st.IBMPIInstanceClient, id string) error { body := &models.PVMInstanceAction{ Action: flex.PtrToString("start"), @@ -1110,7 +1183,6 @@ func startLparAfterResourceChange(ctx context.Context, client *st.IBMPIInstanceC } // Stop / Modify / Start only when the lpar is off limits - func performChangeAndReboot(ctx context.Context, client *st.IBMPIInstanceClient, id, cloudInstanceID string, mem, procs float64) error { /* These are the steps @@ -1156,7 +1228,7 @@ func performChangeAndReboot(ctx context.Context, client *st.IBMPIInstanceClient, func isWaitforPIInstanceUpdate(ctx context.Context, client *st.IBMPIInstanceClient, id string) (interface{}, error) { log.Printf("Waiting for PIInstance (%s) to be ACTIVE or SHUTOFF AFTER THE RESIZE Due to DLPAR Operation ", id) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"RESIZE", "VERIFY_RESIZE"}, Target: []string{"ACTIVE", "SHUTOFF", helpers.PIInstanceHealthOk}, Refresh: isPIInstanceShutAfterResourceChange(client, id), @@ -1168,7 +1240,7 @@ func isWaitforPIInstanceUpdate(ctx context.Context, client *st.IBMPIInstanceClie return stateConf.WaitForStateContext(ctx) } -func isPIInstanceShutAfterResourceChange(client *st.IBMPIInstanceClient, id string) resource.StateRefreshFunc { +func isPIInstanceShutAfterResourceChange(client *st.IBMPIInstanceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { pvm, err := client.Get(id) diff --git a/ibm/service/power/resource_ibm_pi_placement_group.go b/ibm/service/power/resource_ibm_pi_placement_group.go index 5adfbcaf53..7618ac2547 100644 --- a/ibm/service/power/resource_ibm_pi_placement_group.go +++ b/ibm/service/power/resource_ibm_pi_placement_group.go @@ -9,15 +9,14 @@ import ( "log" "time" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" - - st "github.com/IBM-Cloud/power-go-client/clients/instance" - "github.com/IBM-Cloud/power-go-client/helpers" - models "github.com/IBM-Cloud/power-go-client/power/models" + "github.com/IBM-Cloud/power-go-client/clients/instance" + "github.com/IBM-Cloud/power-go-client/power/models" "github.com/IBM-Cloud/terraform-provider-ibm/ibm/conns" "github.com/IBM-Cloud/terraform-provider-ibm/ibm/flex" "github.com/IBM-Cloud/terraform-provider-ibm/ibm/validate" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" ) func ResourceIBMPIPlacementGroup() *schema.Resource { @@ -35,37 +34,37 @@ func ResourceIBMPIPlacementGroup() *schema.Resource { }, Schema: map[string]*schema.Schema{ - - helpers.PIPlacementGroupName: { - Type: schema.TypeString, - Required: true, - Description: "Name of the placement group", - }, - - helpers.PIPlacementGroupPolicy: { + // Arguments + Arg_CloudInstanceID: { + Description: "The GUID of the service instance associated with an account.", + Required: true, Type: schema.TypeString, + ValidateFunc: validation.NoZeroValues, + }, + Arg_PlacementGroupName: { + Description: "The name of the placement group.", Required: true, - ValidateFunc: validate.ValidateAllowedStringValues([]string{"affinity", "anti-affinity"}), - Description: "Policy of the placement group", + Type: schema.TypeString, + ValidateFunc: validation.NoZeroValues, }, - - helpers.PICloudInstanceId: { - Type: schema.TypeString, - Required: true, - Description: "PI cloud instance ID", + Arg_PlacementGroupPolicy: { + Description: "The value of the group's affinity policy. Valid values are 'affinity' and 'anti-affinity'.", + Required: true, + Type: schema.TypeString, + ValidateFunc: validate.ValidateAllowedStringValues([]string{Affinity, AntiAffinity}), }, - PIPlacementGroupMembers: { - Type: schema.TypeSet, + // Attributes + Attr_Members: { Computed: true, + Description: "The list of server instances IDs that are members of the placement group.", Elem: &schema.Schema{Type: schema.TypeString}, - Description: "Server IDs that are the placement group members", + Type: schema.TypeSet, }, - - PIPlacementGroupID: { - Type: schema.TypeString, + Attr_PlacementGroupID: { Computed: true, - Description: "PI placement group ID", + Description: "The placement group ID.", + Type: schema.TypeString, }, }, } @@ -77,10 +76,10 @@ func resourceIBMPIPlacementGroupCreate(ctx context.Context, d *schema.ResourceDa return diag.FromErr(err) } - cloudInstanceID := d.Get(helpers.PICloudInstanceId).(string) - name := d.Get(helpers.PIPlacementGroupName).(string) - policy := d.Get(helpers.PIPlacementGroupPolicy).(string) - client := st.NewIBMPIPlacementGroupClient(ctx, sess, cloudInstanceID) + cloudInstanceID := d.Get(Arg_CloudInstanceID).(string) + name := d.Get(Arg_PlacementGroupName).(string) + policy := d.Get(Arg_PlacementGroupPolicy).(string) + client := instance.NewIBMPIPlacementGroupClient(ctx, sess, cloudInstanceID) body := &models.PlacementGroupCreate{ Name: &name, Policy: &policy, @@ -98,7 +97,6 @@ func resourceIBMPIPlacementGroupCreate(ctx context.Context, d *schema.ResourceDa } func resourceIBMPIPlacementGroupRead(ctx context.Context, d *schema.ResourceData, meta interface{}) diag.Diagnostics { - sess, err := meta.(conns.ClientSession).IBMPISession() if err != nil { return diag.FromErr(err) @@ -109,7 +107,7 @@ func resourceIBMPIPlacementGroupRead(ctx context.Context, d *schema.ResourceData } cloudInstanceID := parts[0] - client := st.NewIBMPIPlacementGroupClient(ctx, sess, cloudInstanceID) + client := instance.NewIBMPIPlacementGroupClient(ctx, sess, cloudInstanceID) response, err := client.Get(parts[1]) if err != nil { @@ -117,13 +115,12 @@ func resourceIBMPIPlacementGroupRead(ctx context.Context, d *schema.ResourceData return diag.FromErr(err) } - d.Set(helpers.PIPlacementGroupName, response.Name) - d.Set(PIPlacementGroupID, response.ID) - d.Set(helpers.PIPlacementGroupPolicy, response.Policy) - d.Set(PIPlacementGroupMembers, response.Members) + d.Set(Arg_PlacementGroupName, response.Name) + d.Set(Arg_PlacementGroupPolicy, response.Policy) + d.Set(Attr_Members, response.Members) + d.Set(Attr_PlacementGroupID, response.ID) return nil - } func resourceIBMPIPlacementGroupUpdate(ctx context.Context, d *schema.ResourceData, meta interface{}) diag.Diagnostics { @@ -140,7 +137,7 @@ func resourceIBMPIPlacementGroupDelete(ctx context.Context, d *schema.ResourceDa return diag.FromErr(err) } cloudInstanceID := parts[0] - client := st.NewIBMPIPlacementGroupClient(ctx, sess, cloudInstanceID) + client := instance.NewIBMPIPlacementGroupClient(ctx, sess, cloudInstanceID) err = client.Delete(parts[1]) if err != nil { diff --git a/ibm/service/power/resource_ibm_pi_placement_group_test.go b/ibm/service/power/resource_ibm_pi_placement_group_test.go index aa2f953bce..1f53ad8fd3 100644 --- a/ibm/service/power/resource_ibm_pi_placement_group_test.go +++ b/ibm/service/power/resource_ibm_pi_placement_group_test.go @@ -10,14 +10,14 @@ import ( "strings" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" - - st "github.com/IBM-Cloud/power-go-client/clients/instance" acc "github.com/IBM-Cloud/terraform-provider-ibm/ibm/acctest" + + "github.com/IBM-Cloud/power-go-client/clients/instance" "github.com/IBM-Cloud/terraform-provider-ibm/ibm/conns" "github.com/IBM-Cloud/terraform-provider-ibm/ibm/flex" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" ) func TestAccIBMPIPlacementGroupBasic(t *testing.T) { @@ -39,7 +39,7 @@ func TestAccIBMPIPlacementGroupBasic(t *testing.T) { resource.TestCheckResourceAttr( "ibm_pi_placement_group.power_placement_group", "pi_placement_group_policy", policy), resource.TestCheckNoResourceAttr( - "ibm_pi_placement_group.power_placement_group", "members"), + "ibm_pi_placement_group.power_placement_group", "members.#"), ), }, { @@ -76,6 +76,7 @@ func TestAccIBMPIPlacementGroupBasic(t *testing.T) { testAccCheckIBMPIPlacementGroupMemberExistsFromInstanceCreate("ibm_pi_placement_group.power_placement_group", "ibm_pi_instance.power_instance", "ibm_pi_instance.power_instance_in_pg"), testAccCheckIBMPIPlacementGroupMemberExists("ibm_pi_placement_group.power_placement_group", "ibm_pi_instance.sap_power_instance"), ), + ExpectNonEmptyPlan: true, }, { Config: testAccCheckIBMPIDeletePlacementGroup(name, policy, "tinytest-1x4"), @@ -88,7 +89,6 @@ func TestAccIBMPIPlacementGroupBasic(t *testing.T) { } func testAccCheckIBMPIPlacementGroupDestroy(s *terraform.State) error { - sess, err := acc.TestAccProvider.Meta().(conns.ClientSession).IBMPISession() if err != nil { return err @@ -99,18 +99,17 @@ func testAccCheckIBMPIPlacementGroupDestroy(s *terraform.State) error { } parts, _ := flex.IdParts(rs.Primary.ID) cloudinstanceid := parts[0] - placementGroupC := st.NewIBMPIPlacementGroupClient(context.Background(), sess, cloudinstanceid) + placementGroupC := instance.NewIBMPIPlacementGroupClient(context.Background(), sess, cloudinstanceid) _, err = placementGroupC.Get(parts[1]) if err == nil { return fmt.Errorf("PI placement group still exists: %s", rs.Primary.ID) } } - return nil } + func testAccCheckIBMPIPlacementGroupExists(n string) resource.TestCheckFunc { return func(s *terraform.State) error { - rs, ok := s.RootModule().Resources[n] if !ok { @@ -130,7 +129,7 @@ func testAccCheckIBMPIPlacementGroupExists(n string) resource.TestCheckFunc { return err } cloudinstanceid := parts[0] - client := st.NewIBMPIPlacementGroupClient(context.Background(), sess, cloudinstanceid) + client := instance.NewIBMPIPlacementGroupClient(context.Background(), sess, cloudinstanceid) placementGroup, err := client.Get(parts[1]) if err != nil { @@ -141,9 +140,8 @@ func testAccCheckIBMPIPlacementGroupExists(n string) resource.TestCheckFunc { } } -func testAccCheckIBMPIPlacementGroupMemberExists(n string, instance string) resource.TestCheckFunc { +func testAccCheckIBMPIPlacementGroupMemberExists(n string, inst string) resource.TestCheckFunc { return func(s *terraform.State) error { - rs, ok := s.RootModule().Resources[n] if !ok { @@ -164,16 +162,16 @@ func testAccCheckIBMPIPlacementGroupMemberExists(n string, instance string) reso return err } cloudinstanceid := parts[0] - client := st.NewIBMPIPlacementGroupClient(context.Background(), sess, cloudinstanceid) + client := instance.NewIBMPIPlacementGroupClient(context.Background(), sess, cloudinstanceid) pg, err := client.Get(parts[1]) if err != nil { return err } - instancers, ok := s.RootModule().Resources[instance] + instancers, ok := s.RootModule().Resources[inst] if !ok { - return fmt.Errorf("Not found: %s", instance) + return fmt.Errorf("Not found: %s", inst) } instanceParts, err := flex.IdParts(instancers.Primary.ID) if err != nil { @@ -193,7 +191,7 @@ func testAccCheckIBMPIPlacementGroupMemberExists(n string, instance string) reso } } -func testAccCheckIBMPIPlacementGroupMemberDoesNotExist(n string, instance string) resource.TestCheckFunc { +func testAccCheckIBMPIPlacementGroupMemberDoesNotExist(n string, inst string) resource.TestCheckFunc { return func(s *terraform.State) error { rs, ok := s.RootModule().Resources[n] @@ -216,16 +214,16 @@ func testAccCheckIBMPIPlacementGroupMemberDoesNotExist(n string, instance string return err } cloudinstanceid := parts[0] - client := st.NewIBMPIPlacementGroupClient(context.Background(), sess, cloudinstanceid) + client := instance.NewIBMPIPlacementGroupClient(context.Background(), sess, cloudinstanceid) pg, err := client.Get(parts[1]) if err != nil { return err } - instancers, ok := s.RootModule().Resources[instance] + instancers, ok := s.RootModule().Resources[inst] if !ok { - return fmt.Errorf("Not found: %s", instance) + return fmt.Errorf("Not found: %s", inst) } instanccParts, err := flex.IdParts(instancers.Primary.ID) if err != nil { @@ -245,11 +243,10 @@ func containsMember(s []string, str string) bool { return true } } - return false } -func testAccCheckIBMPIPlacementGroupMemberExistsFromInstanceCreate(n string, instance string, newInstance string) resource.TestCheckFunc { +func testAccCheckIBMPIPlacementGroupMemberExistsFromInstanceCreate(n string, inst string, newInstance string) resource.TestCheckFunc { return func(s *terraform.State) error { rs, ok := s.RootModule().Resources[n] @@ -272,16 +269,16 @@ func testAccCheckIBMPIPlacementGroupMemberExistsFromInstanceCreate(n string, ins return err } cloudinstanceid := parts[0] - client := st.NewIBMPIPlacementGroupClient(context.Background(), sess, cloudinstanceid) + client := instance.NewIBMPIPlacementGroupClient(context.Background(), sess, cloudinstanceid) pg, err := client.Get(parts[1]) if err != nil { return err } - instancers, ok := s.RootModule().Resources[instance] + instancers, ok := s.RootModule().Resources[inst] if !ok { - return fmt.Errorf("Not found: %s", instance) + return fmt.Errorf("Not found: %s", inst) } instanceParts, err := flex.IdParts(instancers.Primary.ID) if err != nil { @@ -307,16 +304,16 @@ func testAccCheckIBMPIPlacementGroupMemberExistsFromInstanceCreate(n string, ins } } -func testAccCheckIBMPIPlacementGroupDelete(n string, instance string, newInstance string) resource.TestCheckFunc { +func testAccCheckIBMPIPlacementGroupDelete(n string, inst string, newInstance string) resource.TestCheckFunc { return func(s *terraform.State) error { sess, err := acc.TestAccProvider.Meta().(conns.ClientSession).IBMPISession() if err != nil { return err } - instancers, ok := s.RootModule().Resources[instance] + instancers, ok := s.RootModule().Resources[inst] if !ok { - return fmt.Errorf("Not found: %s", instance) + return fmt.Errorf("Not found: %s", inst) } instanceParts, err := flex.IdParts(instancers.Primary.ID) if err != nil { @@ -332,7 +329,7 @@ func testAccCheckIBMPIPlacementGroupDelete(n string, instance string, newInstanc return err } cloudinstanceid := instanceParts[0] - inst_client := st.NewIBMPIInstanceClient(context.Background(), sess, cloudinstanceid) + inst_client := instance.NewIBMPIInstanceClient(context.Background(), sess, cloudinstanceid) instance, err := inst_client.Get(instanceParts[1]) if err != nil { @@ -365,7 +362,7 @@ func testAccCheckIBMPIPlacementGroupConfig(name string, policy string) string { pi_processors = "0.25" pi_proc_type = "shared" pi_memory = "2" - pi_key_pair_name = ibm_pi_key.key.key_id + pi_key_pair_name = ibm_pi_key.key.name pi_image_id = "%[4]s" pi_sys_type = "e980" pi_instance_name = "%[2]s" @@ -379,8 +376,7 @@ func testAccCheckIBMPIPlacementGroupConfig(name string, policy string) string { pi_cloud_instance_id = "%[1]s" pi_placement_group_name = "%[2]s" pi_placement_group_policy = "%[3]s" - } - `, acc.Pi_cloud_instance_id, name, policy, acc.Pi_image, acc.Pi_network_name) + }`, acc.Pi_cloud_instance_id, name, policy, acc.Pi_image, acc.Pi_network_name) } func testAccCheckIBMPIPlacementGroupAddMemberConfig(name string, policy string) string { @@ -395,7 +391,7 @@ func testAccCheckIBMPIPlacementGroupAddMemberConfig(name string, policy string) pi_processors = "0.25" pi_proc_type = "shared" pi_memory = "2" - pi_key_pair_name = ibm_pi_key.key.key_id + pi_key_pair_name = ibm_pi_key.key.name pi_image_id = "%[4]s" pi_sys_type = "e980" pi_instance_name = "%[2]s" @@ -411,8 +407,7 @@ func testAccCheckIBMPIPlacementGroupAddMemberConfig(name string, policy string) pi_cloud_instance_id = "%[1]s" pi_placement_group_name = "%[2]s" pi_placement_group_policy = "%[3]s" - } - `, acc.Pi_cloud_instance_id, name, policy, acc.Pi_image, acc.Pi_network_name) + }`, acc.Pi_cloud_instance_id, name, policy, acc.Pi_image, acc.Pi_network_name) } func testAccCheckIBMPIPlacementGroupUpdateMemberConfig(name string, policy string) string { @@ -427,7 +422,7 @@ func testAccCheckIBMPIPlacementGroupUpdateMemberConfig(name string, policy strin pi_processors = "0.25" pi_proc_type = "shared" pi_memory = "2" - pi_key_pair_name = ibm_pi_key.key.key_id + pi_key_pair_name = ibm_pi_key.key.name pi_image_id = "%[4]s" pi_sys_type = "e980" pi_instance_name = "%[2]s" @@ -449,8 +444,7 @@ func testAccCheckIBMPIPlacementGroupUpdateMemberConfig(name string, policy strin pi_cloud_instance_id = "%[1]s" pi_placement_group_name = "%[2]s-2" pi_placement_group_policy = "%[3]s" - } - `, acc.Pi_cloud_instance_id, name, policy, acc.Pi_image, acc.Pi_network_name) + }`, acc.Pi_cloud_instance_id, name, policy, acc.Pi_image, acc.Pi_network_name) } func testAccCheckIBMPIPlacementGroupRemoveMemberConfig(name string, policy string) string { @@ -465,7 +459,7 @@ func testAccCheckIBMPIPlacementGroupRemoveMemberConfig(name string, policy strin pi_processors = "0.25" pi_proc_type = "shared" pi_memory = "2" - pi_key_pair_name = ibm_pi_key.key.key_id + pi_key_pair_name = ibm_pi_key.key.name pi_image_id = "%[4]s" pi_sys_type = "e980" pi_instance_name = "%[2]s" @@ -487,8 +481,7 @@ func testAccCheckIBMPIPlacementGroupRemoveMemberConfig(name string, policy strin pi_cloud_instance_id = "%[1]s" pi_placement_group_name = "%[2]s-2" pi_placement_group_policy = "%[3]s" - } - `, acc.Pi_cloud_instance_id, name, policy, acc.Pi_image, acc.Pi_network_name) + }`, acc.Pi_cloud_instance_id, name, policy, acc.Pi_image, acc.Pi_network_name) } func testAccCheckIBMPICreateInstanceInPlacementGroup(name string, policy string, sapProfile string) string { @@ -503,7 +496,7 @@ func testAccCheckIBMPICreateInstanceInPlacementGroup(name string, policy string, pi_processors = "0.25" pi_proc_type = "shared" pi_memory = "2" - pi_key_pair_name = ibm_pi_key.key.key_id + pi_key_pair_name = ibm_pi_key.key.name pi_image_id = "%[4]s" pi_sys_type = "e980" pi_instance_name = "%[2]s" @@ -519,7 +512,7 @@ func testAccCheckIBMPICreateInstanceInPlacementGroup(name string, policy string, pi_processors = "0.25" pi_proc_type = "shared" pi_memory = "2" - pi_key_pair_name = ibm_pi_key.key.key_id + pi_key_pair_name = ibm_pi_key.key.name pi_image_id = "%[4]s" pi_sys_type = "e980" pi_instance_name = "%[2]s-2" @@ -540,7 +533,7 @@ func testAccCheckIBMPICreateInstanceInPlacementGroup(name string, policy string, network_id = "%[7]s" } pi_placement_group_id = ibm_pi_placement_group.power_placement_group.placement_group_id - depends_on = [ ibm_pi_instance.power_instance_in_pg ] + depends_on = [ ibm_pi_instance.power_instance_in_pg ] } resource "ibm_pi_placement_group" "power_placement_group" { @@ -553,8 +546,7 @@ func testAccCheckIBMPICreateInstanceInPlacementGroup(name string, policy string, pi_cloud_instance_id = "%[1]s" pi_placement_group_name = "%[2]s-2" pi_placement_group_policy = "%[3]s" - } - `, acc.Pi_cloud_instance_id, name, policy, acc.Pi_image, sapProfile, acc.Pi_sap_image, acc.Pi_network_name) + }`, acc.Pi_cloud_instance_id, name, policy, acc.Pi_image, sapProfile, acc.Pi_sap_image, acc.Pi_network_name) } func testAccCheckIBMPIDeletePlacementGroup(name string, policy string, sapProfile string) string { @@ -569,7 +561,7 @@ func testAccCheckIBMPIDeletePlacementGroup(name string, policy string, sapProfil pi_processors = "0.25" pi_proc_type = "shared" pi_memory = "2" - pi_key_pair_name = ibm_pi_key.key.key_id + pi_key_pair_name = ibm_pi_key.key.name pi_image_id = "%[4]s" pi_sys_type = "e980" pi_instance_name = "%[2]s" @@ -584,7 +576,7 @@ func testAccCheckIBMPIDeletePlacementGroup(name string, policy string, sapProfil pi_processors = "0.25" pi_proc_type = "shared" pi_memory = "2" - pi_key_pair_name = ibm_pi_key.key.key_id + pi_key_pair_name = ibm_pi_key.key.name pi_image_id = "%[4]s" pi_sys_type = "e980" pi_instance_name = "%[2]s-2" @@ -603,13 +595,18 @@ func testAccCheckIBMPIDeletePlacementGroup(name string, policy string, sapProfil pi_network { network_id = "%[7]s" } - depends_on = [ ibm_pi_instance.power_instance_in_pg ] + depends_on = [ ibm_pi_instance.power_instance_in_pg ] + } + + resource "ibm_pi_placement_group" "power_placement_group" { + pi_cloud_instance_id = "%[1]s" + pi_placement_group_name = "%[2]s" + pi_placement_group_policy = "%[3]s" } resource "ibm_pi_placement_group" "power_placement_group_another" { pi_cloud_instance_id = "%[1]s" pi_placement_group_name = "%[2]s-2" pi_placement_group_policy = "%[3]s" - } - `, acc.Pi_cloud_instance_id, name, policy, acc.Pi_image, sapProfile, acc.Pi_sap_image, acc.Pi_network_name) + }`, acc.Pi_cloud_instance_id, name, policy, acc.Pi_image, sapProfile, acc.Pi_sap_image, acc.Pi_network_name) } diff --git a/website/docs/r/pi_placement_group.html.markdown b/website/docs/r/pi_placement_group.html.markdown index a731f272a2..ee4a9c0aed 100644 --- a/website/docs/r/pi_placement_group.html.markdown +++ b/website/docs/r/pi_placement_group.html.markdown @@ -1,5 +1,4 @@ --- - subcategory: "Power Systems" layout: "ibm" page_title: "IBM: pi_placement_group" @@ -8,9 +7,11 @@ description: |- --- # ibm_pi_placement_group + Create or delete a placement group. ## Example usage + The following example enables you to create a placement group with a group policy of affinity: ```terraform @@ -21,11 +22,12 @@ resource "ibm_pi_placement_group" "testacc_placement_group" { } ``` -**Note** -* Please find [supported Regions](https://cloud.ibm.com/apidocs/power-cloud#endpoint) for endpoints. -* If a Power cloud instance is provisioned at `lon04`, The provider level attributes should be as follows: - * `region` - `lon` - * `zone` - `lon04` +### Notes + +- Please find [supported Regions](https://cloud.ibm.com/apidocs/power-cloud#endpoint) for endpoints. +- If a Power cloud instance is provisioned at `lon04`, The provider level attributes should be as follows: + - `region` - `lon` + - `zone` - `lon04` Example usage: @@ -43,16 +45,16 @@ ibm_pi_placement_group provides the following [timeouts](https://www.terraform.i - **create** - (Default 60 minutes) Used for creating a placement group. - **delete** - (Default 60 minutes) Used for deleting a placement group. - ## Argument reference -Review the argument references that you can specify for your resource. -- `pi_cloud_instance_id` - (Required, String) The GUID of the service instance associated with an account. -- `pi_placement_group_name` - (Required, String) The name of the placement group. -- `pi_placement_group_policy` - (Required, String) The value of the group's affinity policy. Valid values are `affinity` and `anti-affinity`. +Review the argument references that you can specify for your resource. +- `pi_cloud_instance_id` - (Required, String) The GUID of the service instance associated with an account. +- `pi_placement_group_name` - (Required, String) The name of the placement group. +- `pi_placement_group_policy` - (Required, String) The value of the group's affinity policy. Valid values are `affinity` and `anti-affinity`. ## Attribute reference + In addition to all argument reference list, you can access the following attribute reference after your resource is created. - `id` - (String) The unique identifier of the placement group. @@ -63,8 +65,8 @@ Review the argument references that you can specify for your resource. The `ibm_pi_placement_group` resource can be imported by using `power_instance_id` and `placement_group_id`. -**Example** +### Example -``` -$ terraform import ibm_pi_placement_group.example d7bec597-4726-451f-8a63-e62e6f19c32c/b17a2b7f-77ab-491c-811e-495f8d4c8947 +```bash +terraform import ibm_pi_placement_group.example d7bec597-4726-451f-8a63-e62e6f19c32c/b17a2b7f-77ab-491c-811e-495f8d4c8947 ```