Skip to content

Commit f8daf3b

Browse files
authored
test(iam): member assignment acceptance tests (#55)
1 parent c9681c0 commit f8daf3b

File tree

8 files changed

+334
-144
lines changed

8 files changed

+334
-144
lines changed

go.mod

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -40,9 +40,7 @@ require (
4040
github.com/hashicorp/terraform-registry-address v0.2.2 // indirect
4141
github.com/hashicorp/terraform-svchost v0.1.1 // indirect
4242
github.com/hashicorp/yamux v0.1.1 // indirect
43-
github.com/klauspost/compress v1.17.2 // indirect
4443
github.com/kr/pretty v0.3.1 // indirect
45-
github.com/kr/text v0.2.0 // indirect
4644
github.com/mattn/go-colorable v0.1.13 // indirect
4745
github.com/mattn/go-isatty v0.0.20 // indirect
4846
github.com/mitchellh/copystructure v1.2.0 // indirect
@@ -52,7 +50,6 @@ require (
5250
github.com/mitchellh/reflectwalk v1.0.2 // indirect
5351
github.com/oklog/run v1.1.0 // indirect
5452
github.com/pmezard/go-difflib v1.0.0 // indirect
55-
github.com/rogpeppe/go-internal v1.9.0 // indirect
5653
github.com/stretchr/objx v0.5.1 // indirect
5754
github.com/vmihailenco/msgpack v4.0.4+incompatible // indirect
5855
github.com/vmihailenco/msgpack/v5 v5.4.0 // indirect
@@ -65,12 +62,10 @@ require (
6562
golang.org/x/sys v0.13.0 // indirect
6663
golang.org/x/text v0.13.0 // indirect
6764
google.golang.org/appengine v1.6.8 // indirect
68-
google.golang.org/genproto v0.0.0-20231012201019-e917dd12ba7a // indirect
6965
google.golang.org/genproto/googleapis/rpc v0.0.0-20231016165738-49dd2c1f3d0b // indirect
7066
google.golang.org/grpc v1.59.0 // indirect
7167
google.golang.org/protobuf v1.31.0 // indirect
7268
gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c // indirect
73-
gopkg.in/yaml.v2 v2.4.0 // indirect
7469
gopkg.in/yaml.v3 v3.0.1 // indirect
7570
nhooyr.io/websocket v1.8.9 // indirect
7671
)

go.sum

Lines changed: 5 additions & 108 deletions
Large diffs are not rendered by default.

monte_carlo/client/monte_carlo_client.go

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -211,11 +211,11 @@ type GetTables struct {
211211
}
212212

213213
type User struct {
214-
Id string
215-
Email string
216-
FirstName string
217-
LastName string
218-
IsSso bool
214+
CognitoUserId string
215+
Email string
216+
FirstName string
217+
LastName string
218+
IsSso bool
219219
}
220220

221221
type AuthorizationGroup struct {
@@ -232,7 +232,7 @@ type AuthorizationGroup struct {
232232
type CreateOrUpdateAuthorizationGroup struct {
233233
CreateOrUpdateAuthorizationGroup struct {
234234
AuthorizationGroup AuthorizationGroup
235-
} `graphql:"createOrUpdateAuthorizationGroup(name: $name, label: $label, description: $description, roles: $roles, domainRestrictionIds: $domainRestrictionIds, ssoGroup: $ssoGroup)"`
235+
} `graphql:"createOrUpdateAuthorizationGroup(name: $name, label: $label, description: $description, roles: $roles, memberUserIds: $memberUserIds, domainRestrictionIds: $domainRestrictionIds, ssoGroup: $ssoGroup)"`
236236
}
237237

238238
type GetAuthorizationGroups struct {
@@ -247,13 +247,13 @@ type DeleteAuthorizationGroup struct {
247247

248248
type GetUsersInAccount struct {
249249
GetUsersInAccount struct {
250-
Edges []struct{
250+
Edges []struct {
251251
Node User
252252
}
253253
PageInfo struct {
254254
StartCursor string
255255
EndCursor string
256256
HasNextPage bool
257257
}
258-
} `graphql:"getTables(email: $email, first: $first, after: $after)"`
258+
} `graphql:"getUsersInAccount(email: $email, first: $first, after: $after)"`
259259
}

monte_carlo/provider/provider.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,7 @@ func (p *Provider) Resources(ctx context.Context) []func() resource.Resource {
9797
resources.NewTransactionalWarehouseResource,
9898
resources.NewDomainResource,
9999
resources.NewIamGroupResource,
100+
resources.NewIamMemberResource,
100101
}
101102
}
102103

monte_carlo/resources/iam_group.go

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -122,6 +122,7 @@ func (r *IamGroupResource) Create(ctx context.Context, req resource.CreateReques
122122
"roles": []string{data.Role.ValueString()},
123123
"domainRestrictionIds": normalize[client.UUID](data.Domains),
124124
"ssoGroup": data.SsoGroup.ValueStringPointer(),
125+
"memberUserIds": (*[]string)(nil),
125126
}
126127

127128
if err := r.client.Mutate(ctx, &createResult, variables); err == nil {
@@ -165,7 +166,7 @@ func (r *IamGroupResource) Read(ctx context.Context, req resource.ReadRequest, r
165166
data.Label = types.StringValue(found.Label)
166167
data.Description = types.StringValue(found.Description)
167168
data.Role = denormalize(rolesToNames(found.Roles))[0]
168-
data.Domains = denormalize(domainsToUuids(found.DomainRestrictions))
169+
data.Domains = denormalize(domainsToUuids[string](found.DomainRestrictions))
169170
data.SsoGroup = types.StringPointerValue(found.SsoGroup)
170171
resp.Diagnostics.Append(resp.State.Set(ctx, &data)...)
171172
}
@@ -186,6 +187,7 @@ func (r *IamGroupResource) Update(ctx context.Context, req resource.UpdateReques
186187
"roles": []string{data.Role.ValueString()},
187188
"domainRestrictionIds": normalize[client.UUID](data.Domains),
188189
"ssoGroup": data.SsoGroup.ValueStringPointer(),
190+
"memberUserIds": (*[]string)(nil),
189191
}
190192

191193
if err := r.client.Mutate(ctx, &updateResult, variables); err == nil {
@@ -230,10 +232,10 @@ func rolesToNames(roles []struct{ Name string }) []string {
230232
return result
231233
}
232234

233-
func domainsToUuids(domains []struct{ Uuid string }) []string {
234-
result := make([]string, len(domains))
235+
func domainsToUuids[T ~string](domains []struct{ Uuid string }) []T {
236+
result := make([]T, len(domains))
235237
for i, domain := range domains {
236-
result[i] = domain.Uuid
238+
result[i] = T(domain.Uuid)
237239
}
238240
return result
239241
}

monte_carlo/resources/iam_group_test.go

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -53,8 +53,7 @@ func TestAccIamGroupResource(t *testing.T) {
5353
ImportStateId: name,
5454
ImportStateVerifyIdentifierAttribute: "name",
5555
},
56-
// Update and Read testing
57-
{
56+
{ // Update and Read testing
5857
Config: iamGroupConfig(name, roleUpdate, &domainsUpdate, &ssoGroupUpdate),
5958
Check: resource.ComposeAggregateTestCheckFunc(
6059
resource.TestCheckResourceAttr("montecarlo_iam_group.test", "name", name),

monte_carlo/resources/iam_member.go

Lines changed: 27 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ import (
1111
"github.com/kiwicom/terraform-provider-montecarlo/monte_carlo/common"
1212

1313
"github.com/hashicorp/terraform-plugin-framework-validators/stringvalidator"
14+
"github.com/hashicorp/terraform-plugin-framework/path"
1415
"github.com/hashicorp/terraform-plugin-framework/resource"
1516
"github.com/hashicorp/terraform-plugin-framework/resource/schema"
1617
"github.com/hashicorp/terraform-plugin-framework/resource/schema/planmodifier"
@@ -20,7 +21,7 @@ import (
2021
)
2122

2223
var groupsRegex = regexp.MustCompile(`^groups/.+$`)
23-
var memberRegex = regexp.MustCompile(`^user/.+$`)
24+
var memberRegex = regexp.MustCompile(`^user:.+$`)
2425

2526
// Ensure provider defined types fully satisfy framework interfaces.
2627
var _ resource.Resource = &IamMemberResource{}
@@ -56,7 +57,7 @@ func (r *IamMemberResource) Schema(ctx context.Context, req resource.SchemaReque
5657
stringplanmodifier.RequiresReplaceIfConfigured(),
5758
},
5859
Validators: []validator.String{
59-
stringvalidator.RegexMatches(groupsRegex, "Expected format: groups/{group_name}"),
60+
stringvalidator.RegexMatches(groupsRegex, "Expected format - groups/{group_name}"),
6061
},
6162
},
6263
"member": schema.StringAttribute{
@@ -65,7 +66,7 @@ func (r *IamMemberResource) Schema(ctx context.Context, req resource.SchemaReque
6566
stringplanmodifier.RequiresReplaceIfConfigured(),
6667
},
6768
Validators: []validator.String{
68-
stringvalidator.RegexMatches(memberRegex, "Expected format: user/{user_email}"),
69+
stringvalidator.RegexMatches(memberRegex, "Expected format - user:{user_email}"),
6970
},
7071
},
7172
"member_id": schema.StringAttribute{
@@ -92,7 +93,7 @@ func (r *IamMemberResource) Create(ctx context.Context, req resource.CreateReque
9293
return
9394
}
9495

95-
userEmail := strings.Split(data.Member.ValueString(), "user/")[1]
96+
userEmail := strings.Split(data.Member.ValueString(), "user:")[1]
9697
getUserResult := client.GetUsersInAccount{}
9798
variables := map[string]interface{}{
9899
"email": userEmail,
@@ -101,7 +102,7 @@ func (r *IamMemberResource) Create(ctx context.Context, req resource.CreateReque
101102
}
102103

103104
if err := r.client.Query(ctx, &getUserResult, variables); err != nil {
104-
to_print := fmt.Sprintf("MC client 'getTables' query result - %s", err.Error())
105+
to_print := fmt.Sprintf("MC client 'getUsersInAccount' query result - %s", err.Error())
105106
resp.Diagnostics.AddError(to_print, "")
106107
return
107108
} else if len(getUserResult.GetUsersInAccount.Edges) == 0 {
@@ -131,9 +132,9 @@ func (r *IamMemberResource) Create(ctx context.Context, req resource.CreateReque
131132
}
132133

133134
memberUserIds := make([]string, len(found.Users)+1)
134-
memberUserIds[len(found.Users)] = getUserResult.GetUsersInAccount.Edges[0].Node.Id
135+
memberUserIds[len(found.Users)] = getUserResult.GetUsersInAccount.Edges[0].Node.CognitoUserId
135136
for i, user := range found.Users {
136-
memberUserIds[i] = user.Id
137+
memberUserIds[i] = user.CognitoUserId
137138
}
138139

139140
updateResult := client.CreateOrUpdateAuthorizationGroup{}
@@ -142,7 +143,7 @@ func (r *IamMemberResource) Create(ctx context.Context, req resource.CreateReque
142143
"label": found.Label,
143144
"description": found.Description,
144145
"roles": rolesToNames(found.Roles),
145-
"domainRestrictionIds": domainsToUuids(found.DomainRestrictions),
146+
"domainRestrictionIds": domainsToUuids[client.UUID](found.DomainRestrictions),
146147
"ssoGroup": found.SsoGroup,
147148
"memberUserIds": memberUserIds,
148149
}
@@ -151,7 +152,7 @@ func (r *IamMemberResource) Create(ctx context.Context, req resource.CreateReque
151152
to_print := fmt.Sprintf("MC client 'createOrUpdateAuthorizationGroup' mutation result - %s", err.Error())
152153
resp.Diagnostics.AddError(to_print, "")
153154
} else {
154-
data.MemberId = types.StringValue(getUserResult.GetUsersInAccount.Edges[0].Node.Id)
155+
data.MemberId = types.StringValue(getUserResult.GetUsersInAccount.Edges[0].Node.CognitoUserId)
155156
resp.Diagnostics.Append(resp.State.Set(ctx, &data)...)
156157
}
157158
}
@@ -163,7 +164,7 @@ func (r *IamMemberResource) Read(ctx context.Context, req resource.ReadRequest,
163164
return
164165
}
165166

166-
userEmail := strings.Split(data.Member.ValueString(), "user/")[1]
167+
userEmail := strings.Split(data.Member.ValueString(), "user:")[1]
167168
getUserResult := client.GetUsersInAccount{}
168169
variables := map[string]interface{}{
169170
"email": userEmail,
@@ -172,7 +173,7 @@ func (r *IamMemberResource) Read(ctx context.Context, req resource.ReadRequest,
172173
}
173174

174175
if err := r.client.Query(ctx, &getUserResult, variables); err != nil {
175-
to_print := fmt.Sprintf("MC client 'getTables' query result - %s", err.Error())
176+
to_print := fmt.Sprintf("MC client 'getUsersInAccount' query result - %s", err.Error())
176177
resp.Diagnostics.AddError(to_print, "")
177178
return
178179
} else if len(getUserResult.GetUsersInAccount.Edges) == 0 {
@@ -200,13 +201,14 @@ func (r *IamMemberResource) Read(ctx context.Context, req resource.ReadRequest,
200201

201202
if found == nil || found.SsoGroup != nil {
202203
to_print := fmt.Sprintf("Group %s not found or is SSO managed", data.Group.ValueString())
203-
resp.Diagnostics.AddError(to_print, "")
204+
resp.Diagnostics.AddWarning(to_print, "")
205+
resp.State.RemoveResource(ctx)
204206
} else if !slices.Contains(found.Users, getUserResult.GetUsersInAccount.Edges[0].Node) {
205207
to_print := fmt.Sprintf("User %s not found in group %s", userEmail, data.Group.ValueString())
206208
resp.Diagnostics.AddWarning(to_print, "")
207209
resp.State.RemoveResource(ctx)
208210
} else {
209-
data.MemberId = types.StringValue(getUserResult.GetUsersInAccount.Edges[0].Node.Id)
211+
data.MemberId = types.StringValue(getUserResult.GetUsersInAccount.Edges[0].Node.CognitoUserId)
210212
resp.Diagnostics.Append(resp.State.Set(ctx, &data)...)
211213
}
212214
}
@@ -227,7 +229,7 @@ func (r *IamMemberResource) Delete(ctx context.Context, req resource.DeleteReque
227229
variables := map[string]interface{}{}
228230
if err := r.client.Query(ctx, &getGroupResult, variables); err != nil {
229231
to_print := fmt.Sprintf("MC client 'GetAuthorizationGroups' query result - %s", err.Error())
230-
resp.Diagnostics.AddWarning(to_print, "")
232+
resp.Diagnostics.AddError(to_print, "")
231233
return
232234
}
233235

@@ -244,7 +246,7 @@ func (r *IamMemberResource) Delete(ctx context.Context, req resource.DeleteReque
244246

245247
memberUserIds := make([]string, len(found.Users))
246248
for i, user := range found.Users {
247-
memberUserIds[i] = user.Id
249+
memberUserIds[i] = user.CognitoUserId
248250
}
249251

250252
updateResult := client.CreateOrUpdateAuthorizationGroup{}
@@ -254,7 +256,7 @@ func (r *IamMemberResource) Delete(ctx context.Context, req resource.DeleteReque
254256
"label": found.Label,
255257
"description": found.Description,
256258
"roles": rolesToNames(found.Roles),
257-
"domainRestrictionIds": domainsToUuids(found.DomainRestrictions),
259+
"domainRestrictionIds": domainsToUuids[client.UUID](found.DomainRestrictions),
258260
"ssoGroup": found.SsoGroup,
259261
"memberUserIds": memberUserIds,
260262
}
@@ -266,5 +268,13 @@ func (r *IamMemberResource) Delete(ctx context.Context, req resource.DeleteReque
266268
}
267269

268270
func (r *IamMemberResource) ImportState(ctx context.Context, req resource.ImportStateRequest, resp *resource.ImportStateResponse) {
269-
// TODO
271+
idsImported := strings.Split(req.ID, ",")
272+
if len(idsImported) == 2 && idsImported[0] != "" && idsImported[1] != "" {
273+
resp.Diagnostics.Append(resp.State.SetAttribute(ctx, path.Root("group"), idsImported[0])...)
274+
resp.Diagnostics.Append(resp.State.SetAttribute(ctx, path.Root("member"), idsImported[1])...)
275+
} else {
276+
resp.Diagnostics.AddError("Unexpected Import Identifier", fmt.Sprintf(
277+
"Expected import identifier with format: groups/<group_name>,user:<user_email>. Got: %q", req.ID),
278+
)
279+
}
270280
}

0 commit comments

Comments
 (0)