From 0c14bf6b3389e96e7cea7f6de37039e29f684c16 Mon Sep 17 00:00:00 2001 From: upodroid Date: Thu, 2 Sep 2021 17:39:07 +0100 Subject: [PATCH 1/3] allow disabling service accounts Co-authored-by: upodroid --- .../resource_google_service_account.go | 36 ++++++++++ .../resource_google_service_account_test.go | 70 +++++++++++++++++++ .../r/google_service_account.html.markdown | 6 +- 3 files changed, 111 insertions(+), 1 deletion(-) diff --git a/mmv1/third_party/terraform/resources/resource_google_service_account.go b/mmv1/third_party/terraform/resources/resource_google_service_account.go index ac8c64ab18f7..b60bb2406545 100644 --- a/mmv1/third_party/terraform/resources/resource_google_service_account.go +++ b/mmv1/third_party/terraform/resources/resource_google_service_account.go @@ -50,6 +50,12 @@ func resourceGoogleServiceAccount() *schema.Resource { Optional: true, Description: `The display name for the service account. Can be updated without creating a new resource.`, }, + "disabled": { + Type: schema.TypeBool, + Optional: true, + Default: false, + Description: `Whether the service account is disabled. Defaults to false`, + }, "description": { Type: schema.TypeString, Optional: true, @@ -146,6 +152,9 @@ func resourceGoogleServiceAccountRead(d *schema.ResourceData, meta interface{}) if err := d.Set("description", sa.Description); err != nil { return fmt.Errorf("Error setting description: %s", err) } + if err := d.Set("disabled", sa.Disabled); err != nil { + return fmt.Errorf("Error setting disabled: %s", err) + } return nil } @@ -181,6 +190,33 @@ func resourceGoogleServiceAccountUpdate(d *schema.ResourceData, meta interface{} if d.HasChange("display_name") { updateMask = append(updateMask, "display_name") } + + // We want to skip the Patch Call below if only the enabled field has been changed + + if d.HasChange("disabled") && !d.Get("disabled").(bool) { + + _, err = config.NewIamClient(userAgent).Projects.ServiceAccounts.Enable(d.Id(), + &iam.EnableServiceAccountRequest{}).Do() + if err != nil { + return err + } + + if len(updateMask) == 0 { + return nil + } + + } else if d.HasChange("disabled") && d.Get("disabled").(bool) { + _, err = config.NewIamClient(userAgent).Projects.ServiceAccounts.Disable(d.Id(), + &iam.DisableServiceAccountRequest{}).Do() + if err != nil { + return err + } + + if len(updateMask) == 0 { + return nil + } + } + _, err = config.NewIamClient(userAgent).Projects.ServiceAccounts.Patch(d.Id(), &iam.PatchServiceAccountRequest{ UpdateMask: strings.Join(updateMask, ","), diff --git a/mmv1/third_party/terraform/tests/resource_google_service_account_test.go b/mmv1/third_party/terraform/tests/resource_google_service_account_test.go index 89e8eac5d5e8..8d34dda19742 100644 --- a/mmv1/third_party/terraform/tests/resource_google_service_account_test.go +++ b/mmv1/third_party/terraform/tests/resource_google_service_account_test.go @@ -84,6 +84,65 @@ func TestAccServiceAccount_basic(t *testing.T) { }) } +func TestAccServiceAccount_Disabled(t *testing.T) { + t.Parallel() + + accountId := "a" + randString(t, 10) + uniqueId := "" + displayName := "Terraform Test" + desc := "test description" + project := getTestProjectFromEnv() + expectedEmail := fmt.Sprintf("%s@%s.iam.gserviceaccount.com", accountId, project) + vcrTest(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + Providers: testAccProviders, + Steps: []resource.TestStep{ + // The first step creates a basic service account + { + Config: testAccServiceAccountBasic(accountId, displayName, desc), + Check: resource.ComposeTestCheckFunc( + resource.TestCheckResourceAttr( + "google_service_account.acceptance", "project", project), + ), + }, + { + ResourceName: "google_service_account.acceptance", + ImportStateId: fmt.Sprintf("projects/%s/serviceAccounts/%s", project, expectedEmail), + ImportState: true, + ImportStateVerify: true, + }, + // The second step disables the service account + { + Config: testAccServiceAccountBasicDisabled(accountId, displayName, desc, true), + Check: resource.ComposeTestCheckFunc( + resource.TestCheckResourceAttr( + "google_service_account.acceptance", "project", project), + testAccStoreServiceAccountUniqueId(&uniqueId), + ), + }, + { + ResourceName: "google_service_account.acceptance", + ImportState: true, + ImportStateVerify: true, + }, + // The second step enables the disabled service account + { + Config: testAccServiceAccountBasicDisabled(accountId, displayName, desc, false), + Check: resource.ComposeTestCheckFunc( + resource.TestCheckResourceAttr( + "google_service_account.acceptance", "project", project), + testAccStoreServiceAccountUniqueId(&uniqueId), + ), + }, + { + ResourceName: "google_service_account.acceptance", + ImportState: true, + ImportStateVerify: true, + }, + }, + }) +} + func testAccStoreServiceAccountUniqueId(uniqueId *string) resource.TestCheckFunc { return func(s *terraform.State) error { *uniqueId = s.RootModule().Resources["google_service_account.acceptance"].Primary.Attributes["unique_id"] @@ -111,3 +170,14 @@ resource "google_service_account" "acceptance" { } `, project, account, name) } + +func testAccServiceAccountBasicDisabled(account, name, desc string, disabled bool) string { + return fmt.Sprintf(` +resource "google_service_account" "acceptance" { + account_id = "%v" + display_name = "%v" + description = "%v" + disabled = "%t" +} +`, account, name, desc, disabled) +} diff --git a/mmv1/third_party/terraform/website/docs/r/google_service_account.html.markdown b/mmv1/third_party/terraform/website/docs/r/google_service_account.html.markdown index 96c2ffe13490..0ba4ccbc654a 100644 --- a/mmv1/third_party/terraform/website/docs/r/google_service_account.html.markdown +++ b/mmv1/third_party/terraform/website/docs/r/google_service_account.html.markdown @@ -15,7 +15,8 @@ Allows management of a Google Cloud service account. * How-to Guides * [Official Documentation](https://cloud.google.com/compute/docs/access/service-accounts) --> **Warning:** If you delete and recreate a service account, you must reapply any IAM roles that it had before. +-> **Warning:** If you delete and recreate a service account, you must reapply any IAM roles that it had before. Also don't use this resource to +import the Compute Engine default service account as account_id field **cannot** start with a number. -> Creation of service accounts is eventually consistent, and that can lead to errors when you try to apply ACLs to service accounts immediately after @@ -48,6 +49,9 @@ The following arguments are supported: * `description` - (Optional) A text description of the service account. Must be less than or equal to 256 UTF-8 bytes. +* `disabled` - (Optional) Whether a service account is disabled or not. Defaults to `false`. This field has no effect during creation. + Must be set after creation to disable a service account. + * `project` - (Optional) The ID of the project that the service account will be created in. Defaults to the provider project configuration. From ef105d3af5eeb56c454f49d4d1146978608cb306 Mon Sep 17 00:00:00 2001 From: upodroid Date: Thu, 2 Sep 2021 17:52:39 +0100 Subject: [PATCH 2/3] fix typos --- .../resources/resource_google_service_account.go | 4 +--- .../tests/resource_google_service_account_test.go | 8 ++++---- 2 files changed, 5 insertions(+), 7 deletions(-) diff --git a/mmv1/third_party/terraform/resources/resource_google_service_account.go b/mmv1/third_party/terraform/resources/resource_google_service_account.go index b60bb2406545..3670c890e068 100644 --- a/mmv1/third_party/terraform/resources/resource_google_service_account.go +++ b/mmv1/third_party/terraform/resources/resource_google_service_account.go @@ -191,10 +191,8 @@ func resourceGoogleServiceAccountUpdate(d *schema.ResourceData, meta interface{} updateMask = append(updateMask, "display_name") } - // We want to skip the Patch Call below if only the enabled field has been changed - + // We want to skip the Patch Call below if only the disabled field has been changed if d.HasChange("disabled") && !d.Get("disabled").(bool) { - _, err = config.NewIamClient(userAgent).Projects.ServiceAccounts.Enable(d.Id(), &iam.EnableServiceAccountRequest{}).Do() if err != nil { diff --git a/mmv1/third_party/terraform/tests/resource_google_service_account_test.go b/mmv1/third_party/terraform/tests/resource_google_service_account_test.go index 8d34dda19742..88aa1143a561 100644 --- a/mmv1/third_party/terraform/tests/resource_google_service_account_test.go +++ b/mmv1/third_party/terraform/tests/resource_google_service_account_test.go @@ -113,7 +113,7 @@ func TestAccServiceAccount_Disabled(t *testing.T) { }, // The second step disables the service account { - Config: testAccServiceAccountBasicDisabled(accountId, displayName, desc, true), + Config: testAccServiceAccountDisabled(accountId, displayName, desc, true), Check: resource.ComposeTestCheckFunc( resource.TestCheckResourceAttr( "google_service_account.acceptance", "project", project), @@ -125,9 +125,9 @@ func TestAccServiceAccount_Disabled(t *testing.T) { ImportState: true, ImportStateVerify: true, }, - // The second step enables the disabled service account + // The third step enables the disabled service account { - Config: testAccServiceAccountBasicDisabled(accountId, displayName, desc, false), + Config: testAccServiceAccountDisabled(accountId, displayName, desc, false), Check: resource.ComposeTestCheckFunc( resource.TestCheckResourceAttr( "google_service_account.acceptance", "project", project), @@ -171,7 +171,7 @@ resource "google_service_account" "acceptance" { `, project, account, name) } -func testAccServiceAccountBasicDisabled(account, name, desc string, disabled bool) string { +func testAccServiceAccountDisabled(account, name, desc string, disabled bool) string { return fmt.Sprintf(` resource "google_service_account" "acceptance" { account_id = "%v" From 6b894116a7facdfd2b0cd2aef568b7976ad3e0e2 Mon Sep 17 00:00:00 2001 From: upodroid Date: Tue, 7 Sep 2021 22:59:38 +0100 Subject: [PATCH 3/3] revert warning change --- .../website/docs/r/google_service_account.html.markdown | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/mmv1/third_party/terraform/website/docs/r/google_service_account.html.markdown b/mmv1/third_party/terraform/website/docs/r/google_service_account.html.markdown index 0ba4ccbc654a..394a0cba4002 100644 --- a/mmv1/third_party/terraform/website/docs/r/google_service_account.html.markdown +++ b/mmv1/third_party/terraform/website/docs/r/google_service_account.html.markdown @@ -15,8 +15,7 @@ Allows management of a Google Cloud service account. * How-to Guides * [Official Documentation](https://cloud.google.com/compute/docs/access/service-accounts) --> **Warning:** If you delete and recreate a service account, you must reapply any IAM roles that it had before. Also don't use this resource to -import the Compute Engine default service account as account_id field **cannot** start with a number. +-> **Warning:** If you delete and recreate a service account, you must reapply any IAM roles that it had before. -> Creation of service accounts is eventually consistent, and that can lead to errors when you try to apply ACLs to service accounts immediately after