diff --git a/config.go b/config.go index ff07f422..159cc11d 100644 --- a/config.go +++ b/config.go @@ -217,10 +217,7 @@ func generateNewClient(c *Config, client *alks.Client) (*alks.Client, error) { return nil, err } - newClient, err := alks.NewSTSClient(c.URL, newCreds.AccessKey, newCreds.SecretKey, newCreds.SessionToken) - if err != nil { - return nil, err - } + newClient, _ := alks.NewSTSClient(c.URL, newCreds.AccessKey, newCreds.SecretKey, newCreds.SessionToken) // 5. Return this new client for provider return newClient, nil diff --git a/go.mod b/go.mod index a0e36d66..e9309364 100644 --- a/go.mod +++ b/go.mod @@ -3,7 +3,7 @@ module github.com/Cox-Automotive/terraform-provider-alks go 1.18 require ( - github.com/Cox-Automotive/alks-go v0.0.0-20221019181202-84b27abafb6b + github.com/Cox-Automotive/alks-go v0.0.0-20221026220646-c20da5c3cb3a github.com/aws/aws-sdk-go v1.31.15 github.com/hashicorp/terraform-plugin-sdk/v2 v2.21.0 github.com/mitchellh/go-homedir v1.1.0 diff --git a/go.sum b/go.sum index d4f2c6c1..6a8985d3 100644 --- a/go.sum +++ b/go.sum @@ -11,6 +11,14 @@ github.com/Cox-Automotive/alks-go v0.0.0-20221010204605-136b6e9b6530 h1:8j3NYoLn github.com/Cox-Automotive/alks-go v0.0.0-20221010204605-136b6e9b6530/go.mod h1:jJNgXthl59Vt2tJHSC3WZ0vlopV9xqdclfQuLgwHjOw= github.com/Cox-Automotive/alks-go v0.0.0-20221019181202-84b27abafb6b h1:9Ey7kdUL+/f5EY2KOpTawWMw4P7fhZxNmo8gXIuBQzw= github.com/Cox-Automotive/alks-go v0.0.0-20221019181202-84b27abafb6b/go.mod h1:jJNgXthl59Vt2tJHSC3WZ0vlopV9xqdclfQuLgwHjOw= +github.com/Cox-Automotive/alks-go v0.0.0-20221025180450-2e58fb1fb8a5 h1:uUI/XCe1bc9nq3d6jK05TsxOmCf8sLLOX/L3guAYdtg= +github.com/Cox-Automotive/alks-go v0.0.0-20221025180450-2e58fb1fb8a5/go.mod h1:jJNgXthl59Vt2tJHSC3WZ0vlopV9xqdclfQuLgwHjOw= +github.com/Cox-Automotive/alks-go v0.0.0-20221025210209-c92be9283c74 h1:ceg7E2BWn1HNGUZx2K8XQ3uQjT3phYuoeSGUv8Rqcdc= +github.com/Cox-Automotive/alks-go v0.0.0-20221025210209-c92be9283c74/go.mod h1:jJNgXthl59Vt2tJHSC3WZ0vlopV9xqdclfQuLgwHjOw= +github.com/Cox-Automotive/alks-go v0.0.0-20221026190610-eec2e9aedb00 h1:0lV5ATCvq93nrKPm4tD9HpgaAMhfaz2I31Xb6VbIpj8= +github.com/Cox-Automotive/alks-go v0.0.0-20221026190610-eec2e9aedb00/go.mod h1:jJNgXthl59Vt2tJHSC3WZ0vlopV9xqdclfQuLgwHjOw= +github.com/Cox-Automotive/alks-go v0.0.0-20221026220646-c20da5c3cb3a h1:EJJqr3Dg89DRi7eqtD9OX0XOqabndVqK0r9cy8Y7aq0= +github.com/Cox-Automotive/alks-go v0.0.0-20221026220646-c20da5c3cb3a/go.mod h1:jJNgXthl59Vt2tJHSC3WZ0vlopV9xqdclfQuLgwHjOw= github.com/Microsoft/go-winio v0.4.14/go.mod h1:qXqCSQ3Xa7+6tgxaGTIe4Kpcdsi+P8jBhyzoq1bpyYA= github.com/Microsoft/go-winio v0.4.16 h1:FtSW/jqD+l4ba5iPBj9CODVtgfYAD8w2wS923g/cFDk= github.com/Microsoft/go-winio v0.4.16/go.mod h1:XB6nPKklQyQ7GC9LdcBEcBl8PF76WugXOPRXwdLnMv0= diff --git a/helpers.go b/helpers.go index a4e0ae57..388c5b87 100644 --- a/helpers.go +++ b/helpers.go @@ -1,12 +1,12 @@ package main import ( - "errors" + "fmt" "github.com/Cox-Automotive/alks-go" ) -func validateIAMEnabled(client *alks.Client) error { +func validateIAMEnabled(client *alks.Client) *alks.AlksError { // Validate STS for IAM active. resp, err := client.GetMyLoginRole() if err != nil { @@ -14,8 +14,12 @@ func validateIAMEnabled(client *alks.Client) error { } if !resp.LoginRole.IamKeyActive { - return errors.New("uh oh! You're using the " + resp.LoginRole.Role + " role which is not IAM active. " + - "Please instead use one of the following roles: Admin, IAMAdmin, LabAdmin, or a Machine Identity") + return &alks.AlksError{ + StatusCode: 0, + RequestId: "", + Err: fmt.Errorf("uh oh! You're using the " + resp.LoginRole.Role + " role which is not IAM active. " + + "Please instead use one of the following roles: Admin, IAMAdmin, LabAdmin, or a Machine Identity"), + } } return nil diff --git a/resource_alks_iamrole.go b/resource_alks_iamrole.go index 8feb7b07..ddfb85bf 100644 --- a/resource_alks_iamrole.go +++ b/resource_alks_iamrole.go @@ -153,7 +153,7 @@ func resourceAlksIamRoleCreate(ctx context.Context, d *schema.ResourceData, meta resp, err := client.CreateIamRole(options) if err != nil { - return diag.FromErr(err.Err) + return diag.FromErr(err) } d.SetId(resp.RoleName) @@ -174,7 +174,7 @@ func resourceAlksIamRoleDelete(ctx context.Context, d *schema.ResourceData, meta } if err := client.DeleteIamRole(d.Id()); err != nil { - return diag.FromErr(err.Err) + return diag.FromErr(err) } return nil @@ -199,7 +199,7 @@ func resourceAlksIamRoleRead(ctx context.Context, d *schema.ResourceData, meta i //If error is 404, RoleNotFound, we log it and let terraform decide how to handle it. //All other errors cause a failure if err.StatusCode == 404 { - log.Printf("[Error] %s", err.Err) + log.Printf("[Error] %s", err.Error()) d.SetId("") return nil } @@ -283,13 +283,13 @@ func updateAlksAccess(d *schema.ResourceData, meta interface{}) error { if alksAccess { _, err := client.AddRoleMachineIdentity(roleArn) if err != nil { - return err.Err + return err } } else { // delete the machine identity _, err := client.DeleteRoleMachineIdentity(roleArn) if err != nil { - return err.Err + return err } } return nil @@ -308,7 +308,7 @@ func updateIamRoleTags(d *schema.ResourceData, meta interface{}) error { foundRole, err := client.GetIamRole(d.Id()) if err != nil { - return err.Err + return err } existingTags := tagSliceToMap(foundRole.Tags) @@ -324,7 +324,7 @@ func updateIamRoleTags(d *schema.ResourceData, meta interface{}) error { } if _, err := client.UpdateIamRole(&options); err != nil { - return err.Err + return err } return nil } diff --git a/resource_alks_iamtrustrole.go b/resource_alks_iamtrustrole.go index 489e7145..0df01602 100644 --- a/resource_alks_iamtrustrole.go +++ b/resource_alks_iamtrustrole.go @@ -114,7 +114,7 @@ func resourceAlksIamTrustRoleCreate(ctx context.Context, d *schema.ResourceData, resp, err = client.CreateIamTrustRole(options) if err != nil { if strings.Contains(err.Error(), "Role already exists") || strings.Contains(err.Error(), "Instance profile exists") { - return resource.NonRetryableError(err.Err) + return resource.NonRetryableError(err) } // Amazon IAM utilizes an eventual consistency model: diff --git a/resource_alks_ltk.go b/resource_alks_ltk.go index 13095b7e..04c09fde 100644 --- a/resource_alks_ltk.go +++ b/resource_alks_ltk.go @@ -70,7 +70,7 @@ func resourceAlksLtkCreate(ctx context.Context, d *schema.ResourceData, meta int resp, err := client.CreateIamUser(options) if err != nil { - return diag.FromErr(err.Err) + return diag.FromErr(err) } d.SetId(iamUsername) @@ -103,11 +103,11 @@ func resourceAlksLtkRead(ctx context.Context, d *schema.ResourceData, meta inter //If error is 404, UserNotFound, we log it and let terraform decide how to handle it. //All other errors cause a failure if err.StatusCode == 404 { - log.Printf("[Error] %s", err.Err) + log.Printf("[Error] %s", err) d.SetId("") return nil } - return diag.FromErr(err.Err) + return diag.FromErr(err) } log.Printf("[INFO] alks_ltk.id: %v", d.Id()) @@ -159,7 +159,7 @@ func resourceAlksLtkDelete(ctx context.Context, d *schema.ResourceData, meta int } if _, err := client.DeleteIamUser(d.Id()); err != nil { - return diag.FromErr(err.Err) + return diag.FromErr(err) } return nil @@ -194,7 +194,7 @@ func updateUserTags(d *schema.ResourceData, meta interface{}) error { } if _, err := client.UpdateIamUser(&options); err != nil { - return err.Err + return err } return nil } diff --git a/vendor/github.com/Cox-Automotive/alks-go/alks_error.go b/vendor/github.com/Cox-Automotive/alks-go/alks_error.go index b207773d..e3193be3 100644 --- a/vendor/github.com/Cox-Automotive/alks-go/alks_error.go +++ b/vendor/github.com/Cox-Automotive/alks-go/alks_error.go @@ -20,6 +20,8 @@ type AlksResponseError struct { RequestId string `json:"requestId"` } +var AlksResponsErrorStrings = "ALKS Errors: %s \nContact the ALKS Team for assistance on Slack at #alks-client-support" +var GenericAlksError = "ALKS Errors: Contact the ALKS Team for assistance on Slack at #alks-client-support" var ErrorStringFull = "[%s] ALKS Error %d Msg: %s\n Contact the ALKS Team for assistance on Slack at #alks-client-support" var ErrorStringNoReqId = "ALKS Error %d Msg: %s\n Contact the ALKS Team for assistance on Slack at #alks-client-support" var ErrorStringOnlyCodeAndReqId = "[%s] ALKS Error %d\n Contact the ALKS Team for assistance on Slack at #alks-client-support" diff --git a/vendor/github.com/Cox-Automotive/alks-go/iam_role.go b/vendor/github.com/Cox-Automotive/alks-go/iam_role.go index 1585193c..000c0f33 100644 --- a/vendor/github.com/Cox-Automotive/alks-go/iam_role.go +++ b/vendor/github.com/Cox-Automotive/alks-go/iam_role.go @@ -239,14 +239,14 @@ func (c *Client) CreateIamRole(options *CreateIamRoleOptions) (*IamRoleResponse, return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, strings.Join(alksResponseErr.Errors, ", ")), + Err: fmt.Errorf(AlksResponsErrorStrings, strings.Join(alksResponseErr.Errors, ", ")), } } return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode), + Err: fmt.Errorf(GenericAlksError), } } @@ -326,14 +326,14 @@ func (c *Client) CreateIamTrustRole(options *CreateIamRoleOptions) (*IamRoleResp return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, strings.Join(trustErr.Errors, ", ")), + Err: fmt.Errorf(AlksResponsErrorStrings, strings.Join(trustErr.Errors, ", ")), } } return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode), + Err: fmt.Errorf(GenericAlksError), } } @@ -425,7 +425,7 @@ func (c *Client) UpdateIamRole(options *UpdateIamRoleRequest) (*UpdateIamRoleRes return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ParseErrorReqId, reqID, err), + Err: fmt.Errorf(ParseError, err), } } @@ -433,14 +433,14 @@ func (c *Client) UpdateIamRole(options *UpdateIamRoleRequest) (*UpdateIamRoleRes return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, strings.Join(updateErr.Errors, ", ")), + Err: fmt.Errorf(AlksResponsErrorStrings, strings.Join(updateErr.Errors, ", ")), } } return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode), + Err: fmt.Errorf(GenericAlksError), } } @@ -449,14 +449,14 @@ func (c *Client) UpdateIamRole(options *UpdateIamRoleRequest) (*UpdateIamRoleRes return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf("Error parsing updateRole response: [%s] %s", reqID, err), + Err: fmt.Errorf("Error parsing updateRole response"), } } if respObj.RequestFailed() { return nil, &AlksError{ StatusCode: resp.StatusCode, - RequestId: reqID, - Err: fmt.Errorf("Error from update IAM role request: [%s] %s", respObj.RequestID, strings.Join(respObj.GetErrors(), ", ")), + RequestId: respObj.RequestID, + Err: fmt.Errorf("Error from update IAM role request: %s", strings.Join(respObj.GetErrors(), ", ")), } } return respObj, nil @@ -520,7 +520,7 @@ func (c *Client) DeleteIamRole(id string) *AlksError { return &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ParseErrorReqId, reqID, err), + Err: fmt.Errorf(ParseError, err), } } @@ -528,14 +528,14 @@ func (c *Client) DeleteIamRole(id string) *AlksError { return &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, strings.Join(delErr.Errors, ", ")), + Err: fmt.Errorf(AlksResponsErrorStrings, strings.Join(delErr.Errors, ", ")), } } return &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode), + Err: fmt.Errorf(GenericAlksError), } } @@ -546,7 +546,7 @@ func (c *Client) DeleteIamRole(id string) *AlksError { return &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf("Error parsing deleteRole response: [%s] %s", reqID, err), + Err: fmt.Errorf("Error parsing deleteRole response: %s", err), } } @@ -554,8 +554,8 @@ func (c *Client) DeleteIamRole(id string) *AlksError { if del.RequestFailed() { return &AlksError{ StatusCode: resp.StatusCode, - RequestId: reqID, - Err: fmt.Errorf("Error deleting role: [%s] %s", del.BaseResponse.RequestID, strings.Join(del.GetErrors(), ", ")), + RequestId: del.BaseResponse.RequestID, + Err: fmt.Errorf("Error deleting role: %s", strings.Join(del.GetErrors(), ", ")), } } @@ -611,7 +611,7 @@ func (c *Client) GetIamRole(roleName string) (*GetIamRoleResponse, *AlksError) { return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ParseErrorReqId, reqID, err), + Err: fmt.Errorf(ParseError, err), } } @@ -619,14 +619,14 @@ func (c *Client) GetIamRole(roleName string) (*GetIamRoleResponse, *AlksError) { return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, strings.Join(getErr.Errors, ", ")), + Err: fmt.Errorf(AlksResponsErrorStrings, strings.Join(getErr.Errors, ", ")), } } return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode), + Err: fmt.Errorf(GenericAlksError), } } @@ -637,15 +637,15 @@ func (c *Client) GetIamRole(roleName string) (*GetIamRoleResponse, *AlksError) { return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf("Error parsing getRole response: [%s] %s", reqID, err), + Err: fmt.Errorf("Error parsing getRole response: %s", err), } } if cr.RequestFailed() { return nil, &AlksError{ StatusCode: resp.StatusCode, - RequestId: reqID, - Err: fmt.Errorf("Error getting role: [%s] %s", cr.BaseResponse.RequestID, strings.Join(cr.GetErrors(), ", ")), + RequestId: cr.BaseResponse.RequestID, + Err: fmt.Errorf("Error getting role: %s", strings.Join(cr.GetErrors(), ", ")), } } @@ -711,7 +711,7 @@ func (c *Client) AddRoleMachineIdentity(roleARN string) (*MachineIdentityRespons return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ParseErrorReqId, reqID, err), + Err: fmt.Errorf(ParseError, err), } } @@ -719,14 +719,14 @@ func (c *Client) AddRoleMachineIdentity(roleARN string) (*MachineIdentityRespons return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, strings.Join(addErr.Errors, ", ")), + Err: fmt.Errorf(AlksResponsErrorStrings, strings.Join(addErr.Errors, ", ")), } } return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode), + Err: fmt.Errorf(GenericAlksError), } } @@ -737,7 +737,7 @@ func (c *Client) AddRoleMachineIdentity(roleARN string) (*MachineIdentityRespons return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf("Error parsing MachineIdentitiyResponse response: [%s] %s", reqID, err), + Err: fmt.Errorf("Error parsing MachineIdentitiyResponse response: %s", err), } } @@ -745,7 +745,7 @@ func (c *Client) AddRoleMachineIdentity(roleARN string) (*MachineIdentityRespons return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf("Error creating machine identity: [%s] %s", cr.BaseResponse.RequestID, strings.Join(cr.GetErrors(), ", ")), + Err: fmt.Errorf("Error creating machine identity: %s", strings.Join(cr.GetErrors(), ", ")), } } @@ -798,7 +798,7 @@ func (c *Client) DeleteRoleMachineIdentity(roleARN string) (*MachineIdentityResp return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ParseErrorReqId, reqID, err), + Err: fmt.Errorf(ParseError, err), } } @@ -806,14 +806,14 @@ func (c *Client) DeleteRoleMachineIdentity(roleARN string) (*MachineIdentityResp return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, strings.Join(delErr.Errors, ", ")), + Err: fmt.Errorf(AlksResponsErrorStrings, strings.Join(delErr.Errors, ", ")), } } return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode), + Err: fmt.Errorf(GenericAlksError), } } @@ -824,7 +824,7 @@ func (c *Client) DeleteRoleMachineIdentity(roleARN string) (*MachineIdentityResp return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf("Error parsing machineIdentity response: [%s] %s", reqID, err), + Err: fmt.Errorf("Error parsing machineIdentity response: %s", err), } } @@ -832,7 +832,7 @@ func (c *Client) DeleteRoleMachineIdentity(roleARN string) (*MachineIdentityResp return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf("Error deleting machine identity: [%s] %s", dr.BaseResponse.RequestID, strings.Join(dr.GetErrors(), ", ")), + Err: fmt.Errorf("Error deleting machine identity: %s", strings.Join(dr.GetErrors(), ", ")), } } @@ -885,7 +885,7 @@ func (c *Client) SearchRoleMachineIdentity(roleARN string) (*MachineIdentityResp return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ParseErrorReqId, reqID, err), + Err: fmt.Errorf(ParseError, err), } } @@ -893,14 +893,14 @@ func (c *Client) SearchRoleMachineIdentity(roleARN string) (*MachineIdentityResp return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, strings.Join(searchErr.Errors, ", ")), + Err: fmt.Errorf(AlksResponsErrorStrings, strings.Join(searchErr.Errors, ", ")), } } return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode), + Err: fmt.Errorf(GenericAlksError), } } @@ -911,15 +911,15 @@ func (c *Client) SearchRoleMachineIdentity(roleARN string) (*MachineIdentityResp return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf("Error parsing MachineIdentity response: [%s] %s", reqID, err), + Err: fmt.Errorf("Error parsing MachineIdentity response: %s", err), } } if sr.RequestFailed() { return nil, &AlksError{ StatusCode: resp.StatusCode, - RequestId: reqID, - Err: fmt.Errorf("Error searching machine identity [%s] %s", sr.BaseResponse.RequestID, strings.Join(sr.GetErrors(), ", ")), + RequestId: sr.BaseResponse.RequestID, + Err: fmt.Errorf("Error searching machine identity %s", strings.Join(sr.GetErrors(), ", ")), } } diff --git a/vendor/github.com/Cox-Automotive/alks-go/iam_session.go b/vendor/github.com/Cox-Automotive/alks-go/iam_session.go index 4c4f4047..6b379518 100644 --- a/vendor/github.com/Cox-Automotive/alks-go/iam_session.go +++ b/vendor/github.com/Cox-Automotive/alks-go/iam_session.go @@ -7,7 +7,7 @@ import ( // CreateIamSession creates a new IAM STS session. If no error is returned // then you will received a IamSessionResponse object containing your session // keys. -func (c *Client) CreateIamSession() (*SessionResponse, error) { +func (c *Client) CreateIamSession() (*SessionResponse, *AlksError) { log.Println("[INFO] Creating IAM session") return c.CreateSession(1, true) diff --git a/vendor/github.com/Cox-Automotive/alks-go/iam_user.go b/vendor/github.com/Cox-Automotive/alks-go/iam_user.go index 79e00c2d..d61ad2cd 100644 --- a/vendor/github.com/Cox-Automotive/alks-go/iam_user.go +++ b/vendor/github.com/Cox-Automotive/alks-go/iam_user.go @@ -146,7 +146,7 @@ func (c *Client) GetIamUsers() (*GetIamUsersResponse, *AlksError) { return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ParseErrorReqId, reqID, err), + Err: fmt.Errorf(ParseError, err), } } @@ -154,14 +154,14 @@ func (c *Client) GetIamUsers() (*GetIamUsersResponse, *AlksError) { return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, strings.Join(keyErr.Errors, ", ")), + Err: fmt.Errorf(AlksResponsErrorStrings, strings.Join(keyErr.Errors, ", ")), } } return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode), + Err: fmt.Errorf(GenericAlksError), } } @@ -172,7 +172,7 @@ func (c *Client) GetIamUsers() (*GetIamUsersResponse, *AlksError) { return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf("Error parsing GetLongTermKeysResponse: [%s] %s", reqID, err), + Err: fmt.Errorf("Error parsing GetLongTermKeysResponse: %s", err), } } @@ -221,7 +221,7 @@ func (c *Client) GetIamUser(iamUsername string) (*GetIamUserResponse, *AlksError return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ParseErrorReqId, reqID, err), + Err: fmt.Errorf(ParseError, err), } } @@ -230,7 +230,7 @@ func (c *Client) GetIamUser(iamUsername string) (*GetIamUserResponse, *AlksError return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, keyErr.Errors), + Err: fmt.Errorf(AlksResponsErrorStrings, strings.Join(keyErr.Errors, ", ")), } } } @@ -238,7 +238,7 @@ func (c *Client) GetIamUser(iamUsername string) (*GetIamUserResponse, *AlksError return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode), + Err: fmt.Errorf(GenericAlksError), } } @@ -249,7 +249,7 @@ func (c *Client) GetIamUser(iamUsername string) (*GetIamUserResponse, *AlksError return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf("error parsing GetLongTermKeyResponse: [%s] %s", reqID, err), + Err: fmt.Errorf("error parsing GetLongTermKeyResponse: %s", err), } } @@ -334,7 +334,7 @@ func (c *Client) CreateIamUser(options *IamUserOptions) (*CreateIamUserResponse, return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ParseErrorReqId, reqID, err), + Err: fmt.Errorf(ParseError, err), } } @@ -342,14 +342,14 @@ func (c *Client) CreateIamUser(options *IamUserOptions) (*CreateIamUserResponse, return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, keyErr.Errors), + Err: fmt.Errorf(AlksResponsErrorStrings, strings.Join(keyErr.Errors, ", ")), } } return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode), + Err: fmt.Errorf(GenericAlksError), } } @@ -360,7 +360,7 @@ func (c *Client) CreateIamUser(options *IamUserOptions) (*CreateIamUserResponse, return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf("error parsing CreateLongTermKeyResponse: [%s] %s", reqID, err), + Err: fmt.Errorf("error parsing CreateLongTermKeyResponse: %s", err), } } return cr, nil @@ -413,7 +413,7 @@ func (c *Client) DeleteIamUser(iamUsername string) (*DeleteIamUserResponse, *Alk return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ParseErrorReqId, reqID, err), + Err: fmt.Errorf(ParseError, err), } } @@ -421,13 +421,13 @@ func (c *Client) DeleteIamUser(iamUsername string) (*DeleteIamUserResponse, *Alk return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringNoReqId, resp.StatusCode, keyErr.Errors), + Err: fmt.Errorf(AlksResponsErrorStrings, strings.Join(keyErr.Errors, ", ")), } } return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode), + Err: fmt.Errorf(GenericAlksError), } } @@ -438,7 +438,7 @@ func (c *Client) DeleteIamUser(iamUsername string) (*DeleteIamUserResponse, *Alk return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf("error parsing DeleteLongTermKeyResponse: [%s] %s", reqID, err), + Err: fmt.Errorf("error parsing DeleteLongTermKeyResponse: %s", err), } } return cr, nil @@ -525,7 +525,7 @@ func (c *Client) UpdateIamUser(options *IamUserOptions) (*UpdateIamUserResponse, return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ParseErrorReqId, reqID, err), + Err: fmt.Errorf(ParseError, err), } } @@ -533,14 +533,14 @@ func (c *Client) UpdateIamUser(options *IamUserOptions) (*UpdateIamUserResponse, return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringNoReqId, resp.StatusCode, updateErr.Errors), + Err: fmt.Errorf(AlksResponsErrorStrings, strings.Join(updateErr.Errors, ", ")), } } return nil, &AlksError{ StatusCode: resp.StatusCode, RequestId: reqID, - Err: fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode), + Err: fmt.Errorf(GenericAlksError), } } diff --git a/vendor/github.com/Cox-Automotive/alks-go/is_iam_enabled.go b/vendor/github.com/Cox-Automotive/alks-go/is_iam_enabled.go index 11c0c250..89d4d77a 100644 --- a/vendor/github.com/Cox-Automotive/alks-go/is_iam_enabled.go +++ b/vendor/github.com/Cox-Automotive/alks-go/is_iam_enabled.go @@ -21,7 +21,7 @@ type IsIamEnabledResponse struct { } // IsIamEnabled will check if a MI, AccountDetails, or STS assumed role is IAM active or not. -func (c *Client) IsIamEnabled(roleArn string) (*IsIamEnabledResponse, error) { +func (c *Client) IsIamEnabled(roleArn string) (*IsIamEnabledResponse, *AlksError) { if len(roleArn) > 1 { log.Printf("[INFO] Is IAM enabled for MI: %s", roleArn) @@ -37,57 +37,77 @@ func (c *Client) IsIamEnabled(roleArn string) (*IsIamEnabledResponse, error) { body, err := json.Marshal(iam) if err != nil { - return nil, fmt.Errorf("error encoding IAM create role JSON: %s", err) + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: fmt.Errorf("error encoding IAM create role JSON: %s", err), + } + } req, err := c.NewRequest(body, "POST", "/isIamEnabled") if err != nil { - return nil, err + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: err, + } } resp, err := c.http.Do(req) if err != nil { - return nil, err + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: "", + Err: err, + } + } + reqID := GetRequestID(resp) if resp.StatusCode < 200 || resp.StatusCode >= 300 { iamErr := new(AlksResponseError) err = decodeBody(resp, &iamErr) if err != nil { - if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf(ParseErrorReqId, reqID, err) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: reqID, + Err: fmt.Errorf(ParseError, err), } - - return nil, fmt.Errorf(ParseError, err) } if iamErr.Errors != nil { - if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, iamErr.Errors) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: reqID, + Err: fmt.Errorf(AlksResponsErrorStrings, iamErr.Errors), } - - return nil, fmt.Errorf(ErrorStringNoReqId, resp.StatusCode, iamErr.Errors) } - if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: reqID, + Err: fmt.Errorf(GenericAlksError), } - return nil, fmt.Errorf(ErrorStringOnlyCode, resp.StatusCode) } validate := new(IsIamEnabledResponse) err = decodeBody(resp, validate) if err != nil { - if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf("error parsing isIamEnabled response: [%s] %s", reqID, err) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: reqID, + Err: fmt.Errorf("error parsing isIamEnabled response: %s", err), } - - return nil, fmt.Errorf("error parsing isIamEnabled response: %s", err) } if validate.RequestFailed() { - return nil, fmt.Errorf("error validating if IAM enabled: [%s] %s", validate.BaseResponse.RequestID, strings.Join(validate.GetErrors(), ", ")) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: validate.BaseResponse.RequestID, + Err: fmt.Errorf("error validating if IAM enabled: %s", strings.Join(validate.GetErrors(), ", ")), + } } return validate, nil diff --git a/vendor/github.com/Cox-Automotive/alks-go/login_role.go b/vendor/github.com/Cox-Automotive/alks-go/login_role.go index db81ea5e..6474a9fd 100644 --- a/vendor/github.com/Cox-Automotive/alks-go/login_role.go +++ b/vendor/github.com/Cox-Automotive/alks-go/login_role.go @@ -7,68 +7,95 @@ import ( ) // GetMyLoginRole returns the LoginRole corresponding to the clients current STS credentials -func (c *Client) GetMyLoginRole() (*LoginRoleResponse, error) { +func (c *Client) GetMyLoginRole() (*LoginRoleResponse, *AlksError) { log.Printf("[INFO] Requesting Login Role information from ALKS") if !c.IsUsingSTSCredentials() { - return nil, fmt.Errorf("GetMyLoginRole only supports clients using STS credentials, try using GetLoginRole instead") + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: fmt.Errorf("GetMyLoginRole only supports clients using STS credentials, try using GetLoginRole instead"), + } } req, err := c.NewRequest(nil, "GET", "/loginRoles/id/me") if err != nil { - return nil, err + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: err, + } } resp, err := c.http.Do(req) if err != nil { - return nil, err + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: err, + } } + reqID := GetRequestID(resp) + if resp.StatusCode < 200 || resp.StatusCode >= 300 { loginErr := new(AlksResponseError) err = decodeBody(resp, &loginErr) if err != nil { - if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf(ParseErrorReqId, reqID, err) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: reqID, + Err: fmt.Errorf(ParseError, err), } - - return nil, fmt.Errorf(ParseError, err) } if loginErr.Errors != nil { - if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, loginErr.Errors) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: reqID, + Err: fmt.Errorf(AlksResponsErrorStrings, loginErr.Errors), } - - return nil, fmt.Errorf(ErrorStringNoReqId, resp.StatusCode, loginErr.Errors) } - if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: reqID, + Err: fmt.Errorf(GenericAlksError), } - return nil, fmt.Errorf(ErrorStringOnlyCode, resp.StatusCode) } lrr := new(LoginRoleResponse) err = decodeBody(resp, &lrr) if err != nil { if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf("Error parsing LoginRole response: [%s] %s", reqID, err) + return nil, &AlksError{ + StatusCode: 0, + RequestId: reqID, + Err: fmt.Errorf("Error parsing LoginRole response: %s", err), + } } - return nil, fmt.Errorf("Error parsing LoginRole response: %s", err) + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: fmt.Errorf("Error parsing LoginRole response: %s", err), + } } if lrr.RequestFailed() { - return nil, fmt.Errorf("Error fetching role information: [%s] %s", lrr.BaseResponse.RequestID, strings.Join(lrr.GetErrors(), ", ")) + return nil, &AlksError{ + StatusCode: 0, + RequestId: lrr.BaseResponse.RequestID, + Err: fmt.Errorf("Error fetching role information: %s", strings.Join(lrr.GetErrors(), ", ")), + } } return lrr, nil } // GetLoginRole returns the login role corresponding to the current account and role stored in AccountDetails -func (c *Client) GetLoginRole() (*LoginRoleResponse, error) { +func (c *Client) GetLoginRole() (*LoginRoleResponse, *AlksError) { // If the client is configured with STS call the correct method if c.IsUsingSTSCredentials() { log.Println("[INFO] Client configured with STS credentials, dispatching to GetMyLoginRole instead") @@ -77,64 +104,86 @@ func (c *Client) GetLoginRole() (*LoginRoleResponse, error) { account, err := c.AccountDetails.GetAccountNumber() if err != nil { - return nil, err + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: err, + } } roleName, err := c.AccountDetails.GetRoleName(false) if err != nil { - return nil, err + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: err, + } } log.Printf("[INFO] Requesting Login Role information for %v/%v from ALKS", account, roleName) req, err := c.NewRequest(nil, "GET", fmt.Sprintf("/loginRoles/id/%v/%v", account, roleName)) if err != nil { - return nil, err + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: err, + } } resp, err := c.http.Do(req) if err != nil { - return nil, err + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: "", + Err: err, + } } + reqID := GetRequestID(resp) + if resp.StatusCode < 200 || resp.StatusCode >= 300 { loginErr := new(AlksResponseError) err = decodeBody(resp, &loginErr) if err != nil { - if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf(ParseErrorReqId, reqID, err) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: reqID, + Err: fmt.Errorf(ParseError, err), } - - return nil, fmt.Errorf(ParseError, err) } if loginErr.Errors != nil { - if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf(ErrorStringFull, reqID, resp.StatusCode, loginErr.Errors) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: reqID, + Err: fmt.Errorf(AlksResponsErrorStrings, loginErr.Errors), } - - return nil, fmt.Errorf(ErrorStringNoReqId, resp.StatusCode, loginErr.Errors) } - if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf(ErrorStringOnlyCodeAndReqId, reqID, resp.StatusCode) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: reqID, + Err: fmt.Errorf(GenericAlksError), } - - return nil, fmt.Errorf(ErrorStringOnlyCode, resp.StatusCode) } lrr := new(LoginRoleResponse) err = decodeBody(resp, &lrr) if err != nil { - if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf("Error parsing LoginRole response: [%s] %s", reqID, err) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: reqID, + Err: fmt.Errorf("Error parsing LoginRole response: %s", err), } - - return nil, fmt.Errorf("Error parsing LoginRole response: %s", err) } if lrr.RequestFailed() { - return nil, fmt.Errorf("Error fetching role information: [%s] %s", lrr.BaseResponse.RequestID, strings.Join(lrr.GetErrors(), ", ")) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: lrr.BaseResponse.RequestID, + Err: fmt.Errorf("Error fetching role information: %s", strings.Join(lrr.GetErrors(), ", ")), + } } return lrr, nil diff --git a/vendor/github.com/Cox-Automotive/alks-go/session.go b/vendor/github.com/Cox-Automotive/alks-go/session.go index c3e41d1d..070aa0c7 100644 --- a/vendor/github.com/Cox-Automotive/alks-go/session.go +++ b/vendor/github.com/Cox-Automotive/alks-go/session.go @@ -50,38 +50,55 @@ type AccountsResponse struct { } // GetAccounts return a list of AccountRoles for an AWS account -func (c *Client) GetAccounts() (*AccountsResponse, error) { +func (c *Client) GetAccounts() (*AccountsResponse, *AlksError) { log.Printf("[INFO] Requesting available accounts from ALKS") b, err := json.Marshal(c.Credentials) if err != nil { - return nil, fmt.Errorf("Error encoding account request JSON: %s", err) + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: fmt.Errorf("Error encoding account request JSON: %s", err), + } } req, err := c.NewRequest(b, "POST", "/getAccounts/") if err != nil { - return nil, err + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: err, + } } resp, err := c.http.Do(req) if err != nil { - return nil, err + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: err, + } } _accts := new(AccountsResponseInt) err = decodeBody(resp, &_accts) - + reqID := GetRequestID(resp) if err != nil { - if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf("Error parsing get accounts response: [%s] %s", reqID, err) - } - return nil, fmt.Errorf("Error parsing get accounts response: %s", err) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: reqID, + Err: fmt.Errorf("Error parsing get accounts response: %s", err), + } } if _accts.RequestFailed() { - return nil, fmt.Errorf("Error getting accounts : [%s] %s", _accts.BaseResponse.RequestID, strings.Join(_accts.GetErrors(), ", ")) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: _accts.BaseResponse.RequestID, + Err: fmt.Errorf("Error getting accounts : %s", strings.Join(_accts.GetErrors(), ", ")), + } } accts := new(AccountsResponse) @@ -96,13 +113,17 @@ func (c *Client) GetAccounts() (*AccountsResponse, error) { // CreateSession will create a new STS session on AWS. If no error is // returned then you will receive a SessionResponse object representing // your STS session. -func (c *Client) CreateSession(sessionDuration int, useIAM bool) (*SessionResponse, error) { +func (c *Client) CreateSession(sessionDuration int, useIAM bool) (*SessionResponse, *AlksError) { log.Printf("[INFO] Creating %v hr session", sessionDuration) var found = false durations, err := c.Durations() if err != nil { - return nil, fmt.Errorf("Error fetching allowable durations from ALKS: %s", err) + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: fmt.Errorf("Error fetching allowable durations from ALKS: %s", err), + } } for _, v := range durations { @@ -112,7 +133,11 @@ func (c *Client) CreateSession(sessionDuration int, useIAM bool) (*SessionRespon } if !found { - return nil, fmt.Errorf("Unsupported session duration") + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: fmt.Errorf("Unsupported session duration"), + } } session := SessionRequest{sessionDuration} @@ -123,7 +148,11 @@ func (c *Client) CreateSession(sessionDuration int, useIAM bool) (*SessionRespon }{session, c.AccountDetails}) if err != nil { - return nil, fmt.Errorf("Error encoding session create JSON: %s", err) + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: fmt.Errorf("Error encoding session create JSON: %s", err), + } } var endpoint = "/getKeys/" @@ -132,12 +161,20 @@ func (c *Client) CreateSession(sessionDuration int, useIAM bool) (*SessionRespon } req, err := c.NewRequest(b, "POST", endpoint) if err != nil { - return nil, err + return nil, &AlksError{ + StatusCode: 0, + RequestId: "", + Err: err, + } } resp, httpErr := c.http.Do(req) if httpErr != nil { - return nil, err + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: "", + Err: err, + } } sr := new(SessionResponse) @@ -145,14 +182,26 @@ func (c *Client) CreateSession(sessionDuration int, useIAM bool) (*SessionRespon if err != nil { if reqID := GetRequestID(resp); reqID != "" { - return nil, fmt.Errorf("Error parsing session create response: [%s] %s", reqID, err) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: reqID, + Err: fmt.Errorf("Error parsing session create response: %s", err), + } } - return nil, fmt.Errorf("Error parsing session create response: %s", err) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: "", + Err: fmt.Errorf("Error parsing session create response: %s", err), + } } if sr.RequestFailed() { - return nil, fmt.Errorf("Error creating session: [%s] %s", sr.BaseResponse.RequestID, strings.Join(sr.GetErrors(), ", ")) + return nil, &AlksError{ + StatusCode: resp.StatusCode, + RequestId: sr.BaseResponse.RequestID, + Err: fmt.Errorf("Error creating session: %s", strings.Join(sr.GetErrors(), ", ")), + } } sr.Expires = time.Now().Local().Add(time.Hour * time.Duration(sessionDuration)) diff --git a/vendor/modules.txt b/vendor/modules.txt index 568b3d13..4f4354e1 100644 --- a/vendor/modules.txt +++ b/vendor/modules.txt @@ -1,4 +1,4 @@ -# github.com/Cox-Automotive/alks-go v0.0.0-20221019181202-84b27abafb6b +# github.com/Cox-Automotive/alks-go v0.0.0-20221026220646-c20da5c3cb3a ## explicit; go 1.16 github.com/Cox-Automotive/alks-go # github.com/agext/levenshtein v1.2.2