From d6bbf4307c6062f86c66c2c708b812c6303ad0e8 Mon Sep 17 00:00:00 2001 From: Dan Corne Date: Mon, 30 Oct 2023 11:30:44 +0000 Subject: [PATCH] Name AWS groups from the email address when using groups sync method We're using the other sync method, "user_groups", but would like to switch to the "groups" on because it runs a lot more efficiently, just over 4.5 minutes compared to the "user_groups" one which is timing out at 15 minutes near the end of the process. Unfortunately, the "groups" method names AWS group from the email address in Google i.e. $name@$domain.com. The more efficient method, "groups", uses the name of the group in Google i.e. $name. This means if we switch, it'll remove all the old groups and create new ones, which will then remove everyone's permissions until the account assignments are added to the new groups. This process is easy in Terraform, but would create an outage on permissions and has the same problem when switching back as well. Instead, let's set the "groups" method to name them after the email as well. I've also removed a duplicate loop and ran the LSP formatter on the code. Most formatting changes are whitespace so easy to ignore. --- internal/sync.go | 74 ++++++++++++++++++++++--------------------- internal/sync_test.go | 42 ++++++++++++------------ 2 files changed, 59 insertions(+), 57 deletions(-) diff --git a/internal/sync.go b/internal/sync.go index 7df5fede..22f0330d 100644 --- a/internal/sync.go +++ b/internal/sync.go @@ -66,13 +66,14 @@ func New(cfg *config.Config, a aws.Client, g google.Client, ids identitystoreifa // References: // * https://developers.google.com/admin-sdk/directory/v1/guides/search-users // query possible values: -// '' --> empty or not defined -// name:'Jane' -// email:admin* -// isAdmin=true -// manager='janesmith@example.com' -// orgName=Engineering orgTitle:Manager -// EmploymentData.projects:'GeneGnomes' +// "" --> empty or not defined +// +// name:'Jane' +// email:admin* +// isAdmin=true +// manager='janesmith@example.com' +// orgName=Engineering orgTitle:Manager +// EmploymentData.projects:'GeneGnomes' func (s *syncGSuite) SyncUsers(query string) error { log.Debug("get deleted users") deletedUsers, err := s.google.GetDeletedUsers() @@ -165,13 +166,14 @@ func (s *syncGSuite) SyncUsers(query string) error { // References: // * https://developers.google.com/admin-sdk/directory/v1/guides/search-groups // query possible values: -// '' --> empty or not defined -// name='contact' -// email:admin* -// memberKey=user@company.com -// name:contact* email:contact* -// name:Admin* email:aws-* -// email:aws-* +// "" --> empty or not defined +// +// name='contact' +// email:admin* +// memberKey=user@company.com +// name:contact* email:contact* +// name:Admin* email:aws-* +// email:aws-* func (s *syncGSuite) SyncGroups(query string) error { log.WithField("query", query).Debug("get google groups") @@ -271,20 +273,22 @@ func (s *syncGSuite) SyncGroups(query string) error { // References: // * https://developers.google.com/admin-sdk/directory/v1/guides/search-groups // query possible values: -// '' --> empty or not defined -// name='contact' -// email:admin* -// memberKey=user@company.com -// name:contact* email:contact* -// name:Admin* email:aws-* -// email:aws-* +// "" --> empty or not defined +// +// name='contact' +// email:admin* +// memberKey=user@company.com +// name:contact* email:contact* +// name:Admin* email:aws-* +// email:aws-* +// // process workflow: -// 1) delete users in aws, these were deleted in google -// 2) update users in aws, these were updated in google -// 3) add users in aws, these were added in google -// 4) add groups in aws and add its members, these were added in google -// 5) validate equals aws an google groups members -// 6) delete groups in aws, these were deleted in google +// 1. delete users in aws, these were deleted in google +// 2. update users in aws, these were updated in google +// 3. add users in aws, these were added in google +// 4. add groups in aws and add its members, these were added in google +// 5. validate equals aws an google groups members +// 6. delete groups in aws, these were deleted in google func (s *syncGSuite) SyncGroupsUsers(query string) error { log.WithField("query", query).Info("get google groups") @@ -601,15 +605,13 @@ func getGroupOperations(awsGroups []*aws.Group, googleGroups []*admin.Group) (ad } for _, gGroup := range googleGroups { - googleMap[gGroup.Name] = struct{}{} - } + googleMap[gGroup.Email] = struct{}{} - // AWS Groups found and not found in google - for _, gGroup := range googleGroups { - if _, found := awsMap[gGroup.Name]; found { - equals = append(equals, awsMap[gGroup.Name]) + // AWS Groups found and not found in google + if _, found := awsMap[gGroup.Email]; found { + equals = append(equals, awsMap[gGroup.Email]) } else { - add = append(add, aws.NewGroup(gGroup.Name)) + add = append(add, aws.NewGroup(gGroup.Email)) } } @@ -867,8 +869,8 @@ func ConvertSdkUserObjToNative(user *identitystore.User) *aws.User { for _, email := range user.Emails { if email.Value == nil || email.Type == nil || email.Primary == nil { - // This must be a user created by AWS Control Tower - // Need feature development to make how these users are treated + // This must be a user created by AWS Control Tower + // Need feature development to make how these users are treated // configurable. continue } diff --git a/internal/sync_test.go b/internal/sync_test.go index f76e32fc..b2500c50 100644 --- a/internal/sync_test.go +++ b/internal/sync_test.go @@ -58,19 +58,19 @@ func Test_getGroupOperations(t *testing.T) { name: "equal groups google and aws", args: args{ awsGroups: []*aws.Group{ - aws.NewGroup("Group-1"), - aws.NewGroup("Group-2"), + aws.NewGroup("Group-1@domain.com"), + aws.NewGroup("Group-2@domain.com"), }, googleGroups: []*admin.Group{ - {Name: "Group-1"}, - {Name: "Group-2"}, + {Email: "Group-1@domain.com"}, + {Email: "Group-2@domain.com"}, }, }, wantAdd: nil, wantDelete: nil, wantEquals: []*aws.Group{ - aws.NewGroup("Group-1"), - aws.NewGroup("Group-2"), + aws.NewGroup("Group-1@domain.com"), + aws.NewGroup("Group-2@domain.com"), }, }, { @@ -78,13 +78,13 @@ func Test_getGroupOperations(t *testing.T) { args: args{ awsGroups: nil, googleGroups: []*admin.Group{ - {Name: "Group-1"}, - {Name: "Group-2"}, + {Email: "Group-1@domain.com"}, + {Email: "Group-2@domain.com"}, }, }, wantAdd: []*aws.Group{ - aws.NewGroup("Group-1"), - aws.NewGroup("Group-2"), + aws.NewGroup("Group-1@domain.com"), + aws.NewGroup("Group-2@domain.com"), }, wantDelete: nil, wantEquals: nil, @@ -93,14 +93,14 @@ func Test_getGroupOperations(t *testing.T) { name: "delete two aws groups", args: args{ awsGroups: []*aws.Group{ - aws.NewGroup("Group-1"), - aws.NewGroup("Group-2"), + aws.NewGroup("Group-1@domain.com"), + aws.NewGroup("Group-2@domain.com"), }, googleGroups: nil, }, wantAdd: nil, wantDelete: []*aws.Group{ - aws.NewGroup("Group-1"), - aws.NewGroup("Group-2"), + aws.NewGroup("Group-1@domain.com"), + aws.NewGroup("Group-2@domain.com"), }, wantEquals: nil, }, @@ -108,22 +108,22 @@ func Test_getGroupOperations(t *testing.T) { name: "add one, delete one and one equal", args: args{ awsGroups: []*aws.Group{ - aws.NewGroup("Group-2"), - aws.NewGroup("Group-3"), + aws.NewGroup("Group-2@domain.com"), + aws.NewGroup("Group-3@domain.com"), }, googleGroups: []*admin.Group{ - {Name: "Group-1"}, - {Name: "Group-2"}, + {Email: "Group-1@domain.com"}, + {Email: "Group-2@domain.com"}, }, }, wantAdd: []*aws.Group{ - aws.NewGroup("Group-1"), + aws.NewGroup("Group-1@domain.com"), }, wantDelete: []*aws.Group{ - aws.NewGroup("Group-3"), + aws.NewGroup("Group-3@domain.com"), }, wantEquals: []*aws.Group{ - aws.NewGroup("Group-2"), + aws.NewGroup("Group-2@domain.com"), }, }, }