Skip to content

Commit

Permalink
WIP
Browse files Browse the repository at this point in the history
  • Loading branch information
anvial committed Apr 18, 2024
1 parent 5755767 commit ae0f045
Show file tree
Hide file tree
Showing 7 changed files with 61 additions and 54 deletions.
9 changes: 5 additions & 4 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@ go 1.21
require (
github.com/bflad/tfproviderlint v0.29.0
github.com/hashicorp/terraform-plugin-docs v0.19.0
// juju 3.3.0
github.com/juju/juju v0.0.0-20240418052717-3d086f386814
// juju 3.5.0
github.com/juju/juju v0.0.0-20240406000153-4582af466744

)

Expand All @@ -16,7 +16,7 @@ require (
github.com/hashicorp/terraform-plugin-go v0.22.1
github.com/hashicorp/terraform-plugin-log v0.9.0
github.com/hashicorp/terraform-plugin-testing v1.7.0
github.com/juju/charm/v12 v12.0.1
github.com/juju/charm/v12 v12.0.0
github.com/juju/clock v1.0.3
github.com/juju/cmd/v3 v3.0.14
github.com/juju/collections v1.0.4
Expand Down Expand Up @@ -127,8 +127,9 @@ require (
github.com/juju/lumberjack/v2 v2.0.2 // indirect
github.com/juju/mgo/v3 v3.0.4 // indirect
github.com/juju/mutex/v2 v2.0.0 // indirect
github.com/juju/names/v4 v4.0.0-20220207005702-9c6532a52823 // indirect
github.com/juju/os/v2 v2.2.3 // indirect
github.com/juju/packaging/v3 v3.0.0 // indirect
github.com/juju/packaging/v2 v2.0.1 // indirect
github.com/juju/persistent-cookiejar v1.0.0 // indirect
github.com/juju/proxy v1.0.0 // indirect
github.com/juju/pubsub/v2 v2.0.0 // indirect
Expand Down
14 changes: 8 additions & 6 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -324,8 +324,8 @@ github.com/juju/ansiterm v1.0.0 h1:gmMvnZRq7JZJx6jkfSq9/+2LMrVEwGwt7UR6G+lmDEg=
github.com/juju/ansiterm v1.0.0/go.mod h1:PyXUpnI3olx3bsPcHt98FGPX/KCFZ1Fi+hw1XLI6384=
github.com/juju/blobstore/v3 v3.0.2 h1:roZ4YBuZYmWId6y/6ZLQSAMmNlHOclHD8PQAMOQer6E=
github.com/juju/blobstore/v3 v3.0.2/go.mod h1:NXEgMhrVH5744/zLfSkzsySlDQUpCgzvcNxjJJhICko=
github.com/juju/charm/v12 v12.0.1 h1:C40Vv7Llfj05y86CnxxbQbSdIXdGzP01rajJR63Ni24=
github.com/juju/charm/v12 v12.0.1/go.mod h1:QRuKxXC5zzfPlAa8ipmxX1tvpbIBliueLVHGbs3T7wU=
github.com/juju/charm/v12 v12.0.0 h1:/h3YRMqbgxT89QkQGgMS/myOxuHy/kzBLCDOvodsoFY=
github.com/juju/charm/v12 v12.0.0/go.mod h1:rX3no84EHT+qN+BGtwqPyvueC1Sxr0bXWxsbUd6i1iY=
github.com/juju/clock v1.0.3 h1:yJHIsWXeU8j3QcBdiess09SzfiXRRrsjKPn2whnMeds=
github.com/juju/clock v1.0.3/go.mod h1:HIBvJ8kiV/n7UHwKuCkdYL4l/MDECztHR2sAvWDxxf0=
github.com/juju/cmd/v3 v3.0.14 h1:KuuamArSH7vQ6SdQKEHYK2scEMkJTEZKLs8abrlW3XE=
Expand Down Expand Up @@ -354,8 +354,8 @@ github.com/juju/idmclient/v2 v2.0.0 h1:PsGa092JGy6iFNHZCcao+bigVsTyz1C+tHNRdYmKv
github.com/juju/idmclient/v2 v2.0.0/go.mod h1:EOiFbPmnkqKvCUS/DHpDRWhL7eKF0AJaTvMjIYlIUak=
github.com/juju/jsonschema v1.0.0 h1:2ScR9hhVdHxft+Te3fnclVx61MmlikHNEOirTGi+hV4=
github.com/juju/jsonschema v1.0.0/go.mod h1:SlFW+jFtpWX0P4Tb+zTTPR4ufttLrnJIdQPePxVEfkM=
github.com/juju/juju v0.0.0-20240418052717-3d086f386814 h1:GRea7SuGIEBMAzPGif7RDormNiuMm0LKJP22y1LaNoM=
github.com/juju/juju v0.0.0-20240418052717-3d086f386814/go.mod h1:LN4FXgbHGi5VsBjy0gs+xXDWM0eiOHaAyl6QDF7bCjY=
github.com/juju/juju v0.0.0-20240406000153-4582af466744 h1:IM8Nvz6eJ8vHklgsleP11gUhsPsU0t6ePAPw0NQFtwE=
github.com/juju/juju v0.0.0-20240406000153-4582af466744/go.mod h1:8W1iXQ/tGftslRzNF/1U8mVZFjtqc0zZKygwuIcmbPI=
github.com/juju/loggo v1.0.0 h1:Y6ZMQOGR9Aj3BGkiWx7HBbIx6zNwNkxhVNOHU2i1bl0=
github.com/juju/loggo v1.0.0/go.mod h1:NIXFioti1SmKAlKNuUwbMenNdef59IF52+ZzuOmHYkg=
github.com/juju/lru v1.0.0 h1:FP8mBNF3jBnKwGO5PtsR+8iIegx8DREfhRhpcGpYcn4=
Expand All @@ -366,14 +366,16 @@ github.com/juju/mgo/v3 v3.0.4 h1:ek6YDy71tqikpoFSpvLkpCZ7zvYNYH+xSk/MebMkCEE=
github.com/juju/mgo/v3 v3.0.4/go.mod h1:fAvhDCRbUlEbRIae6UQT8RvPUoLwKnJsBgO6OzHKNxw=
github.com/juju/mutex/v2 v2.0.0 h1:rVmJdOaXGWF8rjcFHBNd4x57/1tks5CgXHx55O55SB0=
github.com/juju/mutex/v2 v2.0.0/go.mod h1:jwCfBs/smYDaeZLqeaCi8CB8M+tOes4yf827HoOEoqk=
github.com/juju/names/v4 v4.0.0-20220207005702-9c6532a52823 h1:Sv0+v4107/GHA0S25ay/rgGVmLyc+5Fjp0NnTksW/IQ=
github.com/juju/names/v4 v4.0.0-20220207005702-9c6532a52823/go.mod h1:xpkrQpHbz1DGY+0Geo32ZnyognGA/2vSB++rpu/Z+Lc=
github.com/juju/names/v5 v5.0.0 h1:3IkRTUaniNXsgjy4lNqbJx7dVdsONlzuH6YMYT7uXss=
github.com/juju/names/v5 v5.0.0/go.mod h1:PkvHbErUTniKvLu1ejJ5m/AbXOW55MFn1jsGVEbVXk8=
github.com/juju/naturalsort v1.0.0 h1:kGmUUy3h8mJ5/SJYaqKOBR3f3owEd5R52Lh+Tjg/dNM=
github.com/juju/naturalsort v1.0.0/go.mod h1:Zqa/vGkXr78k47zM6tFmU9phhxKz/PIdqBzpLhJ86zc=
github.com/juju/os/v2 v2.2.3 h1:5SnGWfzFTXcFwu/sd9qEEf/No3UZxivOjJuWmsHI4N4=
github.com/juju/os/v2 v2.2.3/go.mod h1:xGfP9I+Xb/A03NcGBsoJgwr084hPckkQHecaHuV3wBQ=
github.com/juju/packaging/v3 v3.0.0 h1:ZzuHhR8Ql9z2oeQ0m73x6k58PW65Cgk5wR9Yc1exoOI=
github.com/juju/packaging/v3 v3.0.0/go.mod h1:WXh/SXqh1du8SFzwb1KC+yZuV4Qc4alWP3MEPqFX9Lw=
github.com/juju/packaging/v2 v2.0.1 h1:KeTfqx3Z0c6RcM053GJH7mplroXoRSuh/dK5vqDQLn8=
github.com/juju/packaging/v2 v2.0.1/go.mod h1:JC+FIRTJXGLt9wA+iP3ltkzv+aWVMMojB/R47uIAK0Y=
github.com/juju/persistent-cookiejar v1.0.0 h1:Ag7+QLzqC2m+OYXy2QQnRjb3gTkEBSZagZ6QozwT3EQ=
github.com/juju/persistent-cookiejar v1.0.0/go.mod h1:zrbmo4nBKaiP/Ez3F67ewkMbzGYfXyMvRtbOfuAwG0w=
github.com/juju/proxy v1.0.0 h1:5XMp0opQJx8K/js3RFG/2EAk+cvKba/zwFJwd5f0AW0=
Expand Down
2 changes: 1 addition & 1 deletion internal/juju/applications.go
Original file line number Diff line number Diff line change
Expand Up @@ -418,7 +418,7 @@ func (c applicationsClient) legacyDeploy(ctx context.Context, conn api.Connectio
urlForOrigin = urlForOrigin.WithSeries(userSuppliedSeries)
}

origin, err := utils.MakeOrigin(charm.Schema(charmURL.Schema), charmURL.Revision, channel, platform)
origin, err := utils.MakeOrigin(charm.Schema(urlForOrigin.Schema), transformedInput.charmRevision, channel, platform)
if err != nil {
return err
}
Expand Down
3 changes: 2 additions & 1 deletion internal/juju/secrets.go
Original file line number Diff line number Diff line change
Expand Up @@ -310,7 +310,8 @@ func (c *secretsClient) UpdateSecretAccess(input *GrantRevokeSecretAccessInput,
func getApplicationsFromAccessInfo(accessInfo []coresecrets.AccessInfo) []string {
var applications []string

Check failure on line 311 in internal/juju/secrets.go

View workflow job for this annotation

GitHub Actions / golangci-lint

Consider pre-allocating `applications` (prealloc)
for _, info := range accessInfo {
applications = append(applications, info.Target)
// Trim the prefix "application-" from the application name (info.Target)
applications = append(applications, strings.TrimPrefix(info.Target, "application-"))
}
return applications
}
1 change: 1 addition & 0 deletions internal/provider/provider.go
Original file line number Diff line number Diff line change
Expand Up @@ -293,6 +293,7 @@ func (p *jujuProvider) Resources(_ context.Context) []func() resource.Resource {
func() resource.Resource { return NewSSHKeyResource() },
func() resource.Resource { return NewUserResource() },
func() resource.Resource { return NewSecretResource() },
func() resource.Resource { return NewSecretAccessResource() },
}
}

Expand Down
3 changes: 3 additions & 0 deletions internal/provider/resource_secret.go
Original file line number Diff line number Diff line change
Expand Up @@ -79,6 +79,9 @@ func (s *secretResource) Schema(_ context.Context, req resource.SchemaRequest, r
"secret_id": schema.StringAttribute{
Description: "The ID of the secret.",
Computed: true,
PlanModifiers: []planmodifier.String{
stringplanmodifier.UseStateForUnknown(),
},
},
"info": schema.StringAttribute{
Description: "The description of the secret.",
Expand Down
83 changes: 41 additions & 42 deletions internal/provider/resource_secret_access.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,11 @@ import (
"context"
"fmt"
"github.com/hashicorp/terraform-plugin-framework/attr"
"github.com/hashicorp/terraform-plugin-framework/resource/schema/planmodifier"
"github.com/hashicorp/terraform-plugin-framework/resource/schema/stringplanmodifier"
"reflect"

"github.com/hashicorp/terraform-plugin-framework/path"
"github.com/hashicorp/terraform-plugin-framework/resource"
"github.com/hashicorp/terraform-plugin-framework/resource/schema"
"github.com/hashicorp/terraform-plugin-framework/resource/schema/planmodifier"
"github.com/hashicorp/terraform-plugin-framework/resource/schema/stringplanmodifier"
"github.com/hashicorp/terraform-plugin-framework/types"
"github.com/hashicorp/terraform-plugin-log/tflog"
"github.com/juju/terraform-provider-juju/internal/juju"
Expand Down Expand Up @@ -60,16 +58,18 @@ func (s *secretAccessResource) Schema(_ context.Context, req resource.SchemaRequ
Description: "The model in which the secret belongs.",
Required: true,
PlanModifiers: []planmodifier.String{
stringplanmodifier.RequiresReplace(),
stringplanmodifier.RequiresReplaceIfConfigured(),
stringplanmodifier.UseStateForUnknown(),
},
},
"secret_id": schema.StringAttribute{
Description: "The ID of the secret.",
Computed: true,
Required: true,
},
"applications": schema.ListAttribute{
Description: "The list of applications to which the secret is granted or revoked.",
Required: true,
ElementType: types.StringType,
},
},
}
Expand Down Expand Up @@ -113,8 +113,8 @@ func (s *secretAccessResource) Create(ctx context.Context, req resource.CreateRe
resp.Diagnostics.Append(plan.Applications.ElementsAs(ctx, &applications, false)...)

err := s.client.Secrets.UpdateSecretAccess(&juju.GrantRevokeSecretAccessInput{
ModelName: plan.Model.String(),
SecretId: plan.SecretId.String(),
ModelName: plan.Model.ValueString(),
SecretId: plan.SecretId.ValueString(),
Applications: applications,
}, juju.GrantAccess)
if err != nil {
Expand Down Expand Up @@ -190,12 +190,29 @@ func (s *secretAccessResource) Update(ctx context.Context, req resource.UpdateRe
updatedSecretAccessInput.ModelName = state.Model.ValueString()
updatedSecretAccessInput.SecretId = state.SecretId.ValueString()

var applicationsInPlanNotInState, applicationsInStateNotInPlan interface{}
var applicationsInPlanNotInState, applicationsInStateNotInPlan []string
if !plan.Applications.Equal(state.Applications) {
noChange = false

applicationsInPlanNotInState = difference(plan.Applications, state.Applications)
applicationsInStateNotInPlan = difference(state.Applications, plan.Applications)
planApplications := make([]string, len(plan.Applications.Elements()))
resp.Diagnostics.Append(plan.Applications.ElementsAs(ctx, &planApplications, false)...)

//print the applications in the plan
s.trace(fmt.Sprintf("secret_access_debug applications in plan: %v", planApplications))

stateApplications := make([]string, len(state.Applications.Elements()))
resp.Diagnostics.Append(state.Applications.ElementsAs(ctx, &stateApplications, false)...)

//print the applications in the state
s.trace(fmt.Sprintf("secret_access_debug applications in state: %v", stateApplications))

applicationsInPlanNotInState = difference(planApplications, stateApplications)
applicationsInStateNotInPlan = difference(stateApplications, planApplications)

//print the applications that are in the plan but not in the state
s.trace(fmt.Sprintf("secret_access_debug applications in plan but not in state: %v", applicationsInPlanNotInState))
//print the applications that are in the state but not in the plan
s.trace(fmt.Sprintf("secret_access_debug applications in state but not in plan: %v", applicationsInStateNotInPlan))

resp.Diagnostics.Append(plan.Applications.ElementsAs(ctx, &state.Applications, false)...)
if resp.Diagnostics.HasError() {
Expand All @@ -216,8 +233,8 @@ func (s *secretAccessResource) Update(ctx context.Context, req resource.UpdateRe
err = s.client.Secrets.UpdateSecretAccess(&juju.GrantRevokeSecretAccessInput{
ModelName: state.Model.ValueString(),
SecretId: state.SecretId.ValueString(),
Applications: applicationsInStateNotInPlan.([]string),
}, juju.RevokeAccess)
Applications: applicationsInStateNotInPlan,
}, juju.GrantAccess)
if err != nil {
resp.Diagnostics.AddError("Failed to revoke secret access", err.Error())
return
Expand All @@ -229,8 +246,8 @@ func (s *secretAccessResource) Update(ctx context.Context, req resource.UpdateRe
err = s.client.Secrets.UpdateSecretAccess(&juju.GrantRevokeSecretAccessInput{
ModelName: state.Model.ValueString(),
SecretId: state.SecretId.ValueString(),
Applications: applicationsInPlanNotInState.([]string),
}, juju.GrantAccess)
Applications: applicationsInPlanNotInState,
}, juju.RevokeAccess)
if err != nil {
resp.Diagnostics.AddError("Failed to grant secret access", err.Error())
return
Expand Down Expand Up @@ -289,39 +306,21 @@ func (s *secretAccessResource) Delete(ctx context.Context, req resource.DeleteRe
}

// difference returns the difference between two slices.
func difference(slice1, slice2 interface{}) interface{} {
slice1Value := reflect.ValueOf(slice1)
slice2Value := reflect.ValueOf(slice2)

slice1Type := slice1Value.Type()
slice2Type := slice2Value.Type()

if slice1Type.Kind() != reflect.Slice || slice2Type.Kind() != reflect.Slice {
panic("Invalid data type. Expected slices.")
}
func difference(slice1, slice2 []string) []string {
var diff []string
m := make(map[string]bool)

if slice1Type.Elem() != slice2Type.Elem() {
panic("Inconsistent slice types.")
for _, s1 := range slice1 {
m[s1] = true
}

set := make(map[interface{}]bool)
result := reflect.MakeSlice(slice1Type, 0, slice1Value.Len())

for i := 0; i < slice1Value.Len(); i++ {
set[slice1Value.Index(i).Interface()] = true
}

for i := 0; i < slice2Value.Len(); i++ {
if _, found := set[slice2Value.Index(i).Interface()]; found {
delete(set, slice2Value.Index(i).Interface())
for _, s2 := range slice2 {
if _, ok := m[s2]; !ok {
diff = append(diff, s2)
}
}

for key := range set {
result = reflect.Append(result, reflect.ValueOf(key))
}

return result.Interface()
return diff
}

func (s *secretAccessResource) trace(msg string, additionalFields ...map[string]interface{}) {
Expand Down

0 comments on commit ae0f045

Please sign in to comment.