Skip to content

Commit

Permalink
fix: support multiple grant_privilege_to_role resources on the same r…
Browse files Browse the repository at this point in the history
…ole (#1953)

* Add failng test with multiple grant resources.

* Support multiple grants resources on same role.
  • Loading branch information
sfc-gh-ngaberel authored Jul 17, 2023
1 parent 65e779c commit dfdd166
Show file tree
Hide file tree
Showing 2 changed files with 76 additions and 3 deletions.
11 changes: 8 additions & 3 deletions pkg/resources/grant_privileges_to_role.go
Original file line number Diff line number Diff line change
Expand Up @@ -568,7 +568,7 @@ func ReadGrantPrivilegesToRole(d *schema.ResourceData, meta interface{}) error {
}
}

err := readAccountRoleGrantPrivileges(ctx, client, grantOn, resourceID.Future, &opts, d)
err := readAccountRoleGrantPrivileges(ctx, client, grantOn, resourceID, &opts, d)
if err != nil {
return err
}
Expand Down Expand Up @@ -820,7 +820,7 @@ func setAccountRolePrivilegeOptions(privileges []string, allPrivileges bool, onA
return nil
}

func readAccountRoleGrantPrivileges(ctx context.Context, client *sdk.Client, grantedOn sdk.ObjectType, onFuture bool, opts *sdk.ShowGrantOptions, d *schema.ResourceData) error {
func readAccountRoleGrantPrivileges(ctx context.Context, client *sdk.Client, grantedOn sdk.ObjectType, id GrantPrivilegesToAccountRoleID, opts *sdk.ShowGrantOptions, d *schema.ResourceData) error {
grants, err := client.Grants.Show(ctx, opts)
if err != nil {
return fmt.Errorf("error retrieving grants for account role: %w", err)
Expand All @@ -831,10 +831,15 @@ func readAccountRoleGrantPrivileges(ctx context.Context, client *sdk.Client, gra
roleName := d.Get("role_name").(string)

for _, grant := range grants {
// Only consider privileges that are already present in the ID so we
// don't delete privileges managed by other resources.
if !slices.Contains(id.Privileges, grant.Privilege) {
continue
}
if grant.GrantOption == withGrantOption && grant.GranteeName.Name() == roleName {
// future grants do not have grantedBy, only current grants do. If grantedby
// is an empty string it means the grant could not have been created by terraform
if !onFuture && grant.GrantedBy.Name() == "" {
if !id.Future && grant.GrantedBy.Name() == "" {
continue
}
if grantedOn == grant.GrantedOn {
Expand Down
68 changes: 68 additions & 0 deletions pkg/resources/grant_privileges_to_role_acceptance_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -833,3 +833,71 @@ func grantPrivilegesToRole_onSchemaObject_futureInDatabase(name string, privileg
}
`, name, name, name, privilegesString)
}

func TestAccGrantPrivilegesToRole_multipleResources(t *testing.T) {
name := strings.ToUpper(acctest.RandStringFromCharSet(10, acctest.CharSetAlpha))

resource.ParallelTest(t, resource.TestCase{
Providers: providers(),
CheckDestroy: nil,
Steps: []resource.TestStep{
{
Config: grantPrivilegesToRole_multipleResources(name, []string{"CREATE ACCOUNT", "CREATE ROLE"}, []string{"IMPORT SHARE", "MANAGE GRANTS"}),
Check: resource.ComposeTestCheckFunc(
resource.TestCheckResourceAttr("snowflake_grant_privileges_to_role.g1", "role_name", name),
resource.TestCheckResourceAttr("snowflake_grant_privileges_to_role.g1", "privileges.#", "2"),
resource.TestCheckResourceAttr("snowflake_grant_privileges_to_role.g1", "privileges.0", "CREATE ACCOUNT"),
resource.TestCheckResourceAttr("snowflake_grant_privileges_to_role.g1", "privileges.1", "CREATE ROLE"),

resource.TestCheckResourceAttr("snowflake_grant_privileges_to_role.g2", "role_name", name),
resource.TestCheckResourceAttr("snowflake_grant_privileges_to_role.g2", "privileges.#", "2"),
resource.TestCheckResourceAttr("snowflake_grant_privileges_to_role.g2", "privileges.0", "IMPORT SHARE"),
resource.TestCheckResourceAttr("snowflake_grant_privileges_to_role.g2", "privileges.1", "MANAGE GRANTS"),
),
},
// IMPORT
{
ResourceName: "snowflake_grant_privileges_to_role.g1",
ImportState: true,
ImportStateVerify: true,
},
{
ResourceName: "snowflake_grant_privileges_to_role.g2",
ImportState: true,
ImportStateVerify: true,
},
},
})
}

func grantPrivilegesToRole_multipleResources(name string, privileges1, privileges2 []string) string {
doubleQuotePrivileges1 := make([]string, len(privileges1))
for i, p := range privileges1 {
doubleQuotePrivileges1[i] = fmt.Sprintf(`"%v"`, p)
}
privilegesString1 := strings.Join(doubleQuotePrivileges1, ",")

doubleQuotePrivileges2 := make([]string, len(privileges2))
for i, p := range privileges2 {
doubleQuotePrivileges2[i] = fmt.Sprintf(`"%v"`, p)
}
privilegesString2 := strings.Join(doubleQuotePrivileges2, ",")

return fmt.Sprintf(`
resource "snowflake_role" "r" {
name = "%v"
}
resource "snowflake_grant_privileges_to_role" "g1" {
role_name = snowflake_role.r.name
privileges = [%s]
on_account = true
}
resource "snowflake_grant_privileges_to_role" "g2" {
role_name = snowflake_role.r.name
privileges = [%s]
on_account = true
}
`, name, privilegesString1, privilegesString2)
}

0 comments on commit dfdd166

Please sign in to comment.