diff --git a/api/v1beta2/awscluster_webhook_test.go b/api/v1beta2/awscluster_webhook_test.go index 3a11b4b319..ad1b22d5fb 100644 --- a/api/v1beta2/awscluster_webhook_test.go +++ b/api/v1beta2/awscluster_webhook_test.go @@ -23,7 +23,7 @@ import ( "testing" "time" - "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go-v2/aws" . "github.com/onsi/gomega" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" diff --git a/api/v1beta2/awsmachine_webhook_test.go b/api/v1beta2/awsmachine_webhook_test.go index a3680f5dea..c20dd9f30d 100644 --- a/api/v1beta2/awsmachine_webhook_test.go +++ b/api/v1beta2/awsmachine_webhook_test.go @@ -21,7 +21,7 @@ import ( "strings" "testing" - "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go-v2/aws" . "github.com/onsi/gomega" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" utilfeature "k8s.io/component-base/featuregate/testing" diff --git a/api/v1beta2/awsmachinetemplate_webhook_test.go b/api/v1beta2/awsmachinetemplate_webhook_test.go index 014929c83e..ce355d1e4b 100644 --- a/api/v1beta2/awsmachinetemplate_webhook_test.go +++ b/api/v1beta2/awsmachinetemplate_webhook_test.go @@ -20,7 +20,7 @@ import ( "context" "testing" - "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go-v2/aws" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/utils/ptr" ) diff --git a/api/v1beta2/network_types.go b/api/v1beta2/network_types.go index 0a27a1c4db..26e38bc934 100644 --- a/api/v1beta2/network_types.go +++ b/api/v1beta2/network_types.go @@ -21,8 +21,8 @@ import ( "sort" "time" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "k8s.io/utils/ptr" ) @@ -670,7 +670,7 @@ func (s *SubnetSpec) IsEdgeWavelength() bool { func (s *SubnetSpec) SetZoneInfo(zones []types.AvailabilityZone) error { zoneInfo := func(zoneName string) *types.AvailabilityZone { for _, zone := range zones { - if aws.StringValue(zone.ZoneName) == zoneName { + if aws.ToString(zone.ZoneName) == zoneName { return &zone } } diff --git a/api/v1beta2/sshkeyname_test.go b/api/v1beta2/sshkeyname_test.go index b1d840d527..5b51505ff7 100644 --- a/api/v1beta2/sshkeyname_test.go +++ b/api/v1beta2/sshkeyname_test.go @@ -20,7 +20,7 @@ import ( "context" "testing" - "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go-v2/aws" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "sigs.k8s.io/controller-runtime/pkg/client" ) diff --git a/cmd/clusterawsadm/ami/helper.go b/cmd/clusterawsadm/ami/helper.go index e804029ee3..31edbedad9 100644 --- a/cmd/clusterawsadm/ami/helper.go +++ b/cmd/clusterawsadm/ami/helper.go @@ -24,9 +24,9 @@ import ( "strconv" "strings" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/blang/semver" "github.com/pkg/errors" @@ -218,7 +218,7 @@ func getAllImages(ec2Client common.EC2API, ownerID string) (map[string][]types.I imagesMap := make(map[string][]types.Image) for _, image := range out.Images { - arr := strings.Split(aws.StringValue(image.Name), "-") + arr := strings.Split(aws.ToString(image.Name), "-") if arr[len(arr)-2] == "00" { arr = arr[:len(arr)-2] } else { diff --git a/cmd/clusterawsadm/ami/list.go b/cmd/clusterawsadm/ami/list.go index 2ba3c03657..d545079eb0 100644 --- a/cmd/clusterawsadm/ami/list.go +++ b/cmd/clusterawsadm/ami/list.go @@ -22,10 +22,10 @@ import ( "fmt" "time" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/config" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" amiv1 "sigs.k8s.io/cluster-api-provider-aws/v2/cmd/clusterawsadm/api/ami/v1beta1" @@ -103,7 +103,7 @@ func List(input ListInput) (*amiv1.AWSAMIList, error) { if image == nil { continue } - creationTimestamp, err := time.Parse(time.RFC3339, aws.StringValue(image.CreationDate)) + creationTimestamp, err := time.Parse(time.RFC3339, aws.ToString(image.CreationDate)) if err != nil { return nil, err } @@ -114,13 +114,13 @@ func List(input ListInput) (*amiv1.AWSAMIList, error) { APIVersion: amiv1.SchemeGroupVersion.String(), }, ObjectMeta: metav1.ObjectMeta{ - Name: aws.StringValue(image.Name), + Name: aws.ToString(image.Name), CreationTimestamp: metav1.NewTime(creationTimestamp), }, Spec: amiv1.AWSAMISpec{ OS: os, Region: region, - ImageID: aws.StringValue(image.ImageId), + ImageID: aws.ToString(image.ImageId), KubernetesVersion: version, }, }) diff --git a/cmd/clusterawsadm/cloudformation/service/service.go b/cmd/clusterawsadm/cloudformation/service/service.go index 33db42a8d0..c73eeb9dd0 100644 --- a/cmd/clusterawsadm/cloudformation/service/service.go +++ b/cmd/clusterawsadm/cloudformation/service/service.go @@ -19,55 +19,80 @@ limitations under the License. package cloudformation import ( + "context" "fmt" "os" "text/tabwriter" + "time" - "github.com/aws/aws-sdk-go/aws" - cfn "github.com/aws/aws-sdk-go/service/cloudformation" - "github.com/aws/aws-sdk-go/service/cloudformation/cloudformationiface" + "github.com/aws/aws-sdk-go-v2/aws" + cfn "github.com/aws/aws-sdk-go-v2/service/cloudformation" + cfntypes "github.com/aws/aws-sdk-go-v2/service/cloudformation/types" go_cfn "github.com/awslabs/goformation/v4/cloudformation" "github.com/pkg/errors" "k8s.io/klog/v2" - "k8s.io/utils/ptr" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/awserrors" ) +const ( + // MaxWaitCreateUpdateDelete is the default maximum amount of time to wait for a cfn stack to complete. + MaxWaitCreateUpdateDelete = 30 * time.Minute +) + +// CFNAPI defines the CFN API interface. +type CFNAPI interface { + CreateStack(ctx context.Context, params *cfn.CreateStackInput, optFns ...func(*cfn.Options)) (*cfn.CreateStackOutput, error) + DeleteStack(ctx context.Context, params *cfn.DeleteStackInput, optFns ...func(*cfn.Options)) (*cfn.DeleteStackOutput, error) + DescribeStacks(ctx context.Context, params *cfn.DescribeStacksInput, optFns ...func(*cfn.Options)) (*cfn.DescribeStacksOutput, error) + DescribeStackResources(ctx context.Context, params *cfn.DescribeStackResourcesInput, optFns ...func(*cfn.Options)) (*cfn.DescribeStackResourcesOutput, error) + UpdateStack(ctx context.Context, params *cfn.UpdateStackInput, optFns ...func(*cfn.Options)) (*cfn.UpdateStackOutput, error) + + // Waiters for CFN stacks + WaitUntilStackCreateComplete(ctx context.Context, input *cfn.DescribeStacksInput, maxWait time.Duration) error + WaitUntilStackUpdateComplete(ctx context.Context, input *cfn.DescribeStacksInput, maxWait time.Duration) error + WaitUntilStackDeleteComplete(ctx context.Context, input *cfn.DescribeStacksInput, maxWait time.Duration) error +} + +// CFNClient is a wrapper over cfn.Client for implementing custom methods of CFNAPI. +type CFNClient struct { + *cfn.Client +} + // Service holds a collection of interfaces. // The interfaces are broken down like this to group functions together. // One alternative is to have a large list of functions from the ec2 client. type Service struct { - CFN cloudformationiface.CloudFormationAPI + CFN CFNAPI } // NewService returns a new service given the CloudFormation api client. -func NewService(i cloudformationiface.CloudFormationAPI) *Service { +func NewService(i CFNAPI) *Service { return &Service{ CFN: i, } } // ReconcileBootstrapStack creates or updates bootstrap CloudFormation. -func (s *Service) ReconcileBootstrapStack(stackName string, t go_cfn.Template, tags map[string]string) error { +func (s *Service) ReconcileBootstrapStack(ctx context.Context, stackName string, t go_cfn.Template, tags map[string]string) error { yaml, err := t.YAML() processedYaml := string(yaml) if err != nil { return errors.Wrap(err, "failed to generate AWS CloudFormation YAML") } - stackTags := []*cfn.Tag{} + stackTags := []cfntypes.Tag{} for k, v := range tags { - stackTags = append(stackTags, &cfn.Tag{ - Key: ptr.To[string](k), - Value: ptr.To[string](v), + stackTags = append(stackTags, cfntypes.Tag{ + Key: aws.String(k), + Value: aws.String(v), }) } //nolint:nestif - if err := s.createStack(stackName, processedYaml, stackTags); err != nil { - if code, _ := awserrors.Code(errors.Cause(err)); code == "AlreadyExistsException" { + if err := s.createStack(ctx, stackName, processedYaml, stackTags); err != nil { + if code, _ := awserrors.Code(errors.Cause(err)); code == (&cfntypes.AlreadyExistsException{}).ErrorCode() { klog.Infof("AWS Cloudformation stack %q already exists, updating", klog.KRef("", stackName)) - updateErr := s.updateStack(stackName, processedYaml, stackTags) + updateErr := s.updateStack(ctx, stackName, processedYaml, stackTags) if updateErr != nil { code, ok := awserrors.Code(errors.Cause(updateErr)) message := awserrors.Message(errors.Cause(updateErr)) @@ -83,25 +108,25 @@ func (s *Service) ReconcileBootstrapStack(stackName string, t go_cfn.Template, t } // ReconcileBootstrapNoUpdate creates or updates bootstrap CloudFormation without updating the stack. -func (s *Service) ReconcileBootstrapNoUpdate(stackName string, t go_cfn.Template, tags map[string]string) error { +func (s *Service) ReconcileBootstrapNoUpdate(ctx context.Context, stackName string, t go_cfn.Template, tags map[string]string) error { yaml, err := t.YAML() processedYaml := string(yaml) if err != nil { return errors.Wrap(err, "failed to generate AWS CloudFormation YAML") } - stackTags := []*cfn.Tag{} + stackTags := []cfntypes.Tag{} for k, v := range tags { - stackTags = append(stackTags, &cfn.Tag{ + stackTags = append(stackTags, cfntypes.Tag{ Key: aws.String(k), Value: aws.String(v), }) } //nolint:nestif - if err := s.createStack(stackName, processedYaml, stackTags); err != nil { - if code, _ := awserrors.Code(errors.Cause(err)); code == "AlreadyExistsException" { + if err := s.createStack(ctx, stackName, processedYaml, stackTags); err != nil { + if code, _ := awserrors.Code(errors.Cause(err)); code == (&cfntypes.AlreadyExistsException{}).ErrorCode() { desInput := &cfn.DescribeStacksInput{StackName: aws.String(stackName)} - if err := s.CFN.WaitUntilStackCreateComplete(desInput); err != nil { + if err := s.CFN.WaitUntilStackCreateComplete(ctx, desInput, MaxWaitCreateUpdateDelete); err != nil { return errors.Wrap(err, "failed to wait for AWS CloudFormation stack to be CreateComplete") } return nil @@ -111,21 +136,21 @@ func (s *Service) ReconcileBootstrapNoUpdate(stackName string, t go_cfn.Template return nil } -func (s *Service) createStack(stackName, yaml string, tags []*cfn.Tag) error { +func (s *Service) createStack(ctx context.Context, stackName, yaml string, tags []cfntypes.Tag) error { input := &cfn.CreateStackInput{ - Capabilities: aws.StringSlice([]string{cfn.CapabilityCapabilityIam, cfn.CapabilityCapabilityNamedIam}), + Capabilities: []cfntypes.Capability{cfntypes.CapabilityCapabilityIam, cfntypes.CapabilityCapabilityNamedIam}, TemplateBody: aws.String(yaml), StackName: aws.String(stackName), Tags: tags, } klog.V(2).Infof("creating AWS CloudFormation stack %q", stackName) - if _, err := s.CFN.CreateStack(input); err != nil { + if _, err := s.CFN.CreateStack(ctx, input); err != nil { return errors.Wrap(err, "failed to create AWS CloudFormation stack") } desInput := &cfn.DescribeStacksInput{StackName: aws.String(stackName)} klog.V(2).Infof("waiting for stack %q to create", stackName) - if err := s.CFN.WaitUntilStackCreateComplete(desInput); err != nil { + if err := s.CFN.WaitUntilStackCreateComplete(ctx, desInput, MaxWaitCreateUpdateDelete); err != nil { return errors.Wrap(err, "failed to wait for AWS CloudFormation stack to be CreateComplete") } @@ -133,20 +158,20 @@ func (s *Service) createStack(stackName, yaml string, tags []*cfn.Tag) error { return nil } -func (s *Service) updateStack(stackName, yaml string, tags []*cfn.Tag) error { +func (s *Service) updateStack(ctx context.Context, stackName, yaml string, tags []cfntypes.Tag) error { input := &cfn.UpdateStackInput{ - Capabilities: aws.StringSlice([]string{cfn.CapabilityCapabilityIam, cfn.CapabilityCapabilityNamedIam}), + Capabilities: []cfntypes.Capability{cfntypes.CapabilityCapabilityIam, cfntypes.CapabilityCapabilityNamedIam}, TemplateBody: aws.String(yaml), StackName: aws.String(stackName), Tags: tags, } klog.V(2).Infof("updating AWS CloudFormation stack %q", stackName) - if _, err := s.CFN.UpdateStack(input); err != nil { + if _, err := s.CFN.UpdateStack(ctx, input); err != nil { return errors.Wrap(err, "failed to update AWS CloudFormation stack") } desInput := &cfn.DescribeStacksInput{StackName: aws.String(stackName)} klog.V(2).Infof("waiting for stack %q to update", stackName) - if err := s.CFN.WaitUntilStackUpdateComplete(desInput); err != nil { + if err := s.CFN.WaitUntilStackUpdateComplete(ctx, desInput, MaxWaitCreateUpdateDelete); err != nil { return errors.Wrap(err, "failed to update AWS CloudFormation stack") } @@ -155,20 +180,20 @@ func (s *Service) updateStack(stackName, yaml string, tags []*cfn.Tag) error { } // DeleteStack deletes a cloudformation stack. -func (s *Service) DeleteStack(stackName string, retainResources []*string) error { +func (s *Service) DeleteStack(ctx context.Context, stackName string, retainResources []string) error { klog.V(2).Infof("deleting AWS CloudFormation stack %q", stackName) var err error if retainResources == nil { - _, err = s.CFN.DeleteStack(&cfn.DeleteStackInput{StackName: aws.String(stackName)}) + _, err = s.CFN.DeleteStack(ctx, &cfn.DeleteStackInput{StackName: aws.String(stackName)}) } else { - _, err = s.CFN.DeleteStack(&cfn.DeleteStackInput{StackName: aws.String(stackName), RetainResources: retainResources}) + _, err = s.CFN.DeleteStack(ctx, &cfn.DeleteStackInput{StackName: aws.String(stackName), RetainResources: retainResources}) } if err != nil { return errors.Wrap(err, "failed to delete AWS CloudFormation stack") } klog.V(2).Infof("waiting for stack %q to delete", stackName) - if err := s.CFN.WaitUntilStackDeleteComplete(&cfn.DescribeStacksInput{StackName: aws.String(stackName)}); err != nil { + if err := s.CFN.WaitUntilStackDeleteComplete(ctx, &cfn.DescribeStacksInput{StackName: aws.String(stackName)}, MaxWaitCreateUpdateDelete); err != nil { return errors.Wrap(err, "failed to delete AWS CloudFormation stack") } @@ -178,11 +203,11 @@ func (s *Service) DeleteStack(stackName string, retainResources []*string) error // ShowStackResources prints out in tabular format the resources in the // stack. -func (s *Service) ShowStackResources(stackName string) error { +func (s *Service) ShowStackResources(ctx context.Context, stackName string) error { input := &cfn.DescribeStackResourcesInput{ StackName: aws.String(stackName), } - out, err := s.CFN.DescribeStackResources(input) + out, err := s.CFN.DescribeStackResources(ctx, input) if err != nil { return errors.Wrap(err, "unable to describe stack resources") } @@ -195,15 +220,15 @@ func (s *Service) ShowStackResources(stackName string) error { for _, r := range out.StackResources { fmt.Fprintf(w, "%s\t%s\t%s\n", - aws.StringValue(r.ResourceType), - aws.StringValue(r.PhysicalResourceId), - aws.StringValue(r.ResourceStatus)) + aws.ToString(r.ResourceType), + aws.ToString(r.PhysicalResourceId), + r.ResourceStatus) - switch aws.StringValue(r.ResourceStatus) { - case cfn.ResourceStatusCreateComplete, cfn.ResourceStatusUpdateComplete: + switch r.ResourceStatus { + case cfntypes.ResourceStatusCreateComplete, cfntypes.ResourceStatusUpdateComplete: continue default: - fmt.Println(aws.StringValue(r.ResourceStatusReason)) + fmt.Println(aws.ToString(r.ResourceStatusReason)) } } @@ -213,3 +238,30 @@ func (s *Service) ShowStackResources(stackName string) error { return nil } + +// WaitUntilStackCreateComplete is blocking function to wait until CFN Stack is successfully created. +func (c *CFNClient) WaitUntilStackCreateComplete(ctx context.Context, input *cfn.DescribeStacksInput, maxWait time.Duration) error { + waiter := cfn.NewStackCreateCompleteWaiter(c, func(o *cfn.StackCreateCompleteWaiterOptions) { + o.LogWaitAttempts = true + }) + + return waiter.Wait(ctx, input, maxWait) +} + +// WaitUntilStackUpdateComplete is blocking function to wait until CFN Stack is successfully updated. +func (c *CFNClient) WaitUntilStackUpdateComplete(ctx context.Context, input *cfn.DescribeStacksInput, maxWait time.Duration) error { + waiter := cfn.NewStackUpdateCompleteWaiter(c, func(o *cfn.StackUpdateCompleteWaiterOptions) { + o.LogWaitAttempts = true + }) + + return waiter.Wait(ctx, input, maxWait) +} + +// WaitUntilStackDeleteComplete is blocking function to wait until CFN Stack is successfully deleted. +func (c *CFNClient) WaitUntilStackDeleteComplete(ctx context.Context, input *cfn.DescribeStacksInput, maxWait time.Duration) error { + waiter := cfn.NewStackDeleteCompleteWaiter(c, func(o *cfn.StackDeleteCompleteWaiterOptions) { + o.LogWaitAttempts = true + }) + + return waiter.Wait(ctx, input, maxWait) +} diff --git a/cmd/clusterawsadm/cmd/bootstrap/iam/cloudformation.go b/cmd/clusterawsadm/cmd/bootstrap/iam/cloudformation.go index b4fe6af2f6..9fa4efa7fe 100644 --- a/cmd/clusterawsadm/cmd/bootstrap/iam/cloudformation.go +++ b/cmd/clusterawsadm/cmd/bootstrap/iam/cloudformation.go @@ -17,11 +17,11 @@ limitations under the License. package iam import ( + "context" "fmt" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/session" - cfn "github.com/aws/aws-sdk-go/service/cloudformation" + "github.com/aws/aws-sdk-go-v2/config" + cfn "github.com/aws/aws-sdk-go-v2/service/cloudformation" "github.com/spf13/cobra" "k8s.io/kubectl/pkg/util/templates" @@ -98,24 +98,25 @@ func createCloudFormationStackCmd() *cobra.Command { } fmt.Printf("Attempting to create AWS CloudFormation stack %s\n", t.Spec.StackName) - sess, err := session.NewSessionWithOptions(session.Options{ - SharedConfigState: session.SharedConfigEnable, - Config: aws.Config{Region: aws.String(t.Spec.Region)}, - }) + + sess, err := config.LoadDefaultConfig(context.TODO(), config.WithRegion(t.Spec.Region)) if err != nil { fmt.Printf("Error: %v\n", err) return err } - cfnSvc := cloudformation.NewService(cfn.New(sess)) + cfnSvc := cloudformation.NewService( + &cloudformation.CFNClient{ + Client: cfn.NewFromConfig(sess), + }) - err = cfnSvc.ReconcileBootstrapStack(t.Spec.StackName, *t.RenderCloudFormation(), t.Spec.StackTags) + err = cfnSvc.ReconcileBootstrapStack(context.TODO(), t.Spec.StackName, *t.RenderCloudFormation(), t.Spec.StackTags) if err != nil { fmt.Printf("Error: %v\n", err) return err } - return cfnSvc.ShowStackResources(t.Spec.StackName) + return cfnSvc.ShowStackResources(context.TODO(), t.Spec.StackName) }, } addConfigFlag(newCmd) @@ -144,18 +145,19 @@ func deleteCloudFormationStackCmd() *cobra.Command { } fmt.Printf("Attempting to delete AWS CloudFormation stack %s\n", t.Spec.StackName) - sess, err := session.NewSessionWithOptions(session.Options{ - SharedConfigState: session.SharedConfigEnable, - Config: aws.Config{Region: aws.String(t.Spec.Region)}, - }) + + sess, err := config.LoadDefaultConfig(context.TODO(), config.WithRegion(t.Spec.Region)) if err != nil { fmt.Printf("Error: %v\n", err) return err } - cfnSvc := cloudformation.NewService(cfn.New(sess)) + cfnSvc := cloudformation.NewService( + &cloudformation.CFNClient{ + Client: cfn.NewFromConfig(sess), + }) - err = cfnSvc.DeleteStack(t.Spec.StackName, nil) + err = cfnSvc.DeleteStack(context.TODO(), t.Spec.StackName, nil) if err != nil { fmt.Printf("Error: %v\n", err) return err diff --git a/cmd/clusterawsadm/cmd/eks/addons/list_installed.go b/cmd/clusterawsadm/cmd/eks/addons/list_installed.go index e596e238c6..7a916eca3e 100644 --- a/cmd/clusterawsadm/cmd/eks/addons/list_installed.go +++ b/cmd/clusterawsadm/cmd/eks/addons/list_installed.go @@ -21,9 +21,9 @@ import ( "fmt" "os" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/config" "github.com/aws/aws-sdk-go-v2/service/eks" - "github.com/aws/aws-sdk-go/aws" "github.com/spf13/cobra" "k8s.io/utils/ptr" diff --git a/cmd/clusterawsadm/cmd/eks/addons/types.go b/cmd/clusterawsadm/cmd/eks/addons/types.go index 1c4ef83ffb..30323b4ed3 100644 --- a/cmd/clusterawsadm/cmd/eks/addons/types.go +++ b/cmd/clusterawsadm/cmd/eks/addons/types.go @@ -20,7 +20,7 @@ import ( "fmt" "time" - "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go-v2/aws" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" ) diff --git a/cmd/clusterawsadm/cmd/resource/list/list.go b/cmd/clusterawsadm/cmd/resource/list/list.go index 1a2171a201..175df28356 100644 --- a/cmd/clusterawsadm/cmd/resource/list/list.go +++ b/cmd/clusterawsadm/cmd/resource/list/list.go @@ -55,7 +55,7 @@ func ListAWSResourceCmd() *cobra.Command { } fmt.Fprintf(os.Stdout, "Attempting to fetch resources created by CAPA for cluster:%s present in %s\n\n", clusterName, region) - resourceList, err := resource.ListAWSResource(®ion, &clusterName) + resourceList, err := resource.ListAWSResource(region, clusterName) if err != nil || len(resourceList.AWSResources) == 0 { return err } diff --git a/cmd/clusterawsadm/credentials/credentials.go b/cmd/clusterawsadm/credentials/credentials.go index 1807545253..43dc9eb0ed 100644 --- a/cmd/clusterawsadm/credentials/credentials.go +++ b/cmd/clusterawsadm/credentials/credentials.go @@ -19,12 +19,12 @@ package credentials import ( "bytes" + "context" "encoding/base64" "errors" "text/template" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/session" + "github.com/aws/aws-sdk-go-v2/config" "sigs.k8s.io/cluster-api-provider-aws/v2/cmd/clusterawsadm/cmd/util" ) @@ -60,17 +60,14 @@ type AWSCredentials struct { // default chain. func NewAWSCredentialFromDefaultChain(region, profile string) (*AWSCredentials, error) { creds := AWSCredentials{} - conf := aws.NewConfig() - conf.CredentialsChainVerboseErrors = aws.Bool(true) - sess, err := session.NewSessionWithOptions(session.Options{ - SharedConfigState: session.SharedConfigEnable, - Profile: profile, - Config: *conf, - }) + ctx := context.TODO() + + sess, err := config.LoadDefaultConfig(ctx, config.WithRegion(region), config.WithSharedConfigProfile(profile)) + if err != nil { return nil, err } - chainCreds, err := sess.Config.Credentials.Get() + chainCreds, err := sess.Credentials.Retrieve(ctx) if err != nil { return nil, err } diff --git a/cmd/clusterawsadm/resource/list.go b/cmd/clusterawsadm/resource/list.go index 2d8b39456d..ff8ce76d83 100644 --- a/cmd/clusterawsadm/resource/list.go +++ b/cmd/clusterawsadm/resource/list.go @@ -17,50 +17,47 @@ limitations under the License. package resource import ( + "context" "fmt" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/arn" - "github.com/aws/aws-sdk-go/aws/session" - rgapi "github.com/aws/aws-sdk-go/service/resourcegroupstaggingapi" + "github.com/aws/aws-sdk-go-v2/aws" + "github.com/aws/aws-sdk-go-v2/aws/arn" + "github.com/aws/aws-sdk-go-v2/config" + rgapi "github.com/aws/aws-sdk-go-v2/service/resourcegroupstaggingapi" + rgapitypes "github.com/aws/aws-sdk-go-v2/service/resourcegroupstaggingapi/types" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" ) // ListAWSResource fetches all AWS resources created by CAPA. -func ListAWSResource(region, clusterName *string) (AWSResourceList, error) { +func ListAWSResource(region, clusterName string) (AWSResourceList, error) { var resourceList AWSResourceList - cfg := aws.Config{} - if *region != "" { - cfg.Region = region - } + ctx := context.TODO() - sess, err := session.NewSessionWithOptions(session.Options{ - SharedConfigState: session.SharedConfigEnable, - Config: cfg, - }) + sess, err := config.LoadDefaultConfig(ctx, config.WithRegion(region)) if err != nil { return resourceList, err } - resourceClient := rgapi.New(sess) + resourceClient := rgapi.NewFromConfig(sess) input := &rgapi.GetResourcesInput{ - TagFilters: []*rgapi.TagFilter{}, + TagFilters: []rgapitypes.TagFilter{}, } awsResourceTags := infrav1.Build(infrav1.BuildParams{ - ClusterName: *clusterName, + ClusterName: clusterName, Lifecycle: infrav1.ResourceLifecycleOwned, }) for tagKey, tagValue := range awsResourceTags { - tagFilter := &rgapi.TagFilter{} - tagFilter.SetKey(tagKey) - tagFilter.SetValues([]*string{aws.String(tagValue)}) + tagFilter := rgapitypes.TagFilter{ + Key: aws.String(tagKey), + Values: []string{tagValue}, + } input.TagFilters = append(input.TagFilters, tagFilter) } - output, err := resourceClient.GetResources(input) + output, err := resourceClient.GetResources(ctx, input) if err != nil { return resourceList, err } @@ -71,7 +68,7 @@ func ListAWSResource(region, clusterName *string) (AWSResourceList, error) { } resourceList = AWSResourceList{ - ClusterName: *clusterName, + ClusterName: clusterName, AWSResources: []AWSResource{}, } diff --git a/controllers/awscluster_controller.go b/controllers/awscluster_controller.go index eb3904463b..d0ffbbc462 100644 --- a/controllers/awscluster_controller.go +++ b/controllers/awscluster_controller.go @@ -75,7 +75,6 @@ type AWSClusterReconciler struct { networkServiceFactory func(scope.ClusterScope) services.NetworkInterface elbServiceFactory func(scope.ELBScope) services.ELBInterface securityGroupFactory func(scope.ClusterScope) services.SecurityGroupInterface - Endpoints []scope.ServiceEndpoint WatchFilterValue string ExternalResourceGC bool AlternativeGCStrategy bool @@ -177,7 +176,6 @@ func (r *AWSClusterReconciler) Reconcile(ctx context.Context, req ctrl.Request) Cluster: cluster, AWSCluster: awsCluster, ControllerName: "awscluster", - Endpoints: r.Endpoints, TagUnmanagedNetworkResources: r.TagUnmanagedNetworkResources, MaxWaitActiveUpdateDelete: r.MaxWaitActiveUpdateDelete, }) diff --git a/controllers/awscluster_controller_unit_test.go b/controllers/awscluster_controller_unit_test.go index 6c89b0508b..ee2d0bb9cf 100644 --- a/controllers/awscluster_controller_unit_test.go +++ b/controllers/awscluster_controller_unit_test.go @@ -23,7 +23,7 @@ import ( "testing" "time" - "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" corev1 "k8s.io/api/core/v1" diff --git a/controllers/awsmachine_controller.go b/controllers/awsmachine_controller.go index 7e3c21a269..445bab678c 100644 --- a/controllers/awsmachine_controller.go +++ b/controllers/awsmachine_controller.go @@ -22,7 +22,7 @@ import ( "fmt" "time" - "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/blang/semver" ignTypes "github.com/coreos/ignition/config/v2_3/types" ignV3Types "github.com/coreos/ignition/v2/config/v3_4/types" @@ -84,7 +84,6 @@ type AWSMachineReconciler struct { secretsManagerServiceFactory func(cloud.ClusterScoper) services.SecretInterface SSMServiceFactory func(cloud.ClusterScoper) services.SecretInterface objectStoreServiceFactory func(cloud.ClusterScoper) services.ObjectStoreInterface - Endpoints []scope.ServiceEndpoint WatchFilterValue string TagUnmanagedNetworkResources bool MaxWaitActiveUpdateDelete time.Duration @@ -804,7 +803,7 @@ func (r *AWSMachineReconciler) cloudInitUserData(machineScope *scope.MachineScop machineScope.Error(serviceErr, "Failed to create AWS Secret entry", "secretPrefix", prefix) return nil, serviceErr } - encryptedCloudInit, err := secretSvc.UserData(machineScope.GetSecretPrefix(), machineScope.GetSecretCount(), machineScope.InfraCluster.Region(), r.Endpoints) + encryptedCloudInit, err := secretSvc.UserData(machineScope.GetSecretPrefix(), machineScope.GetSecretCount(), machineScope.InfraCluster.Region()) if err != nil { r.Recorder.Eventf(machineScope.AWSMachine, corev1.EventTypeWarning, "FailedGenerateAWSSecretsCloudInit", err.Error()) return nil, err @@ -1205,7 +1204,6 @@ func (r *AWSMachineReconciler) getInfraCluster(ctx context.Context, log *logger. Cluster: cluster, ControlPlane: controlPlane, ControllerName: "awsManagedControlPlane", - Endpoints: r.Endpoints, TagUnmanagedNetworkResources: r.TagUnmanagedNetworkResources, }) if err != nil { diff --git a/controllers/awsmachine_controller_test.go b/controllers/awsmachine_controller_test.go index 56aceb61d7..c2165e16ef 100644 --- a/controllers/awsmachine_controller_test.go +++ b/controllers/awsmachine_controller_test.go @@ -22,10 +22,10 @@ import ( "testing" "time" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" ec2types "github.com/aws/aws-sdk-go-v2/service/ec2/types" elb "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancing" - "github.com/aws/aws-sdk-go/aws" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" "github.com/pkg/errors" @@ -548,7 +548,7 @@ func expectConditions(g *WithT, m *infrav1.AWSMachine, expected []conditionAsser func mockedCreateSecretCall(s *mock_services.MockSecretInterfaceMockRecorder) { s.Create(gomock.AssignableToTypeOf(&scope.MachineScope{}), gomock.AssignableToTypeOf([]byte{})) - s.UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.AssignableToTypeOf([]scope.ServiceEndpoint{})) + s.UserData(gomock.Any(), gomock.Any(), gomock.Any()) } func mockedCreateInstanceCalls(m *mocks.MockEC2APIMockRecorder) { diff --git a/controllers/awsmachine_controller_unit_test.go b/controllers/awsmachine_controller_unit_test.go index a39a393b1d..e5e9827bdd 100644 --- a/controllers/awsmachine_controller_unit_test.go +++ b/controllers/awsmachine_controller_unit_test.go @@ -24,9 +24,9 @@ import ( "testing" "time" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" ec2types "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/golang/mock/gomock" . "github.com/onsi/ginkgo/v2" . "github.com/onsi/gomega" @@ -315,7 +315,7 @@ func TestAWSMachineReconciler(t *testing.T) { ec2Svc.EXPECT().InstanceIfExists(gomock.Any()).Return(nil, nil) secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return("test", int32(1), nil).Times(1) ec2Svc.EXPECT().CreateInstance(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, expectedErr) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) _, err := reconciler.reconcileNormal(context.Background(), ms, cs, cs, cs, cs) g.Expect(ms.AWSMachine.Finalizers).To(ContainElement(infrav1.MachineFinalizer)) @@ -372,7 +372,7 @@ func TestAWSMachineReconciler(t *testing.T) { instanceCreate(t, g) getInstanceSecurityGroups(t, g) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) _, _ = reconciler.reconcileNormal(context.Background(), ms, cs, cs, cs, cs) g.Expect(ms.AWSMachine.Spec.ProviderID).To(PointTo(Equal(providerID))) }) @@ -385,7 +385,7 @@ func TestAWSMachineReconciler(t *testing.T) { instanceCreate(t, g) getInstanceSecurityGroups(t, g) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) instance.State = infrav1.InstanceStatePending _, _ = reconciler.reconcileNormal(context.Background(), ms, cs, cs, cs, cs) @@ -405,7 +405,7 @@ func TestAWSMachineReconciler(t *testing.T) { instanceCreate(t, g) getInstanceSecurityGroups(t, g) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) instance.State = infrav1.InstanceStateRunning _, _ = reconciler.reconcileNormal(context.Background(), ms, cs, cs, cs, cs) @@ -428,7 +428,7 @@ func TestAWSMachineReconciler(t *testing.T) { klog.SetOutput(buf) instance.State = "NewAWSMachineState" secretSvc.EXPECT().Delete(gomock.Any()).Return(nil).Times(1) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return("test", int32(1), nil).Times(1) _, _ = reconciler.reconcileNormal(context.Background(), ms, cs, cs, cs, cs) g.Expect(ms.AWSMachine.Status.Ready).To(BeFalse()) @@ -443,7 +443,7 @@ func TestAWSMachineReconciler(t *testing.T) { ec2Svc.EXPECT().GetInstanceSecurityGroups(gomock.Any()). Return(map[string][]string{"eid": {}}, nil) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) ec2Svc.EXPECT().GetCoreSecurityGroups(gomock.Any()).Return([]string{}, nil) secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return("test", int32(1), nil).Times(1) } @@ -555,7 +555,7 @@ func TestAWSMachineReconciler(t *testing.T) { klog.SetOutput(buf) ec2Svc.EXPECT().GetInstanceSecurityGroups(gomock.Any()). Return(map[string][]string{"eid": {}}, nil).Times(1) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) ec2Svc.EXPECT().GetCoreSecurityGroups(gomock.Any()).Return([]string{}, nil).Times(1) secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return("test", int32(1), nil).Times(1) ec2Svc.EXPECT().GetAdditionalSecurityGroupsIDs(gomock.Any()).Return(nil, nil) @@ -617,7 +617,7 @@ func TestAWSMachineReconciler(t *testing.T) { klog.SetOutput(buf) secretSvc.EXPECT().Delete(gomock.Any()).Return(nil).Times(1) secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return("test", int32(1), nil).Times(1) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) } t.Run("should warn if an instance is shutting-down", func(t *testing.T) { @@ -665,7 +665,7 @@ func TestAWSMachineReconciler(t *testing.T) { } elbSvc.EXPECT().IsInstanceRegisteredWithAPIServerELB(gomock.Any(), gomock.Any()).Return(true, nil) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return("test", int32(1), nil).Times(1) ec2Svc.EXPECT().GetInstanceSecurityGroups(gomock.Any()).Return(map[string][]string{"eid": {}}, nil).Times(1) ec2Svc.EXPECT().GetCoreSecurityGroups(gomock.Any()).Return([]string{}, nil).Times(1) @@ -691,7 +691,7 @@ func TestAWSMachineReconciler(t *testing.T) { elbSvc.EXPECT().IsInstanceRegisteredWithAPIServerELB(gomock.Any(), gomock.Any()).Return(false, nil) elbSvc.EXPECT().RegisterInstanceWithAPIServerELB(gomock.Any(), gomock.Any()).Return(nil) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return("test", int32(1), nil).Times(1) ec2Svc.EXPECT().GetInstanceSecurityGroups(gomock.Any()).Return(map[string][]string{"eid": {}}, nil).Times(1) ec2Svc.EXPECT().GetCoreSecurityGroups(gomock.Any()).Return([]string{}, nil).Times(1) @@ -735,7 +735,7 @@ func TestAWSMachineReconciler(t *testing.T) { Name: "test", } - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return("test", int32(1), nil).Times(1) secretSvc.EXPECT().Delete(gomock.Any()).Return(errors.New("failed to delete entries from AWS Secret")).Times(1) @@ -765,7 +765,7 @@ func TestAWSMachineReconciler(t *testing.T) { ec2Svc.EXPECT().GetRunningInstanceByTags(gomock.Any()).Return(nil, nil) secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return("test", int32(1), nil).Times(1) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, errors.New(expectedError)).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, errors.New(expectedError)).Times(1) _, err := reconciler.reconcileNormal(context.Background(), ms, cs, cs, cs, cs) g.Expect(err.Error()).To(ContainSubstring(expectedError)) @@ -789,7 +789,7 @@ func TestAWSMachineReconciler(t *testing.T) { ec2Svc.EXPECT().CreateInstance(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(instance, nil) ec2Svc.EXPECT().GetRunningInstanceByTags(gomock.Any()).Return(nil, nil) elbSvc.EXPECT().IsInstanceRegisteredWithAPIServerELB(gomock.Any(), gomock.Any()).Return(false, errors.New("error describing ELB")) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return("test", int32(1), nil).Times(1) _, err := reconciler.reconcileNormal(context.Background(), ms, cs, cs, cs, cs) @@ -817,7 +817,7 @@ func TestAWSMachineReconciler(t *testing.T) { elbSvc.EXPECT().IsInstanceRegisteredWithAPIServerELB(gomock.Any(), gomock.Any()).Return(false, nil) elbSvc.EXPECT().RegisterInstanceWithAPIServerELB(gomock.Any(), gomock.Any()).Return(errors.New("failed to attach ELB")) secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return("test", int32(1), nil).Times(1) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) _, err := reconciler.reconcileNormal(context.Background(), ms, cs, cs, cs, cs) g.Expect(err).ToNot(BeNil()) @@ -845,7 +845,7 @@ func TestAWSMachineReconciler(t *testing.T) { ec2Svc.EXPECT().InstanceIfExists(gomock.Any()).Return(nil, nil) ec2Svc.EXPECT().CreateInstance(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(instance, nil) secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return("test", int32(1), nil) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil) } t.Run("Should fail to return machine annotations after instance is created", func(t *testing.T) { @@ -891,7 +891,7 @@ func TestAWSMachineReconciler(t *testing.T) { ec2Svc.EXPECT().InstanceIfExists(gomock.Any()).Return(nil, nil) ec2Svc.EXPECT().CreateInstance(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(instance, nil) secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return("test", int32(1), nil) - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil) ec2Svc.EXPECT().GetInstanceSecurityGroups(gomock.Any()).Return(map[string][]string{"eid": {}}, nil) } @@ -1013,7 +1013,7 @@ func TestAWSMachineReconciler(t *testing.T) { ec2Svc.EXPECT().GetRunningInstanceByTags(gomock.Any()).Return(nil, nil).AnyTimes() secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return(secretPrefix, int32(1), nil).Times(1) ec2Svc.EXPECT().CreateInstance(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(instance, nil).AnyTimes() - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) ec2Svc.EXPECT().GetInstanceSecurityGroups(gomock.Any()).Return(map[string][]string{"eid": {}}, nil).Times(1) ec2Svc.EXPECT().GetCoreSecurityGroups(gomock.Any()).Return([]string{}, nil).Times(1) ec2Svc.EXPECT().GetAdditionalSecurityGroupsIDs(gomock.Any()).Return(nil, nil).Times(1) @@ -1050,7 +1050,7 @@ func TestAWSMachineReconciler(t *testing.T) { ec2Svc.EXPECT().GetRunningInstanceByTags(gomock.Any()).Return(nil, nil).AnyTimes() secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return(secretPrefix, int32(1), nil).Times(1) ec2Svc.EXPECT().CreateInstance(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(instance, nil).AnyTimes() - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) ec2Svc.EXPECT().GetInstanceSecurityGroups(gomock.Any()).Return(map[string][]string{"eid": {}}, nil).Times(1) ec2Svc.EXPECT().GetCoreSecurityGroups(gomock.Any()).Return([]string{}, nil).Times(1) ec2Svc.EXPECT().GetAdditionalSecurityGroupsIDs(gomock.Any()).Return(nil, nil) @@ -1306,7 +1306,7 @@ func TestAWSMachineReconciler(t *testing.T) { instance.State = infrav1.InstanceStatePending secretSvc.EXPECT().Create(gomock.Any(), gomock.Any()).Return(secretPrefix, int32(1), nil).Times(1) ec2Svc.EXPECT().CreateInstance(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(instance, nil).AnyTimes() - secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) + secretSvc.EXPECT().UserData(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).Times(1) ec2Svc.EXPECT().GetInstanceSecurityGroups(gomock.Any()).Return(map[string][]string{"eid": {}}, nil).Times(1) ec2Svc.EXPECT().GetCoreSecurityGroups(gomock.Any()).Return([]string{}, nil).Times(1) ec2Svc.EXPECT().GetAdditionalSecurityGroupsIDs(gomock.Any()).Return(nil, nil) diff --git a/controllers/rosacluster_controller.go b/controllers/rosacluster_controller.go index f335e69806..2207180c17 100644 --- a/controllers/rosacluster_controller.go +++ b/controllers/rosacluster_controller.go @@ -35,7 +35,6 @@ import ( infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" rosacontrolplanev1 "sigs.k8s.io/cluster-api-provider-aws/v2/controlplane/rosa/api/v1beta2" expinfrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/exp/api/v1beta2" - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/scope" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/logger" "sigs.k8s.io/cluster-api-provider-aws/v2/util/paused" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" @@ -49,7 +48,6 @@ type ROSAClusterReconciler struct { client.Client Recorder record.EventRecorder WatchFilterValue string - Endpoints []scope.ServiceEndpoint } // +kubebuilder:rbac:groups=infrastructure.cluster.x-k8s.io,resources=rosaclusters,verbs=get;list;watch;update;patch;delete diff --git a/controlplane/eks/api/v1beta1/validate.go b/controlplane/eks/api/v1beta1/validate.go index 7851ae6d0a..914df0e2e9 100644 --- a/controlplane/eks/api/v1beta1/validate.go +++ b/controlplane/eks/api/v1beta1/validate.go @@ -19,7 +19,7 @@ package v1beta1 import ( "strings" - "github.com/aws/aws-sdk-go/aws/arn" + "github.com/aws/aws-sdk-go-v2/aws/arn" "github.com/pkg/errors" ) diff --git a/controlplane/eks/api/v1beta2/awsmanagedcontrolplane_webhook_test.go b/controlplane/eks/api/v1beta2/awsmanagedcontrolplane_webhook_test.go index 4a6b79a782..6a260562b0 100644 --- a/controlplane/eks/api/v1beta2/awsmanagedcontrolplane_webhook_test.go +++ b/controlplane/eks/api/v1beta2/awsmanagedcontrolplane_webhook_test.go @@ -22,7 +22,7 @@ import ( "strings" "testing" - "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go-v2/aws" . "github.com/onsi/gomega" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/utils/ptr" diff --git a/controlplane/eks/api/v1beta2/validate.go b/controlplane/eks/api/v1beta2/validate.go index 0579247ed0..0d2491c4a3 100644 --- a/controlplane/eks/api/v1beta2/validate.go +++ b/controlplane/eks/api/v1beta2/validate.go @@ -19,7 +19,7 @@ package v1beta2 import ( "strings" - "github.com/aws/aws-sdk-go/aws/arn" + "github.com/aws/aws-sdk-go-v2/aws/arn" "github.com/pkg/errors" ) diff --git a/controlplane/eks/controllers/awsmanagedcontrolplane_controller.go b/controlplane/eks/controllers/awsmanagedcontrolplane_controller.go index a2dda6c2b6..0aaa2cf867 100644 --- a/controlplane/eks/controllers/awsmanagedcontrolplane_controller.go +++ b/controlplane/eks/controllers/awsmanagedcontrolplane_controller.go @@ -85,8 +85,7 @@ func securityGroupRolesForControlPlane(scope *scope.ManagedControlPlaneScope) [] // AWSManagedControlPlaneReconciler reconciles a AWSManagedControlPlane object. type AWSManagedControlPlaneReconciler struct { client.Client - Recorder record.EventRecorder - Endpoints []scope.ServiceEndpoint + Recorder record.EventRecorder awsNodeServiceFactory func(scope.AWSNodeScope) services.AWSNodeInterface ec2ServiceFactory func(scope.EC2Scope) services.EC2Interface @@ -249,7 +248,6 @@ func (r *AWSManagedControlPlaneReconciler) Reconcile(ctx context.Context, req ct MaxWaitActiveUpdateDelete: r.MaxWaitActiveUpdateDelete, EnableIAM: r.EnableIAM, AllowAdditionalRoles: r.AllowAdditionalRoles, - Endpoints: r.Endpoints, TagUnmanagedNetworkResources: r.TagUnmanagedNetworkResources, Logger: log, }) diff --git a/controlplane/rosa/controllers/rosacontrolplane_controller.go b/controlplane/rosa/controllers/rosacontrolplane_controller.go index 7e95adf4cc..37143bc3f9 100644 --- a/controlplane/rosa/controllers/rosacontrolplane_controller.go +++ b/controlplane/rosa/controllers/rosacontrolplane_controller.go @@ -90,7 +90,6 @@ type ROSAControlPlaneReconciler struct { client.Client WatchFilterValue string WaitInfraPeriod time.Duration - Endpoints []scope.ServiceEndpoint NewStsClient func(cloud.ScopeUsage, cloud.Session, logger.Wrapper, runtime.Object) stsiface.STSClient NewOCMClient func(ctx context.Context, rosaScope *scope.ROSAControlPlaneScope) (rosa.OCMClient, error) // Exposing the restClientConfig for integration test. No need to initialize. @@ -178,7 +177,6 @@ func (r *ROSAControlPlaneReconciler) Reconcile(ctx context.Context, req ctrl.Req Cluster: cluster, ControlPlane: rosaControlPlane, ControllerName: strings.ToLower(rosaControlPlaneKind), - Endpoints: r.Endpoints, Logger: log, NewStsClient: r.NewStsClient, }) diff --git a/controlplane/rosa/controllers/rosacontrolplane_controller_test.go b/controlplane/rosa/controllers/rosacontrolplane_controller_test.go index cf3386c101..61b8f9ce52 100644 --- a/controlplane/rosa/controllers/rosacontrolplane_controller_test.go +++ b/controlplane/rosa/controllers/rosacontrolplane_controller_test.go @@ -28,8 +28,8 @@ import ( "testing" "time" + "github.com/aws/aws-sdk-go-v2/aws" stsv2 "github.com/aws/aws-sdk-go-v2/service/sts" - "github.com/aws/aws-sdk-go/aws" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" v1 "github.com/openshift-online/ocm-sdk-go/clustersmgmt/v1" @@ -417,7 +417,6 @@ func TestRosaControlPlaneReconcileStatusVersion(t *testing.T) { r := ROSAControlPlaneReconciler{ WatchFilterValue: "", - Endpoints: []scope.ServiceEndpoint{}, Client: testEnv, restClientConfig: cfg, NewStsClient: func(cloud.ScopeUsage, cloud.Session, logger.Wrapper, runtime.Object) stsiface.STSClient { diff --git a/docs/book/cmd/amilist/main.go b/docs/book/cmd/amilist/main.go index a6e5513bbe..0587414d19 100644 --- a/docs/book/cmd/amilist/main.go +++ b/docs/book/cmd/amilist/main.go @@ -19,31 +19,37 @@ package main import ( "bytes" + "context" "encoding/json" "github.com/aws/aws-lambda-go/lambda" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/session" - "github.com/aws/aws-sdk-go/service/s3/s3manager" + "github.com/aws/aws-sdk-go-v2/aws" + "github.com/aws/aws-sdk-go-v2/config" + s3manager "github.com/aws/aws-sdk-go-v2/feature/s3/manager" + "github.com/aws/aws-sdk-go-v2/service/s3" + "github.com/aws/aws-sdk-go-v2/service/s3/types" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/cluster-api-provider-aws/v2/cmd/clusterawsadm/ami" ) -var svc *s3manager.Uploader +var ( + ctx = context.TODO() + svc *s3manager.Uploader +) const ( bucket = "cluster-api-aws-amis.sigs.k8s.io" ) func init() { - var err error - var sess *session.Session - sess, err = session.NewSession() + sess, err := config.LoadDefaultConfig(ctx) if err != nil { panic(err) } - svc = s3manager.NewUploader(sess) + s3Client := s3.NewFromConfig(sess) + + svc = s3manager.NewUploader(s3Client) } func main() { @@ -67,11 +73,11 @@ func LambdaHandler() error { return err } - _, err = svc.Upload(&s3manager.UploadInput{ + _, err = svc.Upload(ctx, &s3.PutObjectInput{ Body: bytes.NewReader(data), Bucket: aws.String(bucket), Key: aws.String("amis.json"), - ACL: aws.String("public-read"), + ACL: types.ObjectCannedACLPublicRead, }) if err != nil { ctrl.Log.Error(err, "error uploading data") diff --git a/exp/api/v1beta2/awsmachinepool_webhook_test.go b/exp/api/v1beta2/awsmachinepool_webhook_test.go index 9b6a5cae5f..0f67692803 100644 --- a/exp/api/v1beta2/awsmachinepool_webhook_test.go +++ b/exp/api/v1beta2/awsmachinepool_webhook_test.go @@ -22,7 +22,7 @@ import ( "testing" "time" - "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go-v2/aws" . "github.com/onsi/gomega" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/utils/ptr" diff --git a/exp/api/v1beta2/awsmanagedmachinepool_webhook_test.go b/exp/api/v1beta2/awsmanagedmachinepool_webhook_test.go index 592707e429..34401a3cec 100644 --- a/exp/api/v1beta2/awsmanagedmachinepool_webhook_test.go +++ b/exp/api/v1beta2/awsmanagedmachinepool_webhook_test.go @@ -21,7 +21,7 @@ import ( "strings" "testing" - "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go-v2/aws" . "github.com/onsi/gomega" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/utils/ptr" diff --git a/exp/controlleridentitycreator/awscontrolleridentity_controller.go b/exp/controlleridentitycreator/awscontrolleridentity_controller.go index 288f7feb09..3a7784303f 100644 --- a/exp/controlleridentitycreator/awscontrolleridentity_controller.go +++ b/exp/controlleridentitycreator/awscontrolleridentity_controller.go @@ -34,7 +34,6 @@ import ( infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" ekscontrolplanev1 "sigs.k8s.io/cluster-api-provider-aws/v2/controlplane/eks/api/v1beta2" "sigs.k8s.io/cluster-api-provider-aws/v2/feature" - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/scope" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/logger" "sigs.k8s.io/cluster-api/util/predicates" ) @@ -43,7 +42,6 @@ import ( type AWSControllerIdentityReconciler struct { client.Client Log logr.Logger - Endpoints []scope.ServiceEndpoint WatchFilterValue string } diff --git a/exp/controllers/awsfargatepool_controller.go b/exp/controllers/awsfargatepool_controller.go index 7376290f75..b4fbb0f99d 100644 --- a/exp/controllers/awsfargatepool_controller.go +++ b/exp/controllers/awsfargatepool_controller.go @@ -45,7 +45,6 @@ import ( type AWSFargateProfileReconciler struct { client.Client Recorder record.EventRecorder - Endpoints []scope.ServiceEndpoint EnableIAM bool WatchFilterValue string } @@ -107,7 +106,6 @@ func (r *AWSFargateProfileReconciler) Reconcile(ctx context.Context, req ctrl.Re ControlPlane: controlPlane, FargateProfile: fargateProfile, EnableIAM: r.EnableIAM, - Endpoints: r.Endpoints, }) if err != nil { return ctrl.Result{}, errors.Wrap(err, "failed to create scope") diff --git a/exp/controllers/awsmachinepool_controller_test.go b/exp/controllers/awsmachinepool_controller_test.go index db2879ea86..59675a287a 100644 --- a/exp/controllers/awsmachinepool_controller_test.go +++ b/exp/controllers/awsmachinepool_controller_test.go @@ -24,9 +24,9 @@ import ( "fmt" "testing" + "github.com/aws/aws-sdk-go-v2/aws" ec2types "github.com/aws/aws-sdk-go-v2/service/ec2/types" "github.com/aws/aws-sdk-go-v2/service/s3" - "github.com/aws/aws-sdk-go/aws" "github.com/go-logr/logr" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" diff --git a/exp/controllers/awsmachinepool_machines.go b/exp/controllers/awsmachinepool_machines.go index a7aae3d666..24c633df05 100644 --- a/exp/controllers/awsmachinepool_machines.go +++ b/exp/controllers/awsmachinepool_machines.go @@ -4,7 +4,7 @@ import ( "context" "fmt" - "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/go-logr/logr" "github.com/pkg/errors" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" diff --git a/exp/controllers/awsmanagedmachinepool_controller.go b/exp/controllers/awsmanagedmachinepool_controller.go index 543a74f445..b7e918f7aa 100644 --- a/exp/controllers/awsmanagedmachinepool_controller.go +++ b/exp/controllers/awsmanagedmachinepool_controller.go @@ -54,7 +54,6 @@ import ( type AWSManagedMachinePoolReconciler struct { client.Client Recorder record.EventRecorder - Endpoints []scope.ServiceEndpoint EnableIAM bool AllowAdditionalRoles bool WatchFilterValue string @@ -166,7 +165,6 @@ func (r *AWSManagedMachinePoolReconciler) Reconcile(ctx context.Context, req ctr ManagedMachinePool: awsPool, EnableIAM: r.EnableIAM, AllowAdditionalRoles: r.AllowAdditionalRoles, - Endpoints: r.Endpoints, InfraCluster: managedControlPlaneScope, MaxWaitActiveUpdateDelete: r.MaxWaitActiveUpdateDelete, }) diff --git a/exp/controllers/rosamachinepool_controller.go b/exp/controllers/rosamachinepool_controller.go index 64b7a3e65a..4750369a9b 100644 --- a/exp/controllers/rosamachinepool_controller.go +++ b/exp/controllers/rosamachinepool_controller.go @@ -51,7 +51,6 @@ type ROSAMachinePoolReconciler struct { client.Client Recorder record.EventRecorder WatchFilterValue string - Endpoints []scope.ServiceEndpoint NewStsClient func(cloud.ScopeUsage, cloud.Session, logger.Wrapper, runtime.Object) stsservice.STSClient NewOCMClient func(ctx context.Context, rosaScope *scope.ROSAControlPlaneScope) (rosa.OCMClient, error) } @@ -143,7 +142,6 @@ func (r *ROSAMachinePoolReconciler) Reconcile(ctx context.Context, req ctrl.Requ MachinePool: machinePool, RosaMachinePool: rosaMachinePool, Logger: log, - Endpoints: r.Endpoints, }) if err != nil { return ctrl.Result{}, errors.Wrap(err, "failed to create rosaMachinePool scope") @@ -154,7 +152,6 @@ func (r *ROSAMachinePoolReconciler) Reconcile(ctx context.Context, req ctrl.Requ Cluster: cluster, ControlPlane: controlPlane, ControllerName: "rosaControlPlane", - Endpoints: r.Endpoints, NewStsClient: r.NewStsClient, }) if err != nil { diff --git a/exp/controllers/rosamachinepool_controller_test.go b/exp/controllers/rosamachinepool_controller_test.go index 00e2dbc6b7..553cc38922 100644 --- a/exp/controllers/rosamachinepool_controller_test.go +++ b/exp/controllers/rosamachinepool_controller_test.go @@ -552,7 +552,6 @@ func TestRosaMachinePoolReconcile(t *testing.T) { r := ROSAMachinePoolReconciler{ Recorder: recorder, WatchFilterValue: "", - Endpoints: []scope.ServiceEndpoint{}, Client: testEnv, NewStsClient: func(cloud.ScopeUsage, cloud.Session, logger.Wrapper, runtime.Object) stsiface.STSClient { return stsMock @@ -649,7 +648,6 @@ func TestRosaMachinePoolReconcile(t *testing.T) { r := ROSAMachinePoolReconciler{ Recorder: recorder, WatchFilterValue: "", - Endpoints: []scope.ServiceEndpoint{}, Client: testEnv, NewStsClient: func(cloud.ScopeUsage, cloud.Session, logger.Wrapper, runtime.Object) stsiface.STSClient { return stsMock @@ -668,7 +666,6 @@ func TestRosaMachinePoolReconcile(t *testing.T) { MachinePool: omp, RosaMachinePool: mp, Logger: log, - Endpoints: r.Endpoints, }) g.Expect(err1).ToNot(HaveOccurred()) @@ -677,7 +674,6 @@ func TestRosaMachinePoolReconcile(t *testing.T) { Cluster: oc, ControlPlane: cp, ControllerName: "rosaControlPlane", - Endpoints: r.Endpoints, NewStsClient: r.NewStsClient, }) g.Expect(err2).ToNot(HaveOccurred()) diff --git a/exp/instancestate/awsinstancestate_controller.go b/exp/instancestate/awsinstancestate_controller.go index 97ccb91f63..3f8a09b925 100644 --- a/exp/instancestate/awsinstancestate_controller.go +++ b/exp/instancestate/awsinstancestate_controller.go @@ -54,7 +54,6 @@ type AwsInstanceStateReconciler struct { Log logr.Logger sqsServiceFactory func() instancestate.SQSAPI queueURLs sync.Map - Endpoints []scope.ServiceEndpoint WatchFilterValue string } @@ -69,7 +68,6 @@ func (r *AwsInstanceStateReconciler) getSQSService(region string) (instancestate globalScope, err := scope.NewGlobalScope(scope.GlobalScopeParams{ ControllerName: "awsinstancestate", Region: region, - Endpoints: r.Endpoints, }) if err != nil { diff --git a/go.mod b/go.mod index 56496dbc8b..cfd3722878 100644 --- a/go.mod +++ b/go.mod @@ -7,22 +7,26 @@ require ( github.com/apparentlymart/go-cidr v1.1.0 github.com/aws/amazon-vpc-cni-k8s v1.15.5 github.com/aws/aws-lambda-go v1.41.0 - github.com/aws/aws-sdk-go v1.55.7 - github.com/aws/aws-sdk-go-v2 v1.36.5 - github.com/aws/aws-sdk-go-v2/config v1.27.11 - github.com/aws/aws-sdk-go-v2/credentials v1.17.11 + github.com/aws/aws-sdk-go-v2 v1.38.0 + github.com/aws/aws-sdk-go-v2/config v1.31.0 + github.com/aws/aws-sdk-go-v2/credentials v1.18.4 + github.com/aws/aws-sdk-go-v2/feature/s3/manager v1.18.4 github.com/aws/aws-sdk-go-v2/service/autoscaling v1.52.4 + github.com/aws/aws-sdk-go-v2/service/cloudtrail v1.52.0 + github.com/aws/aws-sdk-go-v2/service/configservice v1.56.0 github.com/aws/aws-sdk-go-v2/service/ec2 v1.233.0 + github.com/aws/aws-sdk-go-v2/service/ecrpublic v1.36.0 + github.com/aws/aws-sdk-go-v2/service/efs v1.39.0 github.com/aws/aws-sdk-go-v2/service/eks v1.64.0 github.com/aws/aws-sdk-go-v2/service/elasticloadbalancing v1.29.6 github.com/aws/aws-sdk-go-v2/service/elasticloadbalancingv2 v1.45.2 github.com/aws/aws-sdk-go-v2/service/iam v1.32.0 github.com/aws/aws-sdk-go-v2/service/resourcegroupstaggingapi v1.26.6 - github.com/aws/aws-sdk-go-v2/service/s3 v1.53.1 + github.com/aws/aws-sdk-go-v2/service/s3 v1.87.0 github.com/aws/aws-sdk-go-v2/service/secretsmanager v1.28.6 github.com/aws/aws-sdk-go-v2/service/ssm v1.59.1 - github.com/aws/aws-sdk-go-v2/service/sts v1.28.6 - github.com/aws/smithy-go v1.22.4 + github.com/aws/aws-sdk-go-v2/service/sts v1.37.0 + github.com/aws/smithy-go v1.22.5 github.com/awslabs/goformation/v4 v4.19.5 github.com/blang/semver v3.5.1+incompatible github.com/coreos/ignition v0.35.0 @@ -66,6 +70,8 @@ require ( sigs.k8s.io/yaml v1.4.0 ) +require github.com/aws/aws-sdk-go v1.55.7 // indirect + require ( al.essio.dev/pkg/shellescape v1.5.1 // indirect cel.dev/expr v0.18.0 // indirect @@ -84,23 +90,23 @@ require ( github.com/adrg/xdg v0.5.3 // indirect github.com/antlr4-go/antlr/v4 v4.13.0 // indirect github.com/asaskevich/govalidator v0.0.0-20200428143746-21a406dcc535 // indirect - github.com/aws/aws-sdk-go-v2/aws/protocol/eventstream v1.6.2 // indirect - github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.16.1 // indirect - github.com/aws/aws-sdk-go-v2/internal/configsources v1.3.36 // indirect - github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.6.36 // indirect - github.com/aws/aws-sdk-go-v2/internal/ini v1.8.0 // indirect - github.com/aws/aws-sdk-go-v2/internal/v4a v1.3.36 // indirect - github.com/aws/aws-sdk-go-v2/service/cloudformation v1.50.0 // indirect + github.com/aws/aws-sdk-go-v2/aws/protocol/eventstream v1.7.0 // indirect + github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.18.3 // indirect + github.com/aws/aws-sdk-go-v2/internal/configsources v1.4.3 // indirect + github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.7.3 // indirect + github.com/aws/aws-sdk-go-v2/internal/ini v1.8.3 // indirect + github.com/aws/aws-sdk-go-v2/internal/v4a v1.4.3 // indirect + github.com/aws/aws-sdk-go-v2/service/cloudformation v1.50.0 github.com/aws/aws-sdk-go-v2/service/eventbridge v1.39.3 - github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding v1.12.4 // indirect - github.com/aws/aws-sdk-go-v2/service/internal/checksum v1.3.7 // indirect - github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.12.17 // indirect - github.com/aws/aws-sdk-go-v2/service/internal/s3shared v1.17.5 // indirect + github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding v1.13.0 // indirect + github.com/aws/aws-sdk-go-v2/service/internal/checksum v1.8.3 // indirect + github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.13.3 // indirect + github.com/aws/aws-sdk-go-v2/service/internal/s3shared v1.19.3 // indirect github.com/aws/aws-sdk-go-v2/service/organizations v1.27.3 // indirect - github.com/aws/aws-sdk-go-v2/service/servicequotas v1.21.4 // indirect + github.com/aws/aws-sdk-go-v2/service/servicequotas v1.21.4 github.com/aws/aws-sdk-go-v2/service/sqs v1.38.8 - github.com/aws/aws-sdk-go-v2/service/sso v1.20.5 // indirect - github.com/aws/aws-sdk-go-v2/service/ssooidc v1.23.4 // indirect + github.com/aws/aws-sdk-go-v2/service/sso v1.28.0 // indirect + github.com/aws/aws-sdk-go-v2/service/ssooidc v1.33.0 // indirect github.com/aymerick/douceur v0.2.0 // indirect github.com/beorn7/perks v1.0.1 // indirect github.com/blang/semver/v4 v4.0.0 // indirect diff --git a/go.sum b/go.sum index ed59e75cd3..ea099d0230 100644 --- a/go.sum +++ b/go.sum @@ -48,30 +48,40 @@ github.com/aws/aws-lambda-go v1.41.0 h1:l/5fyVb6Ud9uYd411xdHZzSf2n86TakxzpvIoz7l github.com/aws/aws-lambda-go v1.41.0/go.mod h1:jwFe2KmMsHmffA1X2R09hH6lFzJQxzI8qK17ewzbQMM= github.com/aws/aws-sdk-go v1.55.7 h1:UJrkFq7es5CShfBwlWAC8DA077vp8PyVbQd3lqLiztE= github.com/aws/aws-sdk-go v1.55.7/go.mod h1:eRwEWoyTWFMVYVQzKMNHWP5/RV4xIUGMQfXQHfHkpNU= -github.com/aws/aws-sdk-go-v2 v1.36.5 h1:0OF9RiEMEdDdZEMqF9MRjevyxAQcf6gY+E7vwBILFj0= -github.com/aws/aws-sdk-go-v2 v1.36.5/go.mod h1:EYrzvCCN9CMUTa5+6lf6MM4tq3Zjp8UhSGR/cBsjai0= -github.com/aws/aws-sdk-go-v2/aws/protocol/eventstream v1.6.2 h1:x6xsQXGSmW6frevwDA+vi/wqhp1ct18mVXYN08/93to= -github.com/aws/aws-sdk-go-v2/aws/protocol/eventstream v1.6.2/go.mod h1:lPprDr1e6cJdyYeGXnRaJoP4Md+cDBvi2eOj00BlGmg= -github.com/aws/aws-sdk-go-v2/config v1.27.11 h1:f47rANd2LQEYHda2ddSCKYId18/8BhSRM4BULGmfgNA= -github.com/aws/aws-sdk-go-v2/config v1.27.11/go.mod h1:SMsV78RIOYdve1vf36z8LmnszlRWkwMQtomCAI0/mIE= -github.com/aws/aws-sdk-go-v2/credentials v1.17.11 h1:YuIB1dJNf1Re822rriUOTxopaHHvIq0l/pX3fwO+Tzs= -github.com/aws/aws-sdk-go-v2/credentials v1.17.11/go.mod h1:AQtFPsDH9bI2O+71anW6EKL+NcD7LG3dpKGMV4SShgo= -github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.16.1 h1:FVJ0r5XTHSmIHJV6KuDmdYhEpvlHpiSd38RQWhut5J4= -github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.16.1/go.mod h1:zusuAeqezXzAB24LGuzuekqMAEgWkVYukBec3kr3jUg= -github.com/aws/aws-sdk-go-v2/internal/configsources v1.3.36 h1:SsytQyTMHMDPspp+spo7XwXTP44aJZZAC7fBV2C5+5s= -github.com/aws/aws-sdk-go-v2/internal/configsources v1.3.36/go.mod h1:Q1lnJArKRXkenyog6+Y+zr7WDpk4e6XlR6gs20bbeNo= -github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.6.36 h1:i2vNHQiXUvKhs3quBR6aqlgJaiaexz/aNvdCktW/kAM= -github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.6.36/go.mod h1:UdyGa7Q91id/sdyHPwth+043HhmP6yP9MBHgbZM0xo8= -github.com/aws/aws-sdk-go-v2/internal/ini v1.8.0 h1:hT8rVHwugYE2lEfdFE0QWVo81lF7jMrYJVDWI+f+VxU= -github.com/aws/aws-sdk-go-v2/internal/ini v1.8.0/go.mod h1:8tu/lYfQfFe6IGnaOdrpVgEL2IrrDOf6/m9RQum4NkY= -github.com/aws/aws-sdk-go-v2/internal/v4a v1.3.36 h1:GMYy2EOWfzdP3wfVAGXBNKY5vK4K8vMET4sYOYltmqs= -github.com/aws/aws-sdk-go-v2/internal/v4a v1.3.36/go.mod h1:gDhdAV6wL3PmPqBhiPbnlS447GoWs8HTTOYef9/9Inw= +github.com/aws/aws-sdk-go-v2 v1.38.0 h1:UCRQ5mlqcFk9HJDIqENSLR3wiG1VTWlyUfLDEvY7RxU= +github.com/aws/aws-sdk-go-v2 v1.38.0/go.mod h1:9Q0OoGQoboYIAJyslFyF1f5K1Ryddop8gqMhWx/n4Wg= +github.com/aws/aws-sdk-go-v2/aws/protocol/eventstream v1.7.0 h1:6GMWV6CNpA/6fbFHnoAjrv4+LGfyTqZz2LtCHnspgDg= +github.com/aws/aws-sdk-go-v2/aws/protocol/eventstream v1.7.0/go.mod h1:/mXlTIVG9jbxkqDnr5UQNQxW1HRYxeGklkM9vAFeabg= +github.com/aws/aws-sdk-go-v2/config v1.31.0 h1:9yH0xiY5fUnVNLRWO0AtayqwU1ndriZdN78LlhruJR4= +github.com/aws/aws-sdk-go-v2/config v1.31.0/go.mod h1:VeV3K72nXnhbe4EuxxhzsDc/ByrCSlZwUnWH52Nde/I= +github.com/aws/aws-sdk-go-v2/credentials v1.18.4 h1:IPd0Algf1b+Qy9BcDp0sCUcIWdCQPSzDoMK3a8pcbUM= +github.com/aws/aws-sdk-go-v2/credentials v1.18.4/go.mod h1:nwg78FjH2qvsRM1EVZlX9WuGUJOL5od+0qvm0adEzHk= +github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.18.3 h1:GicIdnekoJsjq9wqnvyi2elW6CGMSYKhdozE7/Svh78= +github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.18.3/go.mod h1:R7BIi6WNC5mc1kfRM7XM/VHC3uRWkjc396sfabq4iOo= +github.com/aws/aws-sdk-go-v2/feature/s3/manager v1.18.4 h1:0SzCLoPRSK3qSydsaFQWugP+lOBCTPwfcBOm6222+UA= +github.com/aws/aws-sdk-go-v2/feature/s3/manager v1.18.4/go.mod h1:JAet9FsBHjfdI+TnMBX4ModNNaQHAd3dc/Bk+cNsxeM= +github.com/aws/aws-sdk-go-v2/internal/configsources v1.4.3 h1:o9RnO+YZ4X+kt5Z7Nvcishlz0nksIt2PIzDglLMP0vA= +github.com/aws/aws-sdk-go-v2/internal/configsources v1.4.3/go.mod h1:+6aLJzOG1fvMOyzIySYjOFjcguGvVRL68R+uoRencN4= +github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.7.3 h1:joyyUFhiTQQmVK6ImzNU9TQSNRNeD9kOklqTzyk5v6s= +github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.7.3/go.mod h1:+vNIyZQP3b3B1tSLI0lxvrU9cfM7gpdRXMFfm67ZcPc= +github.com/aws/aws-sdk-go-v2/internal/ini v1.8.3 h1:bIqFDwgGXXN1Kpp99pDOdKMTTb5d2KyU5X/BZxjOkRo= +github.com/aws/aws-sdk-go-v2/internal/ini v1.8.3/go.mod h1:H5O/EsxDWyU+LP/V8i5sm8cxoZgc2fdNR9bxlOFrQTo= +github.com/aws/aws-sdk-go-v2/internal/v4a v1.4.3 h1:ZV2XK2L3HBq9sCKQiQ/MdhZJppH/rH0vddEAamsHUIs= +github.com/aws/aws-sdk-go-v2/internal/v4a v1.4.3/go.mod h1:b9F9tk2HdHpbf3xbN7rUZcfmJI26N6NcJu/8OsBFI/0= github.com/aws/aws-sdk-go-v2/service/autoscaling v1.52.4 h1:vzLD0FyNU4uxf2QE5UDG0jSEitiJXbVEUwf2Sk3usF4= github.com/aws/aws-sdk-go-v2/service/autoscaling v1.52.4/go.mod h1:CDqMoc3KRdZJ8qziW96J35lKH01Wq3B2aihtHj2JbRs= github.com/aws/aws-sdk-go-v2/service/cloudformation v1.50.0 h1:Ap5tOJfeAH1hO2UQc3X3uMlwP7uryFeZXMvZCXIlLSE= github.com/aws/aws-sdk-go-v2/service/cloudformation v1.50.0/go.mod h1:/v2KYdCW4BaHKayenaWEXOOdxItIwEA3oU0XzuQY3F0= +github.com/aws/aws-sdk-go-v2/service/cloudtrail v1.52.0 h1:Wgjh6Igu7HS57d8AjRIG0bHjybt015dBTc+zh2L/P3E= +github.com/aws/aws-sdk-go-v2/service/cloudtrail v1.52.0/go.mod h1:TSIIBxkIwUawJ9JyiymBksYZYsvIv8GIF2DkrlcTc5o= +github.com/aws/aws-sdk-go-v2/service/configservice v1.56.0 h1:BFDPvTQk/+BM9T8I6uHhtmur8uaroCXoJ0AI2kpNO1U= +github.com/aws/aws-sdk-go-v2/service/configservice v1.56.0/go.mod h1:46dDCtKXik+9IWU9oEOKBWzfQnyqn7EsmPnFUT7zqQw= github.com/aws/aws-sdk-go-v2/service/ec2 v1.233.0 h1:VxmOsv7MswuKQcSEIurxe4RK9tC6zYnosw9vBvv74lA= github.com/aws/aws-sdk-go-v2/service/ec2 v1.233.0/go.mod h1:35jGWx7ECvCwTsApqicFYzZ7JFEnBc6oHUuOQ3xIS54= +github.com/aws/aws-sdk-go-v2/service/ecrpublic v1.36.0 h1:8GcatvIKYx5WkwjwY4H+K7egBHOddC3wwS6fIbpOUlQ= +github.com/aws/aws-sdk-go-v2/service/ecrpublic v1.36.0/go.mod h1:yz4NeCWotlbHoT41Vc9NofCbKEyiNlKYZFT4SiqVQCY= +github.com/aws/aws-sdk-go-v2/service/efs v1.39.0 h1:nxn7P1nAd7ThB1B0WASAKvjddJQcvLzaOo9iN4tp3ZU= +github.com/aws/aws-sdk-go-v2/service/efs v1.39.0/go.mod h1:8Ij4/TIExqfWWjcyQy82/V/aec2kQruuyndljE+Vuo0= github.com/aws/aws-sdk-go-v2/service/eks v1.64.0 h1:EYeOThTRysemFtC6J6h6b7dNg3jN03QuO5cg92ojIQE= github.com/aws/aws-sdk-go-v2/service/eks v1.64.0/go.mod h1:v1xXy6ea0PHtWkjFUvAUh6B/5wv7UF909Nru0dOIJDk= github.com/aws/aws-sdk-go-v2/service/elasticloadbalancing v1.29.6 h1:9grU/+HRwLXJV8XUjEPThJj/H+0oHkeNBFpSSfZekeg= @@ -82,20 +92,20 @@ github.com/aws/aws-sdk-go-v2/service/eventbridge v1.39.3 h1:T6L7fsONflMeXuvsT8qZ github.com/aws/aws-sdk-go-v2/service/eventbridge v1.39.3/go.mod h1:sIrUII6Z+hAVAgcpmsc2e9HvEr++m/v8aBPT7s4ZYUk= github.com/aws/aws-sdk-go-v2/service/iam v1.32.0 h1:ZNlfPdw849gBo/lvLFbEEvpTJMij0LXqiNWZ+lIamlU= github.com/aws/aws-sdk-go-v2/service/iam v1.32.0/go.mod h1:aXWImQV0uTW35LM0A/T4wEg6R1/ReXUu4SM6/lUHYK0= -github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding v1.12.4 h1:CXV68E2dNqhuynZJPB80bhPQwAKqBWVer887figW6Jc= -github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding v1.12.4/go.mod h1:/xFi9KtvBXP97ppCz1TAEvU1Uf66qvid89rbem3wCzQ= -github.com/aws/aws-sdk-go-v2/service/internal/checksum v1.3.7 h1:ZMeFZ5yk+Ek+jNr1+uwCd2tG89t6oTS5yVWpa6yy2es= -github.com/aws/aws-sdk-go-v2/service/internal/checksum v1.3.7/go.mod h1:mxV05U+4JiHqIpGqqYXOHLPKUC6bDXC44bsUhNjOEwY= -github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.12.17 h1:t0E6FzREdtCsiLIoLCWsYliNsRBgyGD/MCK571qk4MI= -github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.12.17/go.mod h1:ygpklyoaypuyDvOM5ujWGrYWpAK3h7ugnmKCU/76Ys4= -github.com/aws/aws-sdk-go-v2/service/internal/s3shared v1.17.5 h1:f9RyWNtS8oH7cZlbn+/JNPpjUk5+5fLd5lM9M0i49Ys= -github.com/aws/aws-sdk-go-v2/service/internal/s3shared v1.17.5/go.mod h1:h5CoMZV2VF297/VLhRhO1WF+XYWOzXo+4HsObA4HjBQ= +github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding v1.13.0 h1:6+lZi2JeGKtCraAj1rpoZfKqnQ9SptseRZioejfUOLM= +github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding v1.13.0/go.mod h1:eb3gfbVIxIoGgJsi9pGne19dhCBpK6opTYpQqAmdy44= +github.com/aws/aws-sdk-go-v2/service/internal/checksum v1.8.3 h1:3ZKmesYBaFX33czDl6mbrcHb6jeheg6LqjJhQdefhsY= +github.com/aws/aws-sdk-go-v2/service/internal/checksum v1.8.3/go.mod h1:7ryVb78GLCnjq7cw45N6oUb9REl7/vNUwjvIqC5UgdY= +github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.13.3 h1:ieRzyHXypu5ByllM7Sp4hC5f/1Fy5wqxqY0yB85hC7s= +github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.13.3/go.mod h1:O5ROz8jHiOAKAwx179v+7sHMhfobFVi6nZt8DEyiYoM= +github.com/aws/aws-sdk-go-v2/service/internal/s3shared v1.19.3 h1:SE/e52dq9a05RuxzLcjT+S5ZpQobj3ie3UTaSf2NnZc= +github.com/aws/aws-sdk-go-v2/service/internal/s3shared v1.19.3/go.mod h1:zkpvBTsR020VVr8TOrwK2TrUW9pOir28sH5ECHpnAfo= github.com/aws/aws-sdk-go-v2/service/organizations v1.27.3 h1:CnPWlONzFX9/yO6IGuKg9sWUE8WhKztYRFbhmOHXjJI= github.com/aws/aws-sdk-go-v2/service/organizations v1.27.3/go.mod h1:hUHSXe9HFEmLfHrXndAX5e69rv0nBsg22VuNQYl0JLM= github.com/aws/aws-sdk-go-v2/service/resourcegroupstaggingapi v1.26.6 h1:PwbxovpcJvb25k019bkibvJfCpCmIANOFrXZIFPmRzk= github.com/aws/aws-sdk-go-v2/service/resourcegroupstaggingapi v1.26.6/go.mod h1:Z4xLt5mXspLKjBV92i165wAJ/3T6TIv4n7RtIS8pWV0= -github.com/aws/aws-sdk-go-v2/service/s3 v1.53.1 h1:6cnno47Me9bRykw9AEv9zkXE+5or7jz8TsskTTccbgc= -github.com/aws/aws-sdk-go-v2/service/s3 v1.53.1/go.mod h1:qmdkIIAC+GCLASF7R2whgNrJADz0QZPX+Seiw/i4S3o= +github.com/aws/aws-sdk-go-v2/service/s3 v1.87.0 h1:egoDf+Geuuntmw79Mz6mk9gGmELCPzg5PFEABOHB+6Y= +github.com/aws/aws-sdk-go-v2/service/s3 v1.87.0/go.mod h1:t9MDi29H+HDbkolTSQtbI0HP9DemAWQzUjmWC7LGMnE= github.com/aws/aws-sdk-go-v2/service/secretsmanager v1.28.6 h1:TIOEjw0i2yyhmhRry3Oeu9YtiiHWISZ6j/irS1W3gX4= github.com/aws/aws-sdk-go-v2/service/secretsmanager v1.28.6/go.mod h1:3Ba++UwWd154xtP4FRX5pUK3Gt4up5sDHCve6kVfE+g= github.com/aws/aws-sdk-go-v2/service/servicequotas v1.21.4 h1:SSDkZRAO8Ok5SoQ4BJ0onDeb0ga8JBOCkUmNEpRChcw= @@ -104,14 +114,14 @@ github.com/aws/aws-sdk-go-v2/service/sqs v1.38.8 h1:80dpSqWMwx2dAm30Ib7J6ucz1ZHf github.com/aws/aws-sdk-go-v2/service/sqs v1.38.8/go.mod h1:IzNt/udsXlETCdvBOL0nmyMe2t9cGmXmZgsdoZGYYhI= github.com/aws/aws-sdk-go-v2/service/ssm v1.59.1 h1:Z4cmgV3hKuUIkhJsdn47hf/ABYHUtILfMrV+L8+kRwE= github.com/aws/aws-sdk-go-v2/service/ssm v1.59.1/go.mod h1:PUWUl5MDiYNQkUHN9Pyd9kgtA/YhbxnSnHP+yQqzrM8= -github.com/aws/aws-sdk-go-v2/service/sso v1.20.5 h1:vN8hEbpRnL7+Hopy9dzmRle1xmDc7o8tmY0klsr175w= -github.com/aws/aws-sdk-go-v2/service/sso v1.20.5/go.mod h1:qGzynb/msuZIE8I75DVRCUXw3o3ZyBmUvMwQ2t/BrGM= -github.com/aws/aws-sdk-go-v2/service/ssooidc v1.23.4 h1:Jux+gDDyi1Lruk+KHF91tK2KCuY61kzoCpvtvJJBtOE= -github.com/aws/aws-sdk-go-v2/service/ssooidc v1.23.4/go.mod h1:mUYPBhaF2lGiukDEjJX2BLRRKTmoUSitGDUgM4tRxak= -github.com/aws/aws-sdk-go-v2/service/sts v1.28.6 h1:cwIxeBttqPN3qkaAjcEcsh8NYr8n2HZPkcKgPAi1phU= -github.com/aws/aws-sdk-go-v2/service/sts v1.28.6/go.mod h1:FZf1/nKNEkHdGGJP/cI2MoIMquumuRK6ol3QQJNDxmw= -github.com/aws/smithy-go v1.22.4 h1:uqXzVZNuNexwc/xrh6Tb56u89WDlJY6HS+KC0S4QSjw= -github.com/aws/smithy-go v1.22.4/go.mod h1:t1ufH5HMublsJYulve2RKmHDC15xu1f26kHCp/HgceI= +github.com/aws/aws-sdk-go-v2/service/sso v1.28.0 h1:Mc/MKBf2m4VynyJkABoVEN+QzkfLqGj0aiJuEe7cMeM= +github.com/aws/aws-sdk-go-v2/service/sso v1.28.0/go.mod h1:iS5OmxEcN4QIPXARGhavH7S8kETNL11kym6jhoS7IUQ= +github.com/aws/aws-sdk-go-v2/service/ssooidc v1.33.0 h1:6csaS/aJmqZQbKhi1EyEMM7yBW653Wy/B9hnBofW+sw= +github.com/aws/aws-sdk-go-v2/service/ssooidc v1.33.0/go.mod h1:59qHWaY5B+Rs7HGTuVGaC32m0rdpQ68N8QCN3khYiqs= +github.com/aws/aws-sdk-go-v2/service/sts v1.37.0 h1:MG9VFW43M4A8BYeAfaJJZWrroinxeTi2r3+SnmLQfSA= +github.com/aws/aws-sdk-go-v2/service/sts v1.37.0/go.mod h1:JdeBDPgpJfuS6rU/hNglmOigKhyEZtBmbraLE4GK1J8= +github.com/aws/smithy-go v1.22.5 h1:P9ATCXPMb2mPjYBgueqJNCA5S9UfktsW0tTxi+a7eqw= +github.com/aws/smithy-go v1.22.5/go.mod h1:t1ufH5HMublsJYulve2RKmHDC15xu1f26kHCp/HgceI= github.com/awslabs/goformation/v4 v4.19.5 h1:Y+Tzh01tWg8gf//AgGKUamaja7Wx9NPiJf1FpZu4/iU= github.com/awslabs/goformation/v4 v4.19.5/go.mod h1:JoNpnVCBOUtEz9bFxc9sjy8uBUCLF5c4D1L7RhRTVM8= github.com/aymerick/douceur v0.2.0 h1:Mv+mAeH1Q+n9Fr+oyamOlAkUNPWPlA8PPGR0QAaYuPk= diff --git a/main.go b/main.go index ff4cc75ce8..8aac35b373 100644 --- a/main.go +++ b/main.go @@ -62,7 +62,6 @@ import ( "sigs.k8s.io/cluster-api-provider-aws/v2/exp/instancestate" "sigs.k8s.io/cluster-api-provider-aws/v2/feature" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/endpoints" - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/scope" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/logger" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/record" "sigs.k8s.io/cluster-api-provider-aws/v2/version" @@ -229,15 +228,15 @@ func main() { } // Parse service endpoints. - awsServiceEndpoints, err := endpoints.ParseFlag(serviceEndpoints) + err = endpoints.ParseFlag(serviceEndpoints) if err != nil { setupLog.Error(err, "unable to parse service endpoints", "controller", "AWSCluster") os.Exit(1) } - setupReconcilersAndWebhooks(ctx, mgr, awsServiceEndpoints, externalResourceGC, alternativeGCStrategy) + setupReconcilersAndWebhooks(ctx, mgr, externalResourceGC, alternativeGCStrategy) if feature.Gates.Enabled(feature.EKS) { - setupEKSReconcilersAndWebhooks(ctx, mgr, awsServiceEndpoints, externalResourceGC, alternativeGCStrategy, waitInfraPeriod) + setupEKSReconcilersAndWebhooks(ctx, mgr, externalResourceGC, alternativeGCStrategy, waitInfraPeriod) } if feature.Gates.Enabled(feature.ROSA) { @@ -246,7 +245,6 @@ func main() { Client: mgr.GetClient(), WatchFilterValue: watchFilterValue, WaitInfraPeriod: waitInfraPeriod, - Endpoints: awsServiceEndpoints, }).SetupWithManager(ctx, mgr, controller.Options{MaxConcurrentReconciles: awsClusterConcurrency, RecoverPanic: ptr.To[bool](true)}); err != nil { setupLog.Error(err, "unable to create controller", "controller", "ROSAControlPlane") os.Exit(1) @@ -257,7 +255,6 @@ func main() { Client: mgr.GetClient(), Recorder: mgr.GetEventRecorderFor("rosacluster-controller"), WatchFilterValue: watchFilterValue, - Endpoints: awsServiceEndpoints, }).SetupWithManager(ctx, mgr, controller.Options{MaxConcurrentReconciles: awsClusterConcurrency, RecoverPanic: ptr.To[bool](true)}); err != nil { setupLog.Error(err, "unable to create controller", "controller", "ROSACluster") os.Exit(1) @@ -268,7 +265,6 @@ func main() { Client: mgr.GetClient(), Recorder: mgr.GetEventRecorderFor("rosamachinepool-controller"), WatchFilterValue: watchFilterValue, - Endpoints: awsServiceEndpoints, }).SetupWithManager(ctx, mgr, controller.Options{MaxConcurrentReconciles: awsClusterConcurrency, RecoverPanic: ptr.To[bool](true)}); err != nil { setupLog.Error(err, "unable to create controller", "controller", "ROSAMachinePool") os.Exit(1) @@ -304,7 +300,7 @@ func main() { } } -func setupReconcilersAndWebhooks(ctx context.Context, mgr ctrl.Manager, awsServiceEndpoints []scope.ServiceEndpoint, +func setupReconcilersAndWebhooks(ctx context.Context, mgr ctrl.Manager, externalResourceGC, alternativeGCStrategy bool, ) { // Default case - unmanaged controllers are enabled. @@ -313,7 +309,6 @@ func setupReconcilersAndWebhooks(ctx context.Context, mgr ctrl.Manager, awsServi Client: mgr.GetClient(), Log: ctrl.Log.WithName("controllers").WithName("AWSMachine"), Recorder: mgr.GetEventRecorderFor("awsmachine-controller"), - Endpoints: awsServiceEndpoints, WatchFilterValue: watchFilterValue, TagUnmanagedNetworkResources: feature.Gates.Enabled(feature.TagUnmanagedNetworkResources), MaxWaitActiveUpdateDelete: maxWaitActiveUpdateDelete, @@ -326,7 +321,6 @@ func setupReconcilersAndWebhooks(ctx context.Context, mgr ctrl.Manager, awsServi if err := (&controllers.AWSClusterReconciler{ Client: mgr.GetClient(), Recorder: mgr.GetEventRecorderFor("awscluster-controller"), - Endpoints: awsServiceEndpoints, WatchFilterValue: watchFilterValue, ExternalResourceGC: externalResourceGC, AlternativeGCStrategy: alternativeGCStrategy, @@ -364,7 +358,6 @@ func setupReconcilersAndWebhooks(ctx context.Context, mgr ctrl.Manager, awsServi if err := (&instancestate.AwsInstanceStateReconciler{ Client: mgr.GetClient(), Log: ctrl.Log.WithName("controllers").WithName("AWSInstanceStateController"), - Endpoints: awsServiceEndpoints, WatchFilterValue: watchFilterValue, }).SetupWithManager(ctx, mgr, controller.Options{MaxConcurrentReconciles: instanceStateConcurrency, RecoverPanic: ptr.To[bool](true)}); err != nil { setupLog.Error(err, "unable to create controller", "controller", "AWSInstanceStateController") @@ -377,7 +370,6 @@ func setupReconcilersAndWebhooks(ctx context.Context, mgr ctrl.Manager, awsServi if err := (&controlleridentitycreator.AWSControllerIdentityReconciler{ Client: mgr.GetClient(), Log: ctrl.Log.WithName("controllers").WithName("AWSControllerIdentity"), - Endpoints: awsServiceEndpoints, WatchFilterValue: watchFilterValue, }).SetupWithManager(ctx, mgr, controller.Options{MaxConcurrentReconciles: awsClusterConcurrency, RecoverPanic: ptr.To[bool](true)}); err != nil { setupLog.Error(err, "unable to create controller", "controller", "AWSControllerIdentity") @@ -415,7 +407,7 @@ func setupReconcilersAndWebhooks(ctx context.Context, mgr ctrl.Manager, awsServi } } -func setupEKSReconcilersAndWebhooks(ctx context.Context, mgr ctrl.Manager, awsServiceEndpoints []scope.ServiceEndpoint, +func setupEKSReconcilersAndWebhooks(ctx context.Context, mgr ctrl.Manager, externalResourceGC, alternativeGCStrategy bool, waitInfraPeriod time.Duration, ) { setupLog.Info("enabling EKS controllers and webhooks") @@ -439,7 +431,6 @@ func setupEKSReconcilersAndWebhooks(ctx context.Context, mgr ctrl.Manager, awsSe Client: mgr.GetClient(), EnableIAM: enableIAM, AllowAdditionalRoles: allowAddRoles, - Endpoints: awsServiceEndpoints, WatchFilterValue: watchFilterValue, ExternalResourceGC: externalResourceGC, AlternativeGCStrategy: alternativeGCStrategy, @@ -476,7 +467,6 @@ func setupEKSReconcilersAndWebhooks(ctx context.Context, mgr ctrl.Manager, awsSe Client: mgr.GetClient(), Recorder: mgr.GetEventRecorderFor("awsfargateprofile-reconciler"), EnableIAM: enableIAM, - Endpoints: awsServiceEndpoints, WatchFilterValue: watchFilterValue, }).SetupWithManager(ctx, mgr, controller.Options{MaxConcurrentReconciles: awsClusterConcurrency, RecoverPanic: ptr.To[bool](true)}); err != nil { setupLog.Error(err, "unable to create controller", "controller", "AWSFargateProfile") @@ -494,7 +484,6 @@ func setupEKSReconcilersAndWebhooks(ctx context.Context, mgr ctrl.Manager, awsSe AllowAdditionalRoles: allowAddRoles, Client: mgr.GetClient(), EnableIAM: enableIAM, - Endpoints: awsServiceEndpoints, Recorder: mgr.GetEventRecorderFor("awsmanagedmachinepool-reconciler"), WatchFilterValue: watchFilterValue, TagUnmanagedNetworkResources: feature.Gates.Enabled(feature.TagUnmanagedNetworkResources), diff --git a/pkg/cloud/awserrors/errors.go b/pkg/cloud/awserrors/errors.go index aa8e644e60..f3ea60ae42 100644 --- a/pkg/cloud/awserrors/errors.go +++ b/pkg/cloud/awserrors/errors.go @@ -21,8 +21,7 @@ import ( "errors" "net/http" - "github.com/aws/aws-sdk-go/aws/awserr" - "github.com/aws/aws-sdk-go/service/ssm" + ssmtypes "github.com/aws/aws-sdk-go-v2/service/ssm/types" "github.com/aws/smithy-go" smithyhttp "github.com/aws/smithy-go/transport/http" ) @@ -66,10 +65,6 @@ var _ error = &EC2Error{} // Code returns the AWS error code as a string. func Code(err error) (string, bool) { - if awserr, ok := err.(awserr.Error); ok { - return awserr.Code(), true - } - // Handle smithy errors from AWS SDK v2 if smithyErr := ParseSmithyError(err); smithyErr != nil && smithyErr.ErrorCode() != "" { return smithyErr.ErrorCode(), true @@ -80,10 +75,6 @@ func Code(err error) (string, bool) { // Message returns the AWS error message as a string. func Message(err error) string { - if awserr, ok := err.(awserr.Error); ok { - return awserr.Message() - } - // Handle smithy errors from AWS SDK v2 if smithyErr := ParseSmithyError(err); smithyErr != nil { return smithyErr.ErrorMessage() @@ -177,12 +168,6 @@ func IsConflict(err error) bool { return ReasonForError(err) == http.StatusConflict } -// IsSDKError returns true if the error is of type awserr.Error. -func IsSDKError(err error) (ok bool) { - _, ok = err.(awserr.Error) - return -} - // IsInvalidNotFoundError tests for common aws not found errors. func IsInvalidNotFoundError(err error) bool { if code, ok := Code(err); ok { @@ -191,7 +176,7 @@ func IsInvalidNotFoundError(err error) bool { return true case InvalidInstanceID: return true - case ssm.ErrCodeParameterNotFound: + case (&ssmtypes.ParameterNotFound{}).ErrorCode(): return true case LaunchTemplateNameNotFound: return true diff --git a/pkg/cloud/converters/tags.go b/pkg/cloud/converters/tags.go index 7ddd1abe85..fee23a2dc1 100644 --- a/pkg/cloud/converters/tags.go +++ b/pkg/cloud/converters/tags.go @@ -20,14 +20,14 @@ import ( "sort" "strings" + "github.com/aws/aws-sdk-go-v2/aws" autoscalingtypes "github.com/aws/aws-sdk-go-v2/service/autoscaling/types" ec2types "github.com/aws/aws-sdk-go-v2/service/ec2/types" elbtypes "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancing/types" elbv2types "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancingv2/types" iamtypes "github.com/aws/aws-sdk-go-v2/service/iam/types" + secretsmanagertypes "github.com/aws/aws-sdk-go-v2/service/secretsmanager/types" ssmtypes "github.com/aws/aws-sdk-go-v2/service/ssm/types" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/service/secretsmanager" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" ) @@ -149,25 +149,6 @@ func MapToV2Tags(src infrav1.Tags) []elbv2types.Tag { return tags } -// MapToSecretsManagerTags converts a infrav1.Tags to a []*secretsmanager.Tag. -func MapToSecretsManagerTags(src infrav1.Tags) []*secretsmanager.Tag { - tags := make([]*secretsmanager.Tag, 0, len(src)) - - for k, v := range src { - tag := &secretsmanager.Tag{ - Key: aws.String(k), - Value: aws.String(v), - } - - tags = append(tags, tag) - } - - // Sort so that unit tests can expect a stable order - sort.Slice(tags, func(i, j int) bool { return *tags[i].Key < *tags[j].Key }) - - return tags -} - // MapToIAMTags converts a infrav1.Tags to a []*iam.Tag. func MapToIAMTags(src infrav1.Tags) []iamtypes.Tag { tags := make([]iamtypes.Tag, 0, len(src)) @@ -197,3 +178,22 @@ func ASGTagsToMap(src []autoscalingtypes.TagDescription) infrav1.Tags { return tags } + +// MapToSecretsManagerTags converts a infrav1.Tags to a []secretsmanagertypes.Tag. +func MapToSecretsManagerTags(src infrav1.Tags) []secretsmanagertypes.Tag { + tags := make([]secretsmanagertypes.Tag, 0, len(src)) + + for k, v := range src { + tag := secretsmanagertypes.Tag{ + Key: aws.String(k), + Value: aws.String(v), + } + + tags = append(tags, tag) + } + + // Sort so that unit tests can expect a stable order + sort.Slice(tags, func(i, j int) bool { return *tags[i].Key < *tags[j].Key }) + + return tags +} diff --git a/pkg/cloud/convertersv2/tags.go b/pkg/cloud/convertersv2/tags.go deleted file mode 100644 index 69d2ae3f68..0000000000 --- a/pkg/cloud/convertersv2/tags.go +++ /dev/null @@ -1,202 +0,0 @@ -/* -Copyright 2025 The Kubernetes Authors. - -Licensed under the Apache License, Version 2.0 (the "License"); -you may not use this file except in compliance with the License. -You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - -Unless required by applicable law or agreed to in writing, software -distributed under the License is distributed on an "AS IS" BASIS, -WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -See the License for the specific language governing permissions and -limitations under the License. -*/ - -// Package convertersv2 provides conversion functions for AWS SDK V2 types to CAPA types. -package convertersv2 - -import ( - "sort" - - "github.com/aws/aws-sdk-go-v2/aws" - autoscalingtypes "github.com/aws/aws-sdk-go-v2/service/autoscaling/types" - v2ec2types "github.com/aws/aws-sdk-go-v2/service/ec2/types" - elbv1types "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancing/types" - elbv2types "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancingv2/types" - iamtypes "github.com/aws/aws-sdk-go-v2/service/iam/types" - secretsmanagertypes "github.com/aws/aws-sdk-go-v2/service/secretsmanager/types" - ssmtypes "github.com/aws/aws-sdk-go-v2/service/ssm/types" - - infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" -) - -// TagsToMap converts a []v2ec2types.Tag into a infrav1.Tags. -func TagsToMap(src []v2ec2types.Tag) infrav1.Tags { - tags := make(infrav1.Tags, len(src)) - - for _, t := range src { - tags[*t.Key] = *t.Value - } - - return tags -} - -// MapPtrToMap converts a [string]*string into a infrav1.Tags. -func MapPtrToMap(src map[string]*string) infrav1.Tags { - tags := make(infrav1.Tags, len(src)) - - for k, v := range src { - tags[k] = *v - } - - return tags -} - -// MapToTags converts a infrav1.Tags to a []v2ec2types.Tag. -func MapToTags(src infrav1.Tags) []v2ec2types.Tag { - tags := make([]v2ec2types.Tag, 0, len(src)) - - for k, v := range src { - tag := v2ec2types.Tag{ - Key: aws.String(k), - Value: aws.String(v), - } - - tags = append(tags, tag) - } - - // Sort so that unit tests can expect a stable order - sort.Slice(tags, func(i, j int) bool { return *tags[i].Key < *tags[j].Key }) - - return tags -} - -// ELBTagsToMap converts a []elbv1types.Tag into a infrav1.Tags. -func ELBTagsToMap(src []elbv1types.Tag) infrav1.Tags { - tags := make(infrav1.Tags, len(src)) - - for _, t := range src { - tags[*t.Key] = *t.Value - } - - return tags -} - -// V2TagsToMap converts a []elbv2types.Tag into a infrav1.Tags. -func V2TagsToMap(src []elbv2types.Tag) infrav1.Tags { - tags := make(infrav1.Tags, len(src)) - - for _, t := range src { - tags[*t.Key] = *t.Value - } - - return tags -} - -// MapToELBTags converts a infrav1.Tags to a []elbv1types.Tag. -func MapToELBTags(src infrav1.Tags) []elbv1types.Tag { - tags := make([]elbv1types.Tag, 0, len(src)) - - for k, v := range src { - tag := elbv1types.Tag{ - Key: aws.String(k), - Value: aws.String(v), - } - - tags = append(tags, tag) - } - - // Sort so that unit tests can expect a stable order - sort.Slice(tags, func(i, j int) bool { return *tags[i].Key < *tags[j].Key }) - - return tags -} - -// MapToV2Tags converts a infrav1.Tags to a []elbv2types.Tag. -func MapToV2Tags(src infrav1.Tags) []elbv2types.Tag { - tags := make([]elbv2types.Tag, 0, len(src)) - - for k, v := range src { - tag := elbv2types.Tag{ - Key: aws.String(k), - Value: aws.String(v), - } - - tags = append(tags, tag) - } - - // Sort so that unit tests can expect a stable order - sort.Slice(tags, func(i, j int) bool { return *tags[i].Key < *tags[j].Key }) - - return tags -} - -// MapToSecretsManagerTags converts a infrav1.Tags to a []secretsmanagertypes.Tag. -func MapToSecretsManagerTags(src infrav1.Tags) []secretsmanagertypes.Tag { - tags := make([]secretsmanagertypes.Tag, 0, len(src)) - - for k, v := range src { - tag := secretsmanagertypes.Tag{ - Key: aws.String(k), - Value: aws.String(v), - } - - tags = append(tags, tag) - } - - // Sort so that unit tests can expect a stable order - sort.Slice(tags, func(i, j int) bool { return *tags[i].Key < *tags[j].Key }) - - return tags -} - -// MapToSSMTags converts a infrav1.Tags to a []ssm.Tag. -func MapToSSMTags(src infrav1.Tags) []ssmtypes.Tag { - tags := make([]ssmtypes.Tag, 0, len(src)) - - for k, v := range src { - tag := ssmtypes.Tag{ - Key: aws.String(k), - Value: aws.String(v), - } - - tags = append(tags, tag) - } - - // Sort so that unit tests can expect a stable order - sort.Slice(tags, func(i, j int) bool { return *tags[i].Key < *tags[j].Key }) - - return tags -} - -// MapToIAMTags converts a infrav1.Tags to a []iamtypes.Tag. -func MapToIAMTags(src infrav1.Tags) []iamtypes.Tag { - tags := make([]iamtypes.Tag, 0, len(src)) - - for k, v := range src { - tag := iamtypes.Tag{ - Key: aws.String(k), - Value: aws.String(v), - } - - tags = append(tags, tag) - } - - // Sort so that unit tests can expect a stable order - sort.Slice(tags, func(i, j int) bool { return *tags[i].Key < *tags[j].Key }) - - return tags -} - -// ASGTagsToMap converts a []autoscalingtypes.TagDescription into a infrav1.Tags. -func ASGTagsToMap(src []autoscalingtypes.TagDescription) infrav1.Tags { - tags := make(infrav1.Tags, len(src)) - - for _, t := range src { - tags[*t.Key] = *t.Value - } - - return tags -} diff --git a/pkg/cloud/endpoints/codegen.go b/pkg/cloud/endpoints/codegen.go new file mode 100644 index 0000000000..992deb9297 --- /dev/null +++ b/pkg/cloud/endpoints/codegen.go @@ -0,0 +1,141 @@ +//go:build ignore +// +build ignore + +/* +Copyright 2025 The Kubernetes Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +/* +Copied from AWS SDK GO V2 and modified the package names as needed +This file shoud be updated with SDK verson bump if there change in this file. +Ref: https://github.com/aws/aws-sdk-go-v2/blob/main/internal/endpoints/awsrulesfn/internal/partition/codegen.go +*/ + +package main + +import ( + "encoding/json" + "flag" + "fmt" + "log" + "os" + "strconv" + "text/template" + + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/endpoints" +) + +var tmpl = template.Must(template.New("generate"). + Funcs(map[string]interface{}{ + "quote": func(v string) string { + return strconv.Quote(v) + }, + "strOrNil": func(v *string) string { + if v == nil { + return "nil" + } + return fmt.Sprintf("ptr.String(%q)", *v) + }, + "boolOrNil": func(v *bool) string { + if v == nil { + return "nil" + } + return fmt.Sprintf("ptr.Bool(%t)", *v) + }, + }). + Parse(` +{{- block "root" $ -}} +// Code generated by pkg/cloud/endpoints/codegen.go DO NOT EDIT. + +package endpoints + + +// GetPartition returns an AWS [Partition] for the region provided. If the +// partition cannot be determined nil will be returned. +func GetPartition(region string) *PartitionConfig { + return getPartition(partitions, region) +} + +var partitions = []Partition { + + {{- range $_, $partition := $.Partitions }} + Partition { + ID: {{ quote $partition.ID }}, + RegionRegex: {{ quote $partition.RegionRegex }}, + DefaultConfig: PartitionConfig{ + Name: {{ quote $partition.DefaultConfig.Name }}, + DnsSuffix: {{ quote $partition.DefaultConfig.DnsSuffix }}, + DualStackDnsSuffix: {{ quote $partition.DefaultConfig.DualStackDnsSuffix }}, + SupportsFIPS: {{ $partition.DefaultConfig.SupportsFIPS }}, + SupportsDualStack: {{ $partition.DefaultConfig.SupportsDualStack }}, + ImplicitGlobalRegion: {{ quote $partition.DefaultConfig.ImplicitGlobalRegion }}, + }, + Regions: map[string]RegionOverrides { + {{- range $region, $config := $partition.Regions }} + {{ quote $region }}: RegionOverrides{ + Name: {{ strOrNil $config.Name }}, + DnsSuffix: {{ strOrNil $config.DnsSuffix }}, + DualStackDnsSuffix: {{ strOrNil $config.DualStackDnsSuffix }}, + SupportsFIPS: {{ boolOrNil $config.SupportsFIPS }}, + SupportsDualStack: {{ boolOrNil $config.SupportsDualStack }}, + }, + {{- end }} + }, + }, + {{- end }} +} +{{- end }} +`)) + +type PartitionModel struct { + Partitions []endpoints.Partition `json:"partitions"` +} + +func main() { + var modelFilename, outputFilename string + flag.StringVar(&modelFilename, "model", "partitions.json", "The `file` providing the partition model metadata.") + flag.StringVar(&outputFilename, "output", "partitions.go", "The `file` to write the source to.") + flag.Parse() + + modelFile, err := os.Open(modelFilename) + if err != nil { + log.Fatalf("failed to open model file, %v", err) + } + + var model PartitionModel + if err = json.NewDecoder(modelFile).Decode(&model); err != nil { + log.Fatalf("failed to unmarshal model file, %v", err) + } + modelFile.Close() + + file, err := os.Create(outputFilename) + if err != nil { + log.Fatalf("failed to create output file, %v", err) + } + defer func() { + if err := file.Close(); err != nil { + log.Fatalf("failed to close output file, %v", err) + } + }() + + err = tmpl.Execute(file, struct { + Partitions []endpoints.Partition + }{ + Partitions: model.Partitions, + }) + if err != nil { + log.Fatalf("failed to render partition Go file, %v", err) + } +} diff --git a/pkg/cloud/endpoints/doc.go b/pkg/cloud/endpoints/doc.go new file mode 100644 index 0000000000..07d8dd4755 --- /dev/null +++ b/pkg/cloud/endpoints/doc.go @@ -0,0 +1,27 @@ +/* +Copyright 2025 The Kubernetes Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +/* +This file downloads the partition.json from AWS SDK GO V2 github and +generates Partition and data for use in the project. +*/ + +// Package endpoints provides AWS Service Endpoints, Region, Partition related methods. +package endpoints + +//go:generate /usr/bin/env bash -c "grep 'github.com/aws/aws-sdk-go-v2 ' ../../../go.mod | cut -d' ' -f2 > .awsSDKversion && curl -ssLO https://raw.githubusercontent.com/aws/aws-sdk-go-v2/refs/tags/$(cat .awsSDKversion)/internal/endpoints/awsrulesfn/partitions.json && rm .awsSDKversion" +//go:generate go run codegen.go -model partitions.json -output partitions.go +//go:generate /usr/bin/env bash -c "cat ../../../hack/boilerplate/boilerplate.generatego.txt partitions.go > _partitions.go && mv _partitions.go partitions.go && rm partitions.json" diff --git a/pkg/cloud/endpoints/endpoints.go b/pkg/cloud/endpoints/endpoints.go index 30d24a66b8..7c4356d452 100644 --- a/pkg/cloud/endpoints/endpoints.go +++ b/pkg/cloud/endpoints/endpoints.go @@ -14,18 +14,29 @@ See the License for the specific language governing permissions and limitations under the License. */ -// Package endpoints contains aws endpoint related utilities. package endpoints import ( + "context" "errors" "net/url" + "slices" "strings" - "github.com/aws/aws-sdk-go/aws/endpoints" + "github.com/aws/aws-sdk-go-v2/service/ec2" + "github.com/aws/aws-sdk-go-v2/service/eks" + elb "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancing" + elbv2 "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancingv2" + "github.com/aws/aws-sdk-go-v2/service/eventbridge" + rgapi "github.com/aws/aws-sdk-go-v2/service/resourcegroupstaggingapi" + "github.com/aws/aws-sdk-go-v2/service/s3" + "github.com/aws/aws-sdk-go-v2/service/secretsmanager" + "github.com/aws/aws-sdk-go-v2/service/sqs" + "github.com/aws/aws-sdk-go-v2/service/ssm" + "github.com/aws/aws-sdk-go-v2/service/sts" + smithyendpoints "github.com/aws/smithy-go/endpoints" - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/endpointsv2" - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/scope" + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/logger" ) var ( @@ -34,42 +45,30 @@ var ( errServiceEndpointURL = errors.New("must use a valid URL as a service-endpoint") errServiceEndpointServiceID = errors.New("must use a valid serviceID from the AWS GO SDK") errServiceEndpointDuplicateServiceID = errors.New("same serviceID defined twice for signing region") + serviceEndpointsMap = map[string]serviceEndpoint{} ) -func serviceEnum() []string { - var serviceIDs = []string{} - resolver := endpoints.DefaultResolver() - partitions := resolver.(endpoints.EnumPartitions).Partitions() - for _, p := range partitions { - for id := range p.Services() { - var add = true - for _, s := range serviceIDs { - if id == s { - add = false - } - } - if add { - serviceIDs = append(serviceIDs, id) - } - } - } - - return serviceIDs +// serviceEndpoint contains AWS Service resolution information for SDK V2. +type serviceEndpoint struct { + ServiceID string + URL string + SigningRegion string } // ParseFlag parses the command line flag of service endponts in the format ${SigningRegion1}:${ServiceID1}=${URL1},${ServiceID2}=${URL2}...;${SigningRegion2}... // returning a set of ServiceEndpoints. -func ParseFlag(serviceEndpoints string) ([]scope.ServiceEndpoint, error) { +func ParseFlag(serviceEndpoints string) error { if serviceEndpoints == "" { - return nil, nil + return nil } - serviceIDs := serviceEnum() + + // There is no Enum for serviceID in V2, so we will directly use the provided endpoint + // If the custom endpoint has any issue, EndpointResolverV2 falls back to default endpoint of specific service. signingRegionConfigs := strings.Split(serviceEndpoints, ";") - endpoints := []scope.ServiceEndpoint{} for _, regionConfig := range signingRegionConfigs { components := strings.SplitN(regionConfig, ":", 2) if len(components) != 2 { - return nil, errServiceEndpointSigningRegion + return errServiceEndpointSigningRegion } signingRegion := components[0] servicePairs := strings.Split(components[1], ",") @@ -77,63 +76,299 @@ func ParseFlag(serviceEndpoints string) ([]scope.ServiceEndpoint, error) { for _, servicePair := range servicePairs { kv := strings.Split(servicePair, "=") if len(kv) != 2 { - return nil, errServiceEndpointFormat - } - var serviceID = "" - for _, id := range serviceIDs { - if kv[0] == id { - serviceID = kv[0] - - break - } + return errServiceEndpointFormat } + serviceID := kv[0] if serviceID == "" { - return nil, errServiceEndpointServiceID + return errServiceEndpointServiceID } - if containsString(seenServices, serviceID) { - return nil, errServiceEndpointDuplicateServiceID + if slices.Contains(seenServices, serviceID) { + return errServiceEndpointDuplicateServiceID } seenServices = append(seenServices, serviceID) + + // convert service ID to UpperCase as service IDs in AWS SDK GO V2 are UpperCase & Go map is Case Sensitve + // This is for backward compabitibility + // Ref: SDK V2 https://pkg.go.dev/github.com/aws/aws-sdk-go-v2/service/ec2#pkg-constants + // Ref: SDK V1 https://pkg.go.dev/github.com/aws/aws-sdk-go/aws/endpoints#pkg-constants + serviceID = strings.ToUpper(serviceID) + URL, err := url.ParseRequestURI(kv[1]) if err != nil { - return nil, errServiceEndpointURL + return errServiceEndpointURL } - endpoints = append(endpoints, scope.ServiceEndpoint{ + endpoint := serviceEndpoint{ ServiceID: serviceID, URL: URL.String(), SigningRegion: signingRegion, - }) + } + serviceEndpointsMap[serviceID] = endpoint } } - // For Go SDK V2 migration - saveToServiceEndpointV2Map(endpoints) + return nil +} + +// GetPartitionFromRegion returns the cluster partition. +func GetPartitionFromRegion(region string) string { + if partition := GetPartition(region); partition != nil { + return partition.Name + } - return endpoints, nil + return defaultPartition } -func containsString(slice []string, s string) bool { - for _, item := range slice { - if item == s { - return true - } +// Custom EndpointResolverV2 ResolveEndpoint handlers. + +// MultiServiceEndpointResolver implements EndpointResolverV2 interface for services. +type MultiServiceEndpointResolver struct { + endpoints map[string]serviceEndpoint +} + +// NewMultiServiceEndpointResolver returns new MultiServiceEndpointResolver. +func NewMultiServiceEndpointResolver() *MultiServiceEndpointResolver { + return &MultiServiceEndpointResolver{ + endpoints: serviceEndpointsMap, } +} - return false -} - -// TODO: punkwalker - remove this after Go SDK V2 migration. -func saveToServiceEndpointV2Map(src []scope.ServiceEndpoint) { - for _, svc := range src { - // convert service ID to UpperCase as service IDs in AWS SDK GO V2 are UpperCase & Go map is Case Sensitve - // This is for backward compabitibility - // Ref: SDK V2 https://pkg.go.dev/github.com/aws/aws-sdk-go-v2/service/ec2#pkg-constants - // Ref: SDK V1 https://pkg.go.dev/github.com/aws/aws-sdk-go/aws/endpoints#pkg-constants - serviceID := strings.ToUpper(svc.ServiceID) - endpoint := endpointsv2.ServiceEndpoint{ - ServiceID: serviceID, - URL: svc.URL, - SigningRegion: svc.SigningRegion, - } - endpointsv2.ServiceEndpointsMap[svc.ServiceID] = endpoint +// S3EndpointResolver implements EndpointResolverV2 interface for S3. +type S3EndpointResolver struct { + *MultiServiceEndpointResolver +} + +// ResolveEndpoint for S3. +func (s *S3EndpointResolver) ResolveEndpoint(ctx context.Context, params s3.EndpointParameters) (smithyendpoints.Endpoint, error) { + // If custom endpoint not found, return default endpoint for the service + log := logger.FromContext(ctx) + endpoint, ok := s.endpoints[s3.ServiceID] + + if !ok { + log.Debug("Custom endpoint not found, using default endpoint") + return s3.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) + } + + log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) + params.Endpoint = &endpoint.URL + params.Region = &endpoint.SigningRegion + return s3.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) +} + +// ELBEndpointResolver implements EndpointResolverV2 interface for ELB. +type ELBEndpointResolver struct { + *MultiServiceEndpointResolver +} + +// ResolveEndpoint for ELB. +func (s *ELBEndpointResolver) ResolveEndpoint(ctx context.Context, params elb.EndpointParameters) (smithyendpoints.Endpoint, error) { + // If custom endpoint not found, return default endpoint for the service + log := logger.FromContext(ctx) + endpoint, ok := s.endpoints[elb.ServiceID] + + if !ok { + log.Debug("Custom endpoint not found, using default endpoint") + return elb.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) + } + + log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) + params.Endpoint = &endpoint.URL + params.Region = &endpoint.SigningRegion + return elb.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) +} + +// ELBV2EndpointResolver implements EndpointResolverV2 interface for ELBV2. +type ELBV2EndpointResolver struct { + *MultiServiceEndpointResolver +} + +// ResolveEndpoint for ELBV2. +func (s *ELBV2EndpointResolver) ResolveEndpoint(ctx context.Context, params elbv2.EndpointParameters) (smithyendpoints.Endpoint, error) { + // If custom endpoint not found, return default endpoint for the service + log := logger.FromContext(ctx) + endpoint, ok := s.endpoints[elbv2.ServiceID] + + if !ok { + log.Debug("Custom endpoint not found, using default endpoint") + return elbv2.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) + } + + log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) + params.Endpoint = &endpoint.URL + params.Region = &endpoint.SigningRegion + return elbv2.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) +} + +// EC2EndpointResolver implements EndpointResolverV2 interface for EC2. +type EC2EndpointResolver struct { + *MultiServiceEndpointResolver +} + +// ResolveEndpoint for ELBV2. +func (s *EC2EndpointResolver) ResolveEndpoint(ctx context.Context, params ec2.EndpointParameters) (smithyendpoints.Endpoint, error) { + // If custom endpoint not found, return default endpoint for the service + log := logger.FromContext(ctx) + endpoint, ok := s.endpoints[ec2.ServiceID] + + if !ok { + log.Debug("Custom endpoint not found, using default endpoint") + return ec2.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) + } + + log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) + params.Endpoint = &endpoint.URL + params.Region = &endpoint.SigningRegion + return ec2.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) +} + +// RGAPIEndpointResolver implements EndpointResolverV2 interface for RGAPI. +type RGAPIEndpointResolver struct { + *MultiServiceEndpointResolver +} + +// ResolveEndpoint for RGAPI. +func (s *RGAPIEndpointResolver) ResolveEndpoint(ctx context.Context, params rgapi.EndpointParameters) (smithyendpoints.Endpoint, error) { + // If custom endpoint not found, return default endpoint for the service + log := logger.FromContext(ctx) + endpoint, ok := s.endpoints[rgapi.ServiceID] + + if !ok { + log.Debug("Custom endpoint not found, using default endpoint") + return rgapi.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) + } + + log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) + params.Endpoint = &endpoint.URL + params.Region = &endpoint.SigningRegion + return rgapi.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) +} + +// SQSEndpointResolver implements EndpointResolverV2 interface for SQS. +type SQSEndpointResolver struct { + *MultiServiceEndpointResolver +} + +// ResolveEndpoint for SQS. +func (s *SQSEndpointResolver) ResolveEndpoint(ctx context.Context, params sqs.EndpointParameters) (smithyendpoints.Endpoint, error) { + // If custom endpoint not found, return default endpoint for the service + log := logger.FromContext(ctx) + endpoint, ok := s.endpoints[sqs.ServiceID] + + if !ok { + log.Debug("Custom endpoint not found, using default endpoint") + return sqs.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) + } + + log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) + params.Endpoint = &endpoint.URL + params.Region = &endpoint.SigningRegion + return sqs.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) +} + +// EventBridgeEndpointResolver implements EndpointResolverV2 interface for EventBridge. +type EventBridgeEndpointResolver struct { + *MultiServiceEndpointResolver +} + +// ResolveEndpoint for EventBridge. +func (s *EventBridgeEndpointResolver) ResolveEndpoint(ctx context.Context, params eventbridge.EndpointParameters) (smithyendpoints.Endpoint, error) { + // If custom endpoint not found, return default endpoint for the service + log := logger.FromContext(ctx) + endpoint, ok := s.endpoints[eventbridge.ServiceID] + + if !ok { + log.Debug("Custom endpoint not found, using default endpoint") + return eventbridge.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) } + + log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) + params.Endpoint = &endpoint.URL + params.Region = &endpoint.SigningRegion + return eventbridge.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) +} + +// EKSEndpointResolver implements EndpointResolverV2 interface for EKS. +type EKSEndpointResolver struct { + *MultiServiceEndpointResolver +} + +// ResolveEndpoint for EKS. +func (s *EKSEndpointResolver) ResolveEndpoint(ctx context.Context, params eks.EndpointParameters) (smithyendpoints.Endpoint, error) { + // If custom endpoint not found, return default endpoint for the service + log := logger.FromContext(ctx) + endpoint, ok := s.endpoints[eks.ServiceID] + + if !ok { + log.Debug("Custom endpoint not found, using default endpoint") + return eks.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) + } + + log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) + params.Endpoint = &endpoint.URL + params.Region = &endpoint.SigningRegion + return eks.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) +} + +// SSMEndpointResolver implements EndpointResolverV2 interface for SSM. +type SSMEndpointResolver struct { + *MultiServiceEndpointResolver +} + +// ResolveEndpoint for SSM. +func (s *SSMEndpointResolver) ResolveEndpoint(ctx context.Context, params ssm.EndpointParameters) (smithyendpoints.Endpoint, error) { + // If custom endpoint not found, return default endpoint for the service + log := logger.FromContext(ctx) + endpoint, ok := s.endpoints[ssm.ServiceID] + + if !ok { + log.Debug("Custom endpoint not found, using default endpoint") + return ssm.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) + } + + log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) + params.Endpoint = &endpoint.URL + params.Region = &endpoint.SigningRegion + return ssm.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) +} + +// STSEndpointResolver implements EndpointResolverV2 interface for STS. +type STSEndpointResolver struct { + *MultiServiceEndpointResolver +} + +// ResolveEndpoint for STS. +func (s *STSEndpointResolver) ResolveEndpoint(ctx context.Context, params sts.EndpointParameters) (smithyendpoints.Endpoint, error) { + // If custom endpoint not found, return default endpoint for the service + log := logger.FromContext(ctx) + endpoint, ok := s.endpoints[sts.ServiceID] + + if !ok { + log.Debug("Custom endpoint not found, using default endpoint") + return sts.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) + } + + log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) + params.Endpoint = &endpoint.URL + params.Region = &endpoint.SigningRegion + return sts.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) +} + +// SecretsManagerEndpointResolver implements EndpointResolverV2 interface for Secrets Manager. +type SecretsManagerEndpointResolver struct { + *MultiServiceEndpointResolver +} + +// ResolveEndpoint for Secrets Manager. +func (s *SecretsManagerEndpointResolver) ResolveEndpoint(ctx context.Context, params secretsmanager.EndpointParameters) (smithyendpoints.Endpoint, error) { + // If custom endpoint not found, return default endpoint for the service + log := logger.FromContext(ctx) + endpoint, ok := s.endpoints[secretsmanager.ServiceID] + + if !ok { + log.Debug("Custom endpoint not found, using default endpoint") + return secretsmanager.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) + } + + log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) + params.Endpoint = &endpoint.URL + params.Region = &endpoint.SigningRegion + return secretsmanager.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) } diff --git a/pkg/cloud/endpoints/endpoints_test.go b/pkg/cloud/endpoints/endpoints_test.go index 58261f8023..42d368100f 100644 --- a/pkg/cloud/endpoints/endpoints_test.go +++ b/pkg/cloud/endpoints/endpoints_test.go @@ -19,123 +19,107 @@ package endpoints import ( "errors" "testing" - - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/scope" ) func TestParseFlags(t *testing.T) { testCases := []struct { - name string - flagToParse string - expectedOutput []scope.ServiceEndpoint - expectedError error + name string + flagToParse string + expectedError error }{ { - name: "no configuration", - flagToParse: "", - expectedOutput: nil, - expectedError: nil, + name: "no configuration", + flagToParse: "", + expectedError: nil, }, { - name: "single region, single service", - flagToParse: "us-iso:ec2=https://localhost:8080", - expectedOutput: []scope.ServiceEndpoint{ - { - ServiceID: "ec2", - URL: "https://localhost:8080", - SigningRegion: "us-iso", - }, - }, + name: "single region, single service", + flagToParse: "us-iso:ec2=https://localhost:8080", expectedError: nil, }, { - name: "single region, multiple services", - flagToParse: "us-iso:ec2=https://localhost:8080,sts=https://elbhost:8080", - expectedOutput: []scope.ServiceEndpoint{ - { - ServiceID: "ec2", - URL: "https://localhost:8080", - SigningRegion: "us-iso", - }, - { - ServiceID: "sts", - URL: "https://elbhost:8080", - SigningRegion: "us-iso", - }, - }, + name: "single region, multiple services", + flagToParse: "us-iso:ec2=https://localhost:8080,sts=https://elbhost:8080", expectedError: nil, }, { - name: "single region, duplicate service", - flagToParse: "us-iso:ec2=https://localhost:8080,ec2=https://elbhost:8080", - expectedOutput: nil, - expectedError: errServiceEndpointDuplicateServiceID, + name: "single region, duplicate service", + flagToParse: "us-iso:ec2=https://localhost:8080,ec2=https://elbhost:8080", + expectedError: errServiceEndpointDuplicateServiceID, }, { - name: "single region, non-valid URI", - flagToParse: "us-iso:ec2=fdsfs", - expectedOutput: nil, - expectedError: errServiceEndpointURL, + name: "single region, non-valid URI", + flagToParse: "us-iso:ec2=fdsfs", + expectedError: errServiceEndpointURL, }, { - name: "multiples regions", - flagToParse: "us-iso:ec2=https://localhost:8080,sts=https://elbhost:8080;gb-iso:ec2=https://localhost:8080,sts=https://elbhost:8080", - expectedOutput: []scope.ServiceEndpoint{ - { - ServiceID: "ec2", - URL: "https://localhost:8080", - SigningRegion: "us-iso", - }, - { - ServiceID: "sts", - URL: "https://elbhost:8080", - SigningRegion: "us-iso", - }, - { - ServiceID: "ec2", - URL: "https://localhost:8080", - SigningRegion: "gb-iso", - }, - { - ServiceID: "sts", - URL: "https://elbhost:8080", - SigningRegion: "gb-iso", - }, - }, + name: "multiples regions", + flagToParse: "us-iso:ec2=https://localhost:8080,sts=https://elbhost:8080;gb-iso:ec2=https://localhost:8080,sts=https://elbhost:8080", expectedError: nil, }, { - name: "invalid config", - flagToParse: "us-isoec2=localhost", - expectedOutput: nil, - expectedError: errServiceEndpointSigningRegion, + name: "invalid config", + flagToParse: "us-isoec2=localhost", + expectedError: errServiceEndpointSigningRegion, }, } for _, tc := range testCases { t.Run(tc.name, func(t *testing.T) { - out, err := ParseFlag(tc.flagToParse) + err := ParseFlag(tc.flagToParse) if !errors.Is(err, tc.expectedError) { t.Fatalf("did not expect correct error: got %v, expected %v", err, tc.expectedError) } - - if !endpointsEqual(out, tc.expectedOutput) { - t.Fatalf("did not expect correct output: got %v, expected %v", out, tc.expectedOutput) - } }) } } -func endpointsEqual(a, b []scope.ServiceEndpoint) bool { - if len(a) != len(b) { - return false +func TestGetPartitionFromRegion(t *testing.T) { + testCases := []struct { + name string + region string + expectedValue string + }{ + { + name: "should return gov partition", + region: "us-gov-east-1", + expectedValue: "aws-us-gov", + }, + { + name: "should return cn partition", + region: "cn-north-1", + expectedValue: "aws-cn", + }, + { + name: "should return iso partition", + region: "us-iso-east-1", + expectedValue: "aws-iso", + }, + { + name: "should return iso-b partition", + region: "us-isob-east-1", + expectedValue: "aws-iso-b", + }, + { + name: "should return default partition for valid region", + region: "us-west-2", + expectedValue: "aws", + }, + { + name: "should return default partition for invalid region", + region: "us-west-3", + expectedValue: "aws", + }, } - for i, v := range a { - if v != b[i] { - return false - } + for _, tc := range testCases { + t.Run(tc.name, func(t *testing.T) { + value := GetPartitionFromRegion(tc.region) + + if value != tc.expectedValue { + t.Fatalf("did not get expected value: got %v, expected %v", value, tc.expectedValue) + } + }) } - return true } diff --git a/pkg/cloud/endpoints/partition.go b/pkg/cloud/endpoints/partition.go new file mode 100644 index 0000000000..b90cb3f2ed --- /dev/null +++ b/pkg/cloud/endpoints/partition.go @@ -0,0 +1,103 @@ +/* +Copyright 2025 The Kubernetes Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +/* +Copied from AWS SDK GO V2 and modified the package names as needed +This file shoud be updated with SDK verson bump if there change in this file. +Ref: https://github.com/aws/aws-sdk-go-v2/blob/main/internal/endpoints/awsrulesfn/partition.go +*/ + +package endpoints + +import "regexp" + +// Partition provides the metadata describing an AWS partition. +type Partition struct { + ID string `json:"id"` + Regions map[string]RegionOverrides `json:"regions"` + RegionRegex string `json:"regionRegex"` + DefaultConfig PartitionConfig `json:"outputs"` +} + +// PartitionConfig provides the endpoint metadata for an AWS region or partition. +// +//nolint:revive +type PartitionConfig struct { + Name string `json:"name"` + DnsSuffix string `json:"dnsSuffix"` + DualStackDnsSuffix string `json:"dualStackDnsSuffix"` + SupportsFIPS bool `json:"supportsFIPS"` + SupportsDualStack bool `json:"supportsDualStack"` + ImplicitGlobalRegion string `json:"implicitGlobalRegion"` +} + +// RegionOverrides provides the custom override for an AWS region. +// +//nolint:revive +type RegionOverrides struct { + Name *string `json:"name"` + DnsSuffix *string `json:"dnsSuffix"` + DualStackDnsSuffix *string `json:"dualStackDnsSuffix"` + SupportsFIPS *bool `json:"supportsFIPS"` + SupportsDualStack *bool `json:"supportsDualStack"` +} + +const defaultPartition = "aws" + +func getPartition(partitions []Partition, region string) *PartitionConfig { + for _, partition := range partitions { + if v, ok := partition.Regions[region]; ok { + p := mergeOverrides(partition.DefaultConfig, v) + return &p + } + } + + for _, partition := range partitions { + regionRegex := regexp.MustCompile(partition.RegionRegex) + if regionRegex.MatchString(region) { + v := partition.DefaultConfig + return &v + } + } + + for _, partition := range partitions { + if partition.ID == defaultPartition { + v := partition.DefaultConfig + return &v + } + } + + return nil +} + +func mergeOverrides(into PartitionConfig, from RegionOverrides) PartitionConfig { + if from.Name != nil { + into.Name = *from.Name + } + if from.DnsSuffix != nil { + into.DnsSuffix = *from.DnsSuffix + } + if from.DualStackDnsSuffix != nil { + into.DualStackDnsSuffix = *from.DualStackDnsSuffix + } + if from.SupportsFIPS != nil { + into.SupportsFIPS = *from.SupportsFIPS + } + if from.SupportsDualStack != nil { + into.SupportsDualStack = *from.SupportsDualStack + } + return into +} diff --git a/pkg/cloud/endpoints/partitions.go b/pkg/cloud/endpoints/partitions.go new file mode 100644 index 0000000000..65ff2f0d6a --- /dev/null +++ b/pkg/cloud/endpoints/partitions.go @@ -0,0 +1,498 @@ +/* +Copyright The Kubernetes Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by pkg/cloud/endpoints/codegen.go DO NOT EDIT. + +package endpoints + + +// GetPartition returns an AWS [Partition] for the region provided. If the +// partition cannot be determined nil will be returned. +func GetPartition(region string) *PartitionConfig { + return getPartition(partitions, region) +} + +var partitions = []Partition { + Partition { + ID: "aws", + RegionRegex: "^(us|eu|ap|sa|ca|me|af|il|mx)\\-\\w+\\-\\d+$", + DefaultConfig: PartitionConfig{ + Name: "aws", + DnsSuffix: "amazonaws.com", + DualStackDnsSuffix: "api.aws", + SupportsFIPS: true, + SupportsDualStack: true, + ImplicitGlobalRegion: "us-east-1", + }, + Regions: map[string]RegionOverrides { + "af-south-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ap-east-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ap-east-2": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ap-northeast-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ap-northeast-2": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ap-northeast-3": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ap-south-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ap-south-2": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ap-southeast-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ap-southeast-2": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ap-southeast-3": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ap-southeast-4": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ap-southeast-5": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ap-southeast-7": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "aws-global": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ca-central-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "ca-west-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "eu-central-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "eu-central-2": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "eu-north-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "eu-south-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "eu-south-2": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "eu-west-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "eu-west-2": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "eu-west-3": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "il-central-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "me-central-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "me-south-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "mx-central-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "sa-east-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "us-east-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "us-east-2": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "us-west-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "us-west-2": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + }, + }, + Partition { + ID: "aws-cn", + RegionRegex: "^cn\\-\\w+\\-\\d+$", + DefaultConfig: PartitionConfig{ + Name: "aws-cn", + DnsSuffix: "amazonaws.com.cn", + DualStackDnsSuffix: "api.amazonwebservices.com.cn", + SupportsFIPS: true, + SupportsDualStack: true, + ImplicitGlobalRegion: "cn-northwest-1", + }, + Regions: map[string]RegionOverrides { + "aws-cn-global": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "cn-north-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "cn-northwest-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + }, + }, + Partition { + ID: "aws-us-gov", + RegionRegex: "^us\\-gov\\-\\w+\\-\\d+$", + DefaultConfig: PartitionConfig{ + Name: "aws-us-gov", + DnsSuffix: "amazonaws.com", + DualStackDnsSuffix: "api.aws", + SupportsFIPS: true, + SupportsDualStack: true, + ImplicitGlobalRegion: "us-gov-west-1", + }, + Regions: map[string]RegionOverrides { + "aws-us-gov-global": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "us-gov-east-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "us-gov-west-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + }, + }, + Partition { + ID: "aws-iso", + RegionRegex: "^us\\-iso\\-\\w+\\-\\d+$", + DefaultConfig: PartitionConfig{ + Name: "aws-iso", + DnsSuffix: "c2s.ic.gov", + DualStackDnsSuffix: "c2s.ic.gov", + SupportsFIPS: true, + SupportsDualStack: false, + ImplicitGlobalRegion: "us-iso-east-1", + }, + Regions: map[string]RegionOverrides { + "aws-iso-global": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "us-iso-east-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "us-iso-west-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + }, + }, + Partition { + ID: "aws-iso-b", + RegionRegex: "^us\\-isob\\-\\w+\\-\\d+$", + DefaultConfig: PartitionConfig{ + Name: "aws-iso-b", + DnsSuffix: "sc2s.sgov.gov", + DualStackDnsSuffix: "sc2s.sgov.gov", + SupportsFIPS: true, + SupportsDualStack: false, + ImplicitGlobalRegion: "us-isob-east-1", + }, + Regions: map[string]RegionOverrides { + "aws-iso-b-global": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "us-isob-east-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + }, + }, + Partition { + ID: "aws-iso-e", + RegionRegex: "^eu\\-isoe\\-\\w+\\-\\d+$", + DefaultConfig: PartitionConfig{ + Name: "aws-iso-e", + DnsSuffix: "cloud.adc-e.uk", + DualStackDnsSuffix: "cloud.adc-e.uk", + SupportsFIPS: true, + SupportsDualStack: false, + ImplicitGlobalRegion: "eu-isoe-west-1", + }, + Regions: map[string]RegionOverrides { + "aws-iso-e-global": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "eu-isoe-west-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + }, + }, + Partition { + ID: "aws-iso-f", + RegionRegex: "^us\\-isof\\-\\w+\\-\\d+$", + DefaultConfig: PartitionConfig{ + Name: "aws-iso-f", + DnsSuffix: "csp.hci.ic.gov", + DualStackDnsSuffix: "csp.hci.ic.gov", + SupportsFIPS: true, + SupportsDualStack: false, + ImplicitGlobalRegion: "us-isof-south-1", + }, + Regions: map[string]RegionOverrides { + "aws-iso-f-global": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "us-isof-east-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + "us-isof-south-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + }, + }, + Partition { + ID: "aws-eusc", + RegionRegex: "^eusc\\-(de)\\-\\w+\\-\\d+$", + DefaultConfig: PartitionConfig{ + Name: "aws-eusc", + DnsSuffix: "amazonaws.eu", + DualStackDnsSuffix: "amazonaws.eu", + SupportsFIPS: true, + SupportsDualStack: false, + ImplicitGlobalRegion: "eusc-de-east-1", + }, + Regions: map[string]RegionOverrides { + "eusc-de-east-1": RegionOverrides{ + Name: nil, + DnsSuffix: nil, + DualStackDnsSuffix: nil, + SupportsFIPS: nil, + SupportsDualStack: nil, + }, + }, + }, +} diff --git a/pkg/cloud/endpointsv2/endpoints.go b/pkg/cloud/endpointsv2/endpoints.go deleted file mode 100644 index 4c92e9084f..0000000000 --- a/pkg/cloud/endpointsv2/endpoints.go +++ /dev/null @@ -1,351 +0,0 @@ -/* -Copyright 2025 The Kubernetes Authors. - -Licensed under the Apache License, Version 2.0 (the "License"); -you may not use this file except in compliance with the License. -You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - -Unless required by applicable law or agreed to in writing, software -distributed under the License is distributed on an "AS IS" BASIS, -WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -See the License for the specific language governing permissions and -limitations under the License. -*/ - -// Package endpointsv2 contains aws endpoint related utilities. -package endpointsv2 - -import ( - "context" - "errors" - "net/url" - "strings" - - "github.com/aws/aws-sdk-go-v2/service/ec2" - "github.com/aws/aws-sdk-go-v2/service/eks" - elb "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancing" - elbv2 "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancingv2" - "github.com/aws/aws-sdk-go-v2/service/eventbridge" - rgapi "github.com/aws/aws-sdk-go-v2/service/resourcegroupstaggingapi" - "github.com/aws/aws-sdk-go-v2/service/s3" - "github.com/aws/aws-sdk-go-v2/service/secretsmanager" - "github.com/aws/aws-sdk-go-v2/service/sqs" - "github.com/aws/aws-sdk-go-v2/service/ssm" - "github.com/aws/aws-sdk-go-v2/service/sts" - smithyendpoints "github.com/aws/smithy-go/endpoints" - - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/logger" -) - -var ( - errServiceEndpointFormat = errors.New("must be formatted as ${ServiceID}=${URL}") - errServiceEndpointSigningRegion = errors.New("must be formatted as ${SigningRegion}:${ServiceID1}=${URL1},${ServiceID2}=${URL2...}") - errServiceEndpointURL = errors.New("must use a valid URL as a service-endpoint") - errServiceEndpointDuplicateServiceID = errors.New("same serviceID defined twice for signing region") - // ServiceEndpointsMap Can be made private after Go SDK V2 migration. - ServiceEndpointsMap = map[string]ServiceEndpoint{} -) - -// ServiceEndpoint contains AWS Service resolution information for SDK V2. -type ServiceEndpoint struct { - ServiceID string - URL string - SigningRegion string -} - -// ParseFlag parses the command line flag of service endponts in the format ${SigningRegion1}:${ServiceID1}=${URL1},${ServiceID2}=${URL2}...;${SigningRegion2}... -// returning a set of ServiceEndpoints. -func ParseFlag(serviceEndpoints string) error { - if serviceEndpoints == "" { - return nil - } - - signingRegionConfigs := strings.Split(serviceEndpoints, ";") - for _, regionConfig := range signingRegionConfigs { - components := strings.SplitN(regionConfig, ":", 2) - if len(components) != 2 { - return errServiceEndpointSigningRegion - } - signingRegion := components[0] - servicePairs := strings.Split(components[1], ",") - for _, servicePair := range servicePairs { - kv := strings.Split(servicePair, "=") - if len(kv) != 2 { - return errServiceEndpointFormat - } - var serviceID = kv[0] - if _, ok := ServiceEndpointsMap[serviceID]; ok { - return errServiceEndpointDuplicateServiceID - } - - URL, err := url.ParseRequestURI(kv[1]) - if err != nil { - return errServiceEndpointURL - } - ServiceEndpointsMap[serviceID] = ServiceEndpoint{ - ServiceID: serviceID, - URL: URL.String(), - SigningRegion: signingRegion, - } - } - } - return nil -} - -// Custom EndpointResolverV2 ResolveEndpoint handlers. - -// MultiServiceEndpointResolver implements EndpointResolverV2 interface for services. -type MultiServiceEndpointResolver struct { - endpoints map[string]ServiceEndpoint -} - -// NewMultiServiceEndpointResolver returns new MultiServiceEndpointResolver. -func NewMultiServiceEndpointResolver() *MultiServiceEndpointResolver { - return &MultiServiceEndpointResolver{ - endpoints: ServiceEndpointsMap, - } -} - -// S3EndpointResolver implements EndpointResolverV2 interface for S3. -type S3EndpointResolver struct { - *MultiServiceEndpointResolver -} - -// ResolveEndpoint for S3. -func (s *S3EndpointResolver) ResolveEndpoint(ctx context.Context, params s3.EndpointParameters) (smithyendpoints.Endpoint, error) { - // If custom endpoint not found, return default endpoint for the service - log := logger.FromContext(ctx) - endpoint, ok := s.endpoints[s3.ServiceID] - - if !ok { - log.Debug("Custom endpoint not found, using default endpoint") - return s3.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) - } - - log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) - params.Endpoint = &endpoint.URL - params.Region = &endpoint.SigningRegion - return s3.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) -} - -// ELBEndpointResolver implements EndpointResolverV2 interface for ELB. -type ELBEndpointResolver struct { - *MultiServiceEndpointResolver -} - -// ResolveEndpoint for ELB. -func (s *ELBEndpointResolver) ResolveEndpoint(ctx context.Context, params elb.EndpointParameters) (smithyendpoints.Endpoint, error) { - // If custom endpoint not found, return default endpoint for the service - log := logger.FromContext(ctx) - endpoint, ok := s.endpoints[elb.ServiceID] - - if !ok { - log.Debug("Custom endpoint not found, using default endpoint") - return elb.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) - } - - log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) - params.Endpoint = &endpoint.URL - params.Region = &endpoint.SigningRegion - return elb.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) -} - -// ELBV2EndpointResolver implements EndpointResolverV2 interface for ELBV2. -type ELBV2EndpointResolver struct { - *MultiServiceEndpointResolver -} - -// ResolveEndpoint for ELBV2. -func (s *ELBV2EndpointResolver) ResolveEndpoint(ctx context.Context, params elbv2.EndpointParameters) (smithyendpoints.Endpoint, error) { - // If custom endpoint not found, return default endpoint for the service - log := logger.FromContext(ctx) - endpoint, ok := s.endpoints[elbv2.ServiceID] - - if !ok { - log.Debug("Custom endpoint not found, using default endpoint") - return elbv2.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) - } - - log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) - params.Endpoint = &endpoint.URL - params.Region = &endpoint.SigningRegion - return elbv2.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) -} - -// EC2EndpointResolver implements EndpointResolverV2 interface for EC2. -type EC2EndpointResolver struct { - *MultiServiceEndpointResolver -} - -// ResolveEndpoint for ELBV2. -func (s *EC2EndpointResolver) ResolveEndpoint(ctx context.Context, params ec2.EndpointParameters) (smithyendpoints.Endpoint, error) { - // If custom endpoint not found, return default endpoint for the service - log := logger.FromContext(ctx) - endpoint, ok := s.endpoints[ec2.ServiceID] - - if !ok { - log.Debug("Custom endpoint not found, using default endpoint") - return ec2.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) - } - - log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) - params.Endpoint = &endpoint.URL - params.Region = &endpoint.SigningRegion - return ec2.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) -} - -// RGAPIEndpointResolver implements EndpointResolverV2 interface for RGAPI. -type RGAPIEndpointResolver struct { - *MultiServiceEndpointResolver -} - -// ResolveEndpoint for RGAPI. -func (s *RGAPIEndpointResolver) ResolveEndpoint(ctx context.Context, params rgapi.EndpointParameters) (smithyendpoints.Endpoint, error) { - // If custom endpoint not found, return default endpoint for the service - log := logger.FromContext(ctx) - endpoint, ok := s.endpoints[rgapi.ServiceID] - - if !ok { - log.Debug("Custom endpoint not found, using default endpoint") - return rgapi.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) - } - - log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) - params.Endpoint = &endpoint.URL - params.Region = &endpoint.SigningRegion - return rgapi.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) -} - -// SQSEndpointResolver implements EndpointResolverV2 interface for SQS. -type SQSEndpointResolver struct { - *MultiServiceEndpointResolver -} - -// ResolveEndpoint for SQS. -func (s *SQSEndpointResolver) ResolveEndpoint(ctx context.Context, params sqs.EndpointParameters) (smithyendpoints.Endpoint, error) { - // If custom endpoint not found, return default endpoint for the service - log := logger.FromContext(ctx) - endpoint, ok := s.endpoints[sqs.ServiceID] - - if !ok { - log.Debug("Custom endpoint not found, using default endpoint") - return sqs.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) - } - - log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) - params.Endpoint = &endpoint.URL - params.Region = &endpoint.SigningRegion - return sqs.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) -} - -// EventBridgeEndpointResolver implements EndpointResolverV2 interface for EventBridge. -type EventBridgeEndpointResolver struct { - *MultiServiceEndpointResolver -} - -// ResolveEndpoint for EventBridge. -func (s *EventBridgeEndpointResolver) ResolveEndpoint(ctx context.Context, params eventbridge.EndpointParameters) (smithyendpoints.Endpoint, error) { - // If custom endpoint not found, return default endpoint for the service - log := logger.FromContext(ctx) - endpoint, ok := s.endpoints[eventbridge.ServiceID] - - if !ok { - log.Debug("Custom endpoint not found, using default endpoint") - return eventbridge.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) - } - - log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) - params.Endpoint = &endpoint.URL - params.Region = &endpoint.SigningRegion - return eventbridge.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) -} - -// EKSEndpointResolver implements EndpointResolverV2 interface for EKS. -type EKSEndpointResolver struct { - *MultiServiceEndpointResolver -} - -// ResolveEndpoint for EKS. -func (s *EKSEndpointResolver) ResolveEndpoint(ctx context.Context, params eks.EndpointParameters) (smithyendpoints.Endpoint, error) { - // If custom endpoint not found, return default endpoint for the service - log := logger.FromContext(ctx) - endpoint, ok := s.endpoints[eks.ServiceID] - - if !ok { - log.Debug("Custom endpoint not found, using default endpoint") - return eks.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) - } - - log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) - params.Endpoint = &endpoint.URL - params.Region = &endpoint.SigningRegion - return eks.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) -} - -// SSMEndpointResolver implements EndpointResolverV2 interface for SSM. -type SSMEndpointResolver struct { - *MultiServiceEndpointResolver -} - -// ResolveEndpoint for SSM. -func (s *SSMEndpointResolver) ResolveEndpoint(ctx context.Context, params ssm.EndpointParameters) (smithyendpoints.Endpoint, error) { - // If custom endpoint not found, return default endpoint for the service - log := logger.FromContext(ctx) - endpoint, ok := s.endpoints[ssm.ServiceID] - - if !ok { - log.Debug("Custom endpoint not found, using default endpoint") - return ssm.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) - } - - log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) - params.Endpoint = &endpoint.URL - params.Region = &endpoint.SigningRegion - return ssm.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) -} - -// STSEndpointResolver implements EndpointResolverV2 interface for STS. -type STSEndpointResolver struct { - *MultiServiceEndpointResolver -} - -// ResolveEndpoint for STS. -func (s *STSEndpointResolver) ResolveEndpoint(ctx context.Context, params sts.EndpointParameters) (smithyendpoints.Endpoint, error) { - // If custom endpoint not found, return default endpoint for the service - log := logger.FromContext(ctx) - endpoint, ok := s.endpoints[sts.ServiceID] - - if !ok { - log.Debug("Custom endpoint not found, using default endpoint") - return sts.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) - } - - log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) - params.Endpoint = &endpoint.URL - params.Region = &endpoint.SigningRegion - return sts.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) -} - -// SecretsManagerEndpointResolver implements EndpointResolverV2 interface for Secrets Manager. -type SecretsManagerEndpointResolver struct { - *MultiServiceEndpointResolver -} - -// ResolveEndpoint for Secrets Manager. -func (s *SecretsManagerEndpointResolver) ResolveEndpoint(ctx context.Context, params secretsmanager.EndpointParameters) (smithyendpoints.Endpoint, error) { - // If custom endpoint not found, return default endpoint for the service - log := logger.FromContext(ctx) - endpoint, ok := s.endpoints[secretsmanager.ServiceID] - - if !ok { - log.Debug("Custom endpoint not found, using default endpoint") - return secretsmanager.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) - } - - log.Debug("Custom endpoint found, using custom endpoint", "endpoint", endpoint.URL) - params.Endpoint = &endpoint.URL - params.Region = &endpoint.SigningRegion - return secretsmanager.NewDefaultEndpointResolverV2().ResolveEndpoint(ctx, params) -} diff --git a/pkg/cloud/filter/ec2.go b/pkg/cloud/filter/ec2.go index dd62611909..47a6c39705 100644 --- a/pkg/cloud/filter/ec2.go +++ b/pkg/cloud/filter/ec2.go @@ -19,8 +19,8 @@ package filter import ( "fmt" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" ) diff --git a/pkg/cloud/identity/identity.go b/pkg/cloud/identity/identity.go index 18e77bf293..0d92d891b3 100644 --- a/pkg/cloud/identity/identity.go +++ b/pkg/cloud/identity/identity.go @@ -1,11 +1,11 @@ /* -Copyright 2021 The Kubernetes Authors. +Copyright 2025 The Kubernetes Authors. Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at - http://www.apache.org/licenses/LICENSE-2.0 + http://www.apache.org/licenses/LICENSE-2.0 Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, @@ -19,25 +19,28 @@ package identity import ( "bytes" + "context" "crypto/sha256" "encoding/gob" "time" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/credentials" - "github.com/aws/aws-sdk-go/aws/credentials/stscreds" - "github.com/aws/aws-sdk-go/aws/session" - "github.com/aws/aws-sdk-go/service/sts/stsiface" + "github.com/aws/aws-sdk-go-v2/aws" + "github.com/aws/aws-sdk-go-v2/config" + "github.com/aws/aws-sdk-go-v2/credentials" + "github.com/aws/aws-sdk-go-v2/credentials/stscreds" + "github.com/aws/aws-sdk-go-v2/service/sts" corev1 "k8s.io/api/core/v1" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" + awsmetrics "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/metrics" + stsservice "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/services/sts" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/logger" ) // AWSPrincipalTypeProvider defines the interface for AWS Principal Type Provider. type AWSPrincipalTypeProvider interface { - credentials.Provider - // Hash returns a unique hash of the data forming the credentials + aws.CredentialsProvider + // Hash returns a unique hash of the data forming the V2 credentials // for this Principal Hash() (string, error) Name() string @@ -49,34 +52,44 @@ func NewAWSStaticPrincipalTypeProvider(identity *infrav1.AWSClusterStaticIdentit secretAccessKey := string(secret.Data["SecretAccessKey"]) sessionToken := string(secret.Data["SessionToken"]) + credProvider := credentials.NewStaticCredentialsProvider(accessKeyID, secretAccessKey, sessionToken) + credCache := aws.NewCredentialsCache(credProvider) return &AWSStaticPrincipalTypeProvider{ Principal: identity, - credentials: credentials.NewStaticCredentials(accessKeyID, secretAccessKey, sessionToken), + credentials: credCache, AccessKeyID: accessKeyID, SecretAccessKey: secretAccessKey, SessionToken: sessionToken, } } -// GetAssumeRoleCredentials will return the Credentials of a given AWSRolePrincipalTypeProvider. -func GetAssumeRoleCredentials(roleIdentityProvider *AWSRolePrincipalTypeProvider, awsConfig *aws.Config) *credentials.Credentials { - sess := session.Must(session.NewSession(awsConfig)) +// GetAssumeRoleCredentialsCache will return the CredentialsCache of a given AWSRolePrincipalTypeProvider. +func GetAssumeRoleCredentialsCache(ctx context.Context, roleIdentityProvider *AWSRolePrincipalTypeProvider, optFns []func(*config.LoadOptions) error) (*aws.CredentialsCache, error) { + cfg, err := config.LoadDefaultConfig(ctx, optFns...) + if err != nil { + return nil, err + } - creds := stscreds.NewCredentials(sess, roleIdentityProvider.Principal.Spec.RoleArn, func(p *stscreds.AssumeRoleProvider) { + stsOpts := sts.WithAPIOptions( + awsmetrics.WithMiddlewares("identity provider", roleIdentityProvider.Principal), + awsmetrics.WithCAPAUserAgentMiddleware()) + stsClient := sts.NewFromConfig(cfg, stsOpts) + credsProvider := stscreds.NewAssumeRoleProvider(stsClient, roleIdentityProvider.Principal.Spec.RoleArn, func(o *stscreds.AssumeRoleOptions) { if roleIdentityProvider.Principal.Spec.ExternalID != "" { - p.ExternalID = aws.String(roleIdentityProvider.Principal.Spec.ExternalID) + o.ExternalID = aws.String(roleIdentityProvider.Principal.Spec.ExternalID) } - p.RoleSessionName = roleIdentityProvider.Principal.Spec.SessionName + o.RoleSessionName = roleIdentityProvider.Principal.Spec.SessionName if roleIdentityProvider.Principal.Spec.InlinePolicy != "" { - p.Policy = aws.String(roleIdentityProvider.Principal.Spec.InlinePolicy) + o.Policy = aws.String(roleIdentityProvider.Principal.Spec.InlinePolicy) } - p.Duration = time.Duration(roleIdentityProvider.Principal.Spec.DurationSeconds) * time.Second + o.Duration = time.Duration(roleIdentityProvider.Principal.Spec.DurationSeconds) * time.Second // For testing if roleIdentityProvider.stsClient != nil { - p.Client = roleIdentityProvider.stsClient + o.Client = roleIdentityProvider.stsClient } }) - return creds + + return aws.NewCredentialsCache(credsProvider), nil } // NewAWSRolePrincipalTypeProvider will create a new AWSRolePrincipalTypeProvider from an AWSClusterRoleIdentity. @@ -94,7 +107,7 @@ func NewAWSRolePrincipalTypeProvider(identity *infrav1.AWSClusterRoleIdentity, s // AWSStaticPrincipalTypeProvider defines the specs for a static AWSPrincipalTypeProvider. type AWSStaticPrincipalTypeProvider struct { Principal *infrav1.AWSClusterStaticIdentity - credentials *credentials.Credentials + credentials *aws.CredentialsCache // these are for tests :/ AccessKeyID string SecretAccessKey string @@ -113,8 +126,8 @@ func (p *AWSStaticPrincipalTypeProvider) Hash() (string, error) { } // Retrieve returns the credential values for the AWSStaticPrincipalTypeProvider. -func (p *AWSStaticPrincipalTypeProvider) Retrieve() (credentials.Value, error) { - return p.credentials.Get() +func (p *AWSStaticPrincipalTypeProvider) Retrieve(ctx context.Context) (aws.Credentials, error) { + return p.credentials.Retrieve(ctx) } // Name returns the name of the AWSStaticPrincipalTypeProvider. @@ -122,19 +135,14 @@ func (p *AWSStaticPrincipalTypeProvider) Name() string { return p.Principal.Name } -// IsExpired checks the expiration state of the AWSStaticPrincipalTypeProvider. -func (p *AWSStaticPrincipalTypeProvider) IsExpired() bool { - return p.credentials.IsExpired() -} - // AWSRolePrincipalTypeProvider defines the specs for a AWSPrincipalTypeProvider with a role. type AWSRolePrincipalTypeProvider struct { Principal *infrav1.AWSClusterRoleIdentity - credentials *credentials.Credentials + credentials *aws.CredentialsCache region string sourceProvider AWSPrincipalTypeProvider log logger.Wrapper - stsClient stsiface.STSAPI + stsClient stsservice.STSClient } // Hash returns the byte encoded AWSRolePrincipalTypeProvider. @@ -154,25 +162,23 @@ func (p *AWSRolePrincipalTypeProvider) Name() string { } // Retrieve returns the credential values for the AWSRolePrincipalTypeProvider. -func (p *AWSRolePrincipalTypeProvider) Retrieve() (credentials.Value, error) { - if p.credentials == nil || p.IsExpired() { - awsConfig := aws.NewConfig().WithRegion(p.region) +func (p *AWSRolePrincipalTypeProvider) Retrieve(ctx context.Context) (aws.Credentials, error) { + if p.credentials == nil { + optFns := []func(*config.LoadOptions) error{config.WithRegion(p.region)} if p.sourceProvider != nil { - sourceCreds, err := p.sourceProvider.Retrieve() + sourceCreds, err := p.sourceProvider.Retrieve(ctx) if err != nil { - return credentials.Value{}, err + return aws.Credentials{}, err } - awsConfig = awsConfig.WithCredentials(credentials.NewStaticCredentialsFromCreds(sourceCreds)) + optFns = append(optFns, config.WithCredentialsProvider(credentials.NewStaticCredentialsProvider(sourceCreds.AccessKeyID, sourceCreds.SecretAccessKey, sourceCreds.SessionToken))) } - creds := GetAssumeRoleCredentials(p, awsConfig) + creds, err := GetAssumeRoleCredentialsCache(ctx, p, optFns) + if err != nil { + return aws.Credentials{}, err + } // Update credentials p.credentials = creds } - return p.credentials.Get() -} - -// IsExpired checks the expiration state of the AWSRolePrincipalTypeProvider. -func (p *AWSRolePrincipalTypeProvider) IsExpired() bool { - return p.credentials.IsExpired() + return p.credentials.Retrieve(ctx) } diff --git a/pkg/cloud/identity/identity_test.go b/pkg/cloud/identity/identity_test.go index 9f4a995ab8..efcbcdd946 100644 --- a/pkg/cloud/identity/identity_test.go +++ b/pkg/cloud/identity/identity_test.go @@ -17,18 +17,17 @@ limitations under the License. package identity import ( + "context" "testing" "time" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/credentials" - "github.com/aws/aws-sdk-go/service/sts" + "github.com/aws/aws-sdk-go-v2/aws" + "github.com/aws/aws-sdk-go-v2/service/sts" + ststypes "github.com/aws/aws-sdk-go-v2/service/sts/types" "github.com/golang/mock/gomock" "github.com/google/go-cmp/cmp" . "github.com/onsi/gomega" - "github.com/pkg/errors" corev1 "k8s.io/api/core/v1" - "k8s.io/utils/ptr" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/services/sts/mock_stsiface" @@ -47,7 +46,7 @@ func TestAWSStaticPrincipalTypeProvider(t *testing.T) { staticProvider := NewAWSStaticPrincipalTypeProvider(&infrav1.AWSClusterStaticIdentity{}, secret) - stsMock := mock_stsiface.NewMockSTSAPI(mockCtrl) + stsMock := mock_stsiface.NewMockSTSClient(mockCtrl) roleIdentity := &infrav1.AWSClusterRoleIdentity{ Spec: infrav1.AWSClusterRoleIdentitySpec{ AWSRoleSpec: infrav1.AWSRoleSpec{ @@ -58,6 +57,8 @@ func TestAWSStaticPrincipalTypeProvider(t *testing.T) { }, } + expiresAt := time.Now() + roleProvider := &AWSRolePrincipalTypeProvider{ credentials: nil, Principal: roleIdentity, @@ -87,56 +88,60 @@ func TestAWSStaticPrincipalTypeProvider(t *testing.T) { testCases := []struct { name string provider AWSPrincipalTypeProvider - expect func(m *mock_stsiface.MockSTSAPIMockRecorder) + expect func(m *mock_stsiface.MockSTSClientMockRecorder) expectErr bool - value credentials.Value + value aws.Credentials }{ { name: "Static provider successfully retrieves", provider: staticProvider, - expect: func(m *mock_stsiface.MockSTSAPIMockRecorder) {}, + expect: func(m *mock_stsiface.MockSTSClientMockRecorder) {}, expectErr: false, - value: credentials.Value{ + value: aws.Credentials{ AccessKeyID: "static-AccessKeyID", SecretAccessKey: "static-SecretAccessKey", - ProviderName: "StaticProvider", + Source: "StaticCredentials", + CanExpire: false, + Expires: time.Time{}, }, }, { name: "Role provider with static provider source successfully retrieves", provider: roleProvider, - expect: func(m *mock_stsiface.MockSTSAPIMockRecorder) { - m.AssumeRoleWithContext(gomock.Any(), &sts.AssumeRoleInput{ + expect: func(m *mock_stsiface.MockSTSClientMockRecorder) { + m.AssumeRole(gomock.Any(), &sts.AssumeRoleInput{ RoleArn: aws.String(roleIdentity.Spec.RoleArn), RoleSessionName: aws.String(roleIdentity.Spec.SessionName), - DurationSeconds: ptr.To[int64](int64(roleIdentity.Spec.DurationSeconds)), + DurationSeconds: aws.Int32(roleIdentity.Spec.DurationSeconds), }).Return(&sts.AssumeRoleOutput{ - Credentials: &sts.Credentials{ + Credentials: &ststypes.Credentials{ AccessKeyId: aws.String("assumedAccessKeyId"), SecretAccessKey: aws.String("assumedSecretAccessKey"), SessionToken: aws.String("assumedSessionToken"), - Expiration: aws.Time(time.Now()), + Expiration: aws.Time(expiresAt), }, }, nil) }, expectErr: false, - value: credentials.Value{ + value: aws.Credentials{ AccessKeyID: "assumedAccessKeyId", SecretAccessKey: "assumedSecretAccessKey", SessionToken: "assumedSessionToken", - ProviderName: "AssumeRoleProvider", + Source: "AssumeRoleProvider", + CanExpire: true, + Expires: expiresAt, }, }, { name: "Role provider with role provider source successfully retrieves", provider: roleProvider2, - expect: func(m *mock_stsiface.MockSTSAPIMockRecorder) { - m.AssumeRoleWithContext(gomock.Any(), &sts.AssumeRoleInput{ + expect: func(m *mock_stsiface.MockSTSClientMockRecorder) { + m.AssumeRole(gomock.Any(), &sts.AssumeRoleInput{ RoleArn: aws.String(roleIdentity.Spec.RoleArn), RoleSessionName: aws.String(roleIdentity.Spec.SessionName), - DurationSeconds: ptr.To[int64](int64(roleIdentity.Spec.DurationSeconds)), + DurationSeconds: aws.Int32(roleIdentity.Spec.DurationSeconds), }).Return(&sts.AssumeRoleOutput{ - Credentials: &sts.Credentials{ + Credentials: &ststypes.Credentials{ AccessKeyId: aws.String("assumedAccessKeyId"), SecretAccessKey: aws.String("assumedSecretAccessKey"), SessionToken: aws.String("assumedSessionToken"), @@ -144,41 +149,28 @@ func TestAWSStaticPrincipalTypeProvider(t *testing.T) { }, }, nil) - m.AssumeRoleWithContext(gomock.Any(), &sts.AssumeRoleInput{ + m.AssumeRole(gomock.Any(), &sts.AssumeRoleInput{ RoleArn: aws.String(roleIdentity2.Spec.RoleArn), RoleSessionName: aws.String(roleIdentity2.Spec.SessionName), - DurationSeconds: ptr.To[int64](int64(roleIdentity2.Spec.DurationSeconds)), + DurationSeconds: aws.Int32(roleIdentity2.Spec.DurationSeconds), }).Return(&sts.AssumeRoleOutput{ - Credentials: &sts.Credentials{ + Credentials: &ststypes.Credentials{ AccessKeyId: aws.String("assumedAccessKeyId2"), SecretAccessKey: aws.String("assumedSecretAccessKey2"), SessionToken: aws.String("assumedSessionToken2"), - Expiration: aws.Time(time.Now()), + Expiration: aws.Time(expiresAt), }, }, nil) }, expectErr: false, - value: credentials.Value{ + value: aws.Credentials{ AccessKeyID: "assumedAccessKeyId2", SecretAccessKey: "assumedSecretAccessKey2", SessionToken: "assumedSessionToken2", - ProviderName: "AssumeRoleProvider", - }, - }, - { - name: "Role provider with role provider source fails to retrieve when the source's source cannot assume source", - provider: roleProvider2, - expect: func(m *mock_stsiface.MockSTSAPIMockRecorder) { - roleProvider.credentials.Expire() - roleProvider2.credentials.Expire() - // AssumeRoleWithContext() call is not needed for roleIdentity as it has unexpired credentials - m.AssumeRoleWithContext(gomock.Any(), &sts.AssumeRoleInput{ - RoleArn: aws.String(roleIdentity.Spec.RoleArn), - RoleSessionName: aws.String(roleIdentity.Spec.SessionName), - DurationSeconds: ptr.To[int64](int64(roleIdentity.Spec.DurationSeconds)), - }).Return(&sts.AssumeRoleOutput{}, errors.New("Not authorized to assume role")) + Source: "AssumeRoleProvider", + CanExpire: true, + Expires: expiresAt, }, - expectErr: true, }, } @@ -187,7 +179,7 @@ func TestAWSStaticPrincipalTypeProvider(t *testing.T) { g := NewWithT(t) tc.expect(stsMock.EXPECT()) - value, err := tc.provider.Retrieve() + value, err := tc.provider.Retrieve(context.TODO()) if tc.expectErr { g.Expect(err).ToNot(BeNil()) return diff --git a/pkg/cloud/identityv2/identity.go b/pkg/cloud/identityv2/identity.go deleted file mode 100644 index 688c473f38..0000000000 --- a/pkg/cloud/identityv2/identity.go +++ /dev/null @@ -1,183 +0,0 @@ -/* -Copyright 2025 The Kubernetes Authors. - -Licensed under the Apache License, Version 2.0 (the "License"); -you may not use this file except in compliance with the License. -You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - -Unless required by applicable law or agreed to in writing, software -distributed under the License is distributed on an "AS IS" BASIS, -WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -See the License for the specific language governing permissions and -limitations under the License. -*/ - -// Package identityv2 provides the AWSPrincipalTypeProvider interface and its implementations. -package identityv2 - -import ( - "bytes" - "context" - "crypto/sha256" - "encoding/gob" - "time" - - "github.com/aws/aws-sdk-go-v2/aws" - "github.com/aws/aws-sdk-go-v2/config" - "github.com/aws/aws-sdk-go-v2/credentials" - "github.com/aws/aws-sdk-go-v2/credentials/stscreds" - "github.com/aws/aws-sdk-go-v2/service/sts" - corev1 "k8s.io/api/core/v1" - - infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" - awsmetricsv2 "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/metricsv2" - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/logger" -) - -// AWSPrincipalTypeProvider defines the interface for AWS Principal Type Provider. -type AWSPrincipalTypeProvider interface { - aws.CredentialsProvider - // Hash returns a unique hash of the data forming the V2 credentials - // for this Principal - Hash() (string, error) - Name() string -} - -// NewAWSStaticPrincipalTypeProvider will create a new AWSStaticPrincipalTypeProvider from a given AWSClusterStaticIdentity. -func NewAWSStaticPrincipalTypeProvider(identity *infrav1.AWSClusterStaticIdentity, secret *corev1.Secret) *AWSStaticPrincipalTypeProvider { - accessKeyID := string(secret.Data["AccessKeyID"]) - secretAccessKey := string(secret.Data["SecretAccessKey"]) - sessionToken := string(secret.Data["SessionToken"]) - - credProvider := credentials.NewStaticCredentialsProvider(accessKeyID, secretAccessKey, sessionToken) - credCache := aws.NewCredentialsCache(credProvider) - return &AWSStaticPrincipalTypeProvider{ - Principal: identity, - credentials: credCache, - AccessKeyID: accessKeyID, - SecretAccessKey: secretAccessKey, - SessionToken: sessionToken, - } -} - -// GetAssumeRoleCredentialsCache will return the CredentialsCache of a given AWSRolePrincipalTypeProvider. -func GetAssumeRoleCredentialsCache(ctx context.Context, roleIdentityProvider *AWSRolePrincipalTypeProvider, optFns []func(*config.LoadOptions) error) (*aws.CredentialsCache, error) { - cfg, err := config.LoadDefaultConfig(ctx, optFns...) - if err != nil { - return nil, err - } - - stsOpts := sts.WithAPIOptions( - awsmetricsv2.WithMiddlewares("identity provider", roleIdentityProvider.Principal), - awsmetricsv2.WithCAPAUserAgentMiddleware()) - stsClient := sts.NewFromConfig(cfg, stsOpts) - credsProvider := stscreds.NewAssumeRoleProvider(stsClient, roleIdentityProvider.Principal.Spec.RoleArn, func(o *stscreds.AssumeRoleOptions) { - if roleIdentityProvider.Principal.Spec.ExternalID != "" { - o.ExternalID = aws.String(roleIdentityProvider.Principal.Spec.ExternalID) - } - o.RoleSessionName = roleIdentityProvider.Principal.Spec.SessionName - if roleIdentityProvider.Principal.Spec.InlinePolicy != "" { - o.Policy = aws.String(roleIdentityProvider.Principal.Spec.InlinePolicy) - } - o.Duration = time.Duration(roleIdentityProvider.Principal.Spec.DurationSeconds) * time.Second - // For testing - if roleIdentityProvider.stsClient != nil { - o.Client = roleIdentityProvider.stsClient - } - }) - - return aws.NewCredentialsCache(credsProvider), nil -} - -// NewAWSRolePrincipalTypeProvider will create a new AWSRolePrincipalTypeProvider from an AWSClusterRoleIdentity. -func NewAWSRolePrincipalTypeProvider(identity *infrav1.AWSClusterRoleIdentity, sourceProvider AWSPrincipalTypeProvider, region string, log logger.Wrapper) *AWSRolePrincipalTypeProvider { - return &AWSRolePrincipalTypeProvider{ - credentials: nil, - stsClient: nil, - region: region, - Principal: identity, - sourceProvider: sourceProvider, - log: log.WithName("AWSRolePrincipalTypeProvider"), - } -} - -// AWSStaticPrincipalTypeProvider defines the specs for a static AWSPrincipalTypeProvider. -type AWSStaticPrincipalTypeProvider struct { - Principal *infrav1.AWSClusterStaticIdentity - credentials *aws.CredentialsCache - // these are for tests :/ - AccessKeyID string - SecretAccessKey string - SessionToken string -} - -// Hash returns the byte encoded AWSStaticPrincipalTypeProvider. -func (p *AWSStaticPrincipalTypeProvider) Hash() (string, error) { - var roleIdentityValue bytes.Buffer - err := gob.NewEncoder(&roleIdentityValue).Encode(p) - if err != nil { - return "", err - } - hash := sha256.New() - return string(hash.Sum(roleIdentityValue.Bytes())), nil -} - -// Retrieve returns the credential values for the AWSStaticPrincipalTypeProvider. -func (p *AWSStaticPrincipalTypeProvider) Retrieve(ctx context.Context) (aws.Credentials, error) { - return p.credentials.Retrieve(ctx) -} - -// Name returns the name of the AWSStaticPrincipalTypeProvider. -func (p *AWSStaticPrincipalTypeProvider) Name() string { - return p.Principal.Name -} - -// AWSRolePrincipalTypeProvider defines the specs for a AWSPrincipalTypeProvider with a role. -type AWSRolePrincipalTypeProvider struct { - Principal *infrav1.AWSClusterRoleIdentity - credentials *aws.CredentialsCache - region string - sourceProvider AWSPrincipalTypeProvider - log logger.Wrapper - stsClient stscreds.AssumeRoleAPIClient -} - -// Hash returns the byte encoded AWSRolePrincipalTypeProvider. -func (p *AWSRolePrincipalTypeProvider) Hash() (string, error) { - var roleIdentityValue bytes.Buffer - err := gob.NewEncoder(&roleIdentityValue).Encode(p) - if err != nil { - return "", err - } - hash := sha256.New() - return string(hash.Sum(roleIdentityValue.Bytes())), nil -} - -// Name returns the name of the AWSRolePrincipalTypeProvider. -func (p *AWSRolePrincipalTypeProvider) Name() string { - return p.Principal.Name -} - -// Retrieve returns the credential values for the AWSRolePrincipalTypeProvider. -func (p *AWSRolePrincipalTypeProvider) Retrieve(ctx context.Context) (aws.Credentials, error) { - if p.credentials == nil { - optFns := []func(*config.LoadOptions) error{config.WithRegion(p.region)} - if p.sourceProvider != nil { - sourceCreds, err := p.sourceProvider.Retrieve(ctx) - if err != nil { - return aws.Credentials{}, err - } - optFns = append(optFns, config.WithCredentialsProvider(credentials.NewStaticCredentialsProvider(sourceCreds.AccessKeyID, sourceCreds.SecretAccessKey, sourceCreds.SessionToken))) - } - - creds, err := GetAssumeRoleCredentialsCache(ctx, p, optFns) - if err != nil { - return aws.Credentials{}, err - } - // Update credentials - p.credentials = creds - } - return p.credentials.Retrieve(ctx) -} diff --git a/pkg/cloud/logs/logs.go b/pkg/cloud/logs/logs.go index 73fbf5359c..08c29e9767 100644 --- a/pkg/cloud/logs/logs.go +++ b/pkg/cloud/logs/logs.go @@ -18,8 +18,7 @@ limitations under the License. package logs import ( - awsv2 "github.com/aws/aws-sdk-go-v2/aws" - "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/go-logr/logr" ) @@ -29,49 +28,14 @@ const ( ) // GetAWSLogLevel will return the log level of an AWS Logger. -func GetAWSLogLevel(logger logr.Logger) aws.LogLevelType { +func GetAWSLogLevel(logger logr.Logger) aws.ClientLogMode { if logger.V(logWithHTTPBody).Enabled() { - return aws.LogDebugWithHTTPBody + return aws.LogRequestWithBody | aws.LogResponseWithBody } if logger.V(logWithHTTPHeader).Enabled() { - return aws.LogDebug + return aws.LogRequest | aws.LogResponse } - return aws.LogOff -} - -// GetAWSLogLevelV2 will return the log level of an AWS Logger. -func GetAWSLogLevelV2(logger logr.Logger) awsv2.ClientLogMode { - if logger.V(logWithHTTPBody).Enabled() { - return awsv2.LogRequestWithBody | awsv2.LogResponseWithBody - } - - if logger.V(logWithHTTPHeader).Enabled() { - return awsv2.LogRequest | awsv2.LogResponse - } - - return awsv2.LogRequestEventMessage -} - -// NewWrapLogr will create an AWS Logger wrapper. -func NewWrapLogr(logger logr.Logger) aws.Logger { - return &logrWrapper{ - log: logger, - } -} - -type logrWrapper struct { - log logr.Logger -} - -func (l *logrWrapper) Log(msgs ...interface{}) { - switch len(msgs) { - case 0: - return - case 1: - l.log.Info(msgs[0].(string)) - default: - l.log.Info(msgs[0].(string), msgs[:1]...) - } + return aws.LogRequestEventMessage } diff --git a/pkg/cloud/metrics/metrics.go b/pkg/cloud/metrics/metrics.go index 4c3e5e988d..82187e02ad 100644 --- a/pkg/cloud/metrics/metrics.go +++ b/pkg/cloud/metrics/metrics.go @@ -1,11 +1,11 @@ /* -Copyright 2020 The Kubernetes Authors. +Copyright 2025 The Kubernetes Authors. Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at - http://www.apache.org/licenses/LICENSE-2.0 + http://www.apache.org/licenses/LICENSE-2.0 Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, @@ -14,28 +14,33 @@ See the License for the specific language governing permissions and limitations under the License. */ -// Package metrics provides a way to capture request metrics. -package metrics +// Package metricsv2 provides a way to capture request metrics. +package metricsv2 import ( - "net/url" + "context" + "fmt" "strconv" - "strings" "time" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/request" + awsmiddleware "github.com/aws/aws-sdk-go-v2/aws/middleware" + "github.com/aws/aws-sdk-go-v2/aws/retry" + "github.com/aws/smithy-go/middleware" + smithyhttp "github.com/aws/smithy-go/transport/http" "github.com/prometheus/client_golang/prometheus" + "k8s.io/apimachinery/pkg/runtime" "sigs.k8s.io/controller-runtime/pkg/metrics" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/awserrors" + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/record" + "sigs.k8s.io/cluster-api-provider-aws/v2/version" ) const ( metricAWSSubsystem = "aws" - metricRequestCountKey = "api_requests_total" - metricRequestDurationKey = "api_request_duration_seconds" - metricAPICallRetries = "api_call_retries" + metricRequestCountKey = "api_requests_total_v2" + metricRequestDurationKey = "api_request_duration_seconds_v2" + metricAPICallRetries = "api_call_retries_v2" metricServiceLabel = "service" metricRegionLabel = "region" metricOperationLabel = "operation" @@ -50,11 +55,13 @@ var ( Name: metricRequestCountKey, Help: "Total number of AWS requests", }, []string{metricControllerLabel, metricServiceLabel, metricRegionLabel, metricOperationLabel, metricStatusCodeLabel, metricErrorCodeLabel}) + awsRequestDurationSeconds = prometheus.NewHistogramVec(prometheus.HistogramOpts{ Subsystem: metricAWSSubsystem, Name: metricRequestDurationKey, Help: "Latency of HTTP requests to AWS", }, []string{metricControllerLabel, metricServiceLabel, metricRegionLabel, metricOperationLabel}) + awsCallRetries = prometheus.NewHistogramVec(prometheus.HistogramOpts{ Subsystem: metricAWSSubsystem, Name: metricAPICallRetries, @@ -69,39 +76,198 @@ func init() { metrics.Registry.MustRegister(awsCallRetries) } -// CaptureRequestMetrics will monitor and capture request metrics. -func CaptureRequestMetrics(controller string) func(r *request.Request) { - return func(r *request.Request) { - duration := time.Since(r.AttemptTime) - operation := r.Operation.Name - region := aws.StringValue(r.Config.Region) - service := endpointToService(r.ClientInfo.Endpoint) - statusCode := "0" - errorCode := "" - if r.HTTPResponse != nil { - statusCode = strconv.Itoa(r.HTTPResponse.StatusCode) +type requestContextKey struct{} + +// RequestData holds information related to request metrics. +type RequestData struct { + RequestStartTime time.Time + RequestEndTime time.Time + StatusCode int + ErrorCode string + Service string + OperationName string + Region string + Controller string + Target runtime.Object + Attempts int +} + +// WithMiddlewares adds instrumentation middleware stacks to AWS GO SDK V2 service clients. +func WithMiddlewares(controller string, target runtime.Object) func(stack *middleware.Stack) error { + return func(stack *middleware.Stack) error { + if err := stack.Initialize.Add(getMetricCollectionMiddleware(controller, target), middleware.Before); err != nil { + return fmt.Errorf("failed to add metric collection middleware: %w", err) + } + if err := stack.Finalize.Add(getRequestMetricContextMiddleware(), middleware.Before); err != nil { + return fmt.Errorf("failed to add request metric context middleware: %w", err) } - if r.Error != nil { - var ok bool - if errorCode, ok = awserrors.Code(r.Error); !ok { - errorCode = "internal" + // Check if the Default Retry Middleware exists. + if _, ok := stack.Finalize.Get((*retry.Attempt)(nil).ID()); ok { + if err := stack.Finalize.Insert(getAttemptContextMiddleware(), (*retry.Attempt)(nil).ID(), middleware.After); err != nil { + return fmt.Errorf("failed to add attempt context middleware: %w", err) } } - awsRequestCount.WithLabelValues(controller, service, region, operation, statusCode, errorCode).Inc() - awsRequestDurationSeconds.WithLabelValues(controller, service, region, operation).Observe(duration.Seconds()) - awsCallRetries.WithLabelValues(controller, service, region, operation).Observe(float64(r.RetryCount)) + return stack.Finalize.Add(getRecordAWSPermissionsIssueMiddleware(target), middleware.After) } } -func endpointToService(endpoint string) string { - endpointURL, err := url.Parse(endpoint) - // If possible extract the service name, else return entire endpoint address - if err == nil { - host := endpointURL.Host - components := strings.Split(host, ".") - if len(components) > 0 { - return components[0] +// WithCAPAUserAgentMiddleware returns User Agent middleware stack for AWS GO SDK V2 sessions. +func WithCAPAUserAgentMiddleware() func(*middleware.Stack) error { + return awsmiddleware.AddUserAgentKeyValue("aws.cluster.x-k8s.io", version.Get().String()) +} + +// WithRequestMetricContextMiddleware returns Request Metric middleware stack for AWS GO SDK V2 sessions. +func WithRequestMetricContextMiddleware() func(*middleware.Stack) error { + return func(stack *middleware.Stack) error { + return stack.Finalize.Add(getRequestMetricContextMiddleware(), middleware.Before) + } +} + +func getMetricCollectionMiddleware(controller string, target runtime.Object) middleware.InitializeMiddleware { + return middleware.InitializeMiddlewareFunc("capa/MetricCollectionMiddleware", func(ctx context.Context, input middleware.InitializeInput, handler middleware.InitializeHandler) (middleware.InitializeOutput, middleware.Metadata, error) { + ctx = initRequestContext(ctx, controller, target) + request := getContext(ctx) + + request.RequestStartTime = time.Now().UTC() + out, metadata, err := handler.HandleInitialize(ctx, input) + + if responseAt, ok := awsmiddleware.GetResponseAt(metadata); ok { + request.RequestEndTime = responseAt + } else { + request.RequestEndTime = time.Now().UTC() + } + request.CaptureRequestMetrics() + return out, metadata, err + }) +} + +func getRequestMetricContextMiddleware() middleware.FinalizeMiddleware { + return middleware.FinalizeMiddlewareFunc("capa/RequestMetricContextMiddleware", func(ctx context.Context, input middleware.FinalizeInput, handler middleware.FinalizeHandler) (middleware.FinalizeOutput, middleware.Metadata, error) { + request := getContext(ctx) + + if request != nil { + request.Service = awsmiddleware.GetServiceID(ctx) + request.OperationName = awsmiddleware.GetOperationName(ctx) + request.Region = awsmiddleware.GetRegion(ctx) + } + return handler.HandleFinalize(ctx, input) + }) +} + +// getAttemptContextMiddleware will capture StatusCode and ErrorCode from API call attempt. +// This will result in the StatusCode and ErrorCode captured for last attempt when publishing to metrics. +func getAttemptContextMiddleware() middleware.FinalizeMiddleware { + return middleware.FinalizeMiddlewareFunc("capa/AttemptMetricContextMiddleware", func(ctx context.Context, input middleware.FinalizeInput, handler middleware.FinalizeHandler) (middleware.FinalizeOutput, middleware.Metadata, error) { + request := getContext(ctx) + if request != nil { + request.Attempts++ } + + out, metadata, err := handler.HandleFinalize(ctx, input) + + if request != nil { + if rawResp := awsmiddleware.GetRawResponse(metadata); rawResp != nil { + if httpResp, ok := rawResp.(*smithyhttp.Response); ok { + request.StatusCode = httpResp.StatusCode + } + } else { + request.StatusCode = -1 + } + + if err != nil { + smithyErr := awserrors.ParseSmithyError(err) + request.ErrorCode = smithyErr.ErrorCode() + request.StatusCode = smithyErr.StatusCode() + } + } + + return out, metadata, err + }) +} + +func getRecordAWSPermissionsIssueMiddleware(target runtime.Object) middleware.FinalizeMiddleware { + return middleware.FinalizeMiddlewareFunc("capa/RecordAWSPermissionsIssueMiddleware", func(ctx context.Context, input middleware.FinalizeInput, handler middleware.FinalizeHandler) (middleware.FinalizeOutput, middleware.Metadata, error) { + output, metadata, err := handler.HandleFinalize(ctx, input) + if err != nil { + request := getContext(ctx) + if request != nil { + var errMessage string + smithyErr := awserrors.ParseSmithyError(err) + request.ErrorCode = smithyErr.ErrorCode() + switch request.ErrorCode { + case "AccessDenied", "AuthFailure", "UnauthorizedOperation", "NoCredentialProviders", + "ExpiredToken", "InvalidClientTokenId", "SignatureDoesNotMatch", "ValidationError": + record.Warnf(target, request.ErrorCode, + "Operation %s failed with a credentials or permission issue: %s", + request.OperationName, + errMessage, + ) + } + } + } + return output, metadata, err + }) +} + +func initRequestContext(ctx context.Context, controller string, target runtime.Object) context.Context { + if middleware.GetStackValue(ctx, requestContextKey{}) == nil { + ctx = middleware.WithStackValue(ctx, requestContextKey{}, &RequestData{ + Controller: controller, + Target: target, + Attempts: 0, + }) + } + return ctx +} + +func getContext(ctx context.Context) *RequestData { + rctx := middleware.GetStackValue(ctx, requestContextKey{}) + if rctx == nil { + return nil } - return endpoint + return rctx.(*RequestData) +} + +// CaptureRequestMetrics will monitor and capture request metrics. +func (r *RequestData) CaptureRequestMetrics() { + if !r.IsIncomplete() { + return + } + + requestDuration := r.RequestEndTime.Sub(r.RequestStartTime) + retryCount := max(r.Attempts-1, 0) + statusCode := strconv.Itoa(r.StatusCode) + errorCode := r.ErrorCode + + if errorCode == "" && r.StatusCode >= 400 { + errorCode = fmt.Sprintf("HTTP%d", r.StatusCode) + } + + awsRequestCount.WithLabelValues( + r.Controller, + r.Service, + r.Region, + r.OperationName, + statusCode, + errorCode, + ).Inc() + + awsRequestDurationSeconds.WithLabelValues( + r.Controller, + r.Service, + r.Region, + r.OperationName, + ).Observe(requestDuration.Seconds()) + + awsCallRetries.WithLabelValues( + r.Controller, + r.Service, + r.Region, + r.OperationName, + ).Observe(float64(retryCount)) +} + +// IsIncomplete will return true if the RequestData was incomplete. +func (r *RequestData) IsIncomplete() bool { + return r.Service == "" || r.Region == "" || r.OperationName == "" || r.Controller == "" } diff --git a/pkg/cloud/metricsv2/metrics.go b/pkg/cloud/metricsv2/metrics.go deleted file mode 100644 index 82187e02ad..0000000000 --- a/pkg/cloud/metricsv2/metrics.go +++ /dev/null @@ -1,273 +0,0 @@ -/* -Copyright 2025 The Kubernetes Authors. - -Licensed under the Apache License, Version 2.0 (the "License"); -you may not use this file except in compliance with the License. -You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - -Unless required by applicable law or agreed to in writing, software -distributed under the License is distributed on an "AS IS" BASIS, -WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -See the License for the specific language governing permissions and -limitations under the License. -*/ - -// Package metricsv2 provides a way to capture request metrics. -package metricsv2 - -import ( - "context" - "fmt" - "strconv" - "time" - - awsmiddleware "github.com/aws/aws-sdk-go-v2/aws/middleware" - "github.com/aws/aws-sdk-go-v2/aws/retry" - "github.com/aws/smithy-go/middleware" - smithyhttp "github.com/aws/smithy-go/transport/http" - "github.com/prometheus/client_golang/prometheus" - "k8s.io/apimachinery/pkg/runtime" - "sigs.k8s.io/controller-runtime/pkg/metrics" - - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/awserrors" - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/record" - "sigs.k8s.io/cluster-api-provider-aws/v2/version" -) - -const ( - metricAWSSubsystem = "aws" - metricRequestCountKey = "api_requests_total_v2" - metricRequestDurationKey = "api_request_duration_seconds_v2" - metricAPICallRetries = "api_call_retries_v2" - metricServiceLabel = "service" - metricRegionLabel = "region" - metricOperationLabel = "operation" - metricControllerLabel = "controller" - metricStatusCodeLabel = "status_code" - metricErrorCodeLabel = "error_code" -) - -var ( - awsRequestCount = prometheus.NewCounterVec(prometheus.CounterOpts{ - Subsystem: metricAWSSubsystem, - Name: metricRequestCountKey, - Help: "Total number of AWS requests", - }, []string{metricControllerLabel, metricServiceLabel, metricRegionLabel, metricOperationLabel, metricStatusCodeLabel, metricErrorCodeLabel}) - - awsRequestDurationSeconds = prometheus.NewHistogramVec(prometheus.HistogramOpts{ - Subsystem: metricAWSSubsystem, - Name: metricRequestDurationKey, - Help: "Latency of HTTP requests to AWS", - }, []string{metricControllerLabel, metricServiceLabel, metricRegionLabel, metricOperationLabel}) - - awsCallRetries = prometheus.NewHistogramVec(prometheus.HistogramOpts{ - Subsystem: metricAWSSubsystem, - Name: metricAPICallRetries, - Help: "Number of retries made against an AWS API", - Buckets: []float64{0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10}, - }, []string{metricControllerLabel, metricServiceLabel, metricRegionLabel, metricOperationLabel}) -) - -func init() { - metrics.Registry.MustRegister(awsRequestCount) - metrics.Registry.MustRegister(awsRequestDurationSeconds) - metrics.Registry.MustRegister(awsCallRetries) -} - -type requestContextKey struct{} - -// RequestData holds information related to request metrics. -type RequestData struct { - RequestStartTime time.Time - RequestEndTime time.Time - StatusCode int - ErrorCode string - Service string - OperationName string - Region string - Controller string - Target runtime.Object - Attempts int -} - -// WithMiddlewares adds instrumentation middleware stacks to AWS GO SDK V2 service clients. -func WithMiddlewares(controller string, target runtime.Object) func(stack *middleware.Stack) error { - return func(stack *middleware.Stack) error { - if err := stack.Initialize.Add(getMetricCollectionMiddleware(controller, target), middleware.Before); err != nil { - return fmt.Errorf("failed to add metric collection middleware: %w", err) - } - if err := stack.Finalize.Add(getRequestMetricContextMiddleware(), middleware.Before); err != nil { - return fmt.Errorf("failed to add request metric context middleware: %w", err) - } - // Check if the Default Retry Middleware exists. - if _, ok := stack.Finalize.Get((*retry.Attempt)(nil).ID()); ok { - if err := stack.Finalize.Insert(getAttemptContextMiddleware(), (*retry.Attempt)(nil).ID(), middleware.After); err != nil { - return fmt.Errorf("failed to add attempt context middleware: %w", err) - } - } - return stack.Finalize.Add(getRecordAWSPermissionsIssueMiddleware(target), middleware.After) - } -} - -// WithCAPAUserAgentMiddleware returns User Agent middleware stack for AWS GO SDK V2 sessions. -func WithCAPAUserAgentMiddleware() func(*middleware.Stack) error { - return awsmiddleware.AddUserAgentKeyValue("aws.cluster.x-k8s.io", version.Get().String()) -} - -// WithRequestMetricContextMiddleware returns Request Metric middleware stack for AWS GO SDK V2 sessions. -func WithRequestMetricContextMiddleware() func(*middleware.Stack) error { - return func(stack *middleware.Stack) error { - return stack.Finalize.Add(getRequestMetricContextMiddleware(), middleware.Before) - } -} - -func getMetricCollectionMiddleware(controller string, target runtime.Object) middleware.InitializeMiddleware { - return middleware.InitializeMiddlewareFunc("capa/MetricCollectionMiddleware", func(ctx context.Context, input middleware.InitializeInput, handler middleware.InitializeHandler) (middleware.InitializeOutput, middleware.Metadata, error) { - ctx = initRequestContext(ctx, controller, target) - request := getContext(ctx) - - request.RequestStartTime = time.Now().UTC() - out, metadata, err := handler.HandleInitialize(ctx, input) - - if responseAt, ok := awsmiddleware.GetResponseAt(metadata); ok { - request.RequestEndTime = responseAt - } else { - request.RequestEndTime = time.Now().UTC() - } - request.CaptureRequestMetrics() - return out, metadata, err - }) -} - -func getRequestMetricContextMiddleware() middleware.FinalizeMiddleware { - return middleware.FinalizeMiddlewareFunc("capa/RequestMetricContextMiddleware", func(ctx context.Context, input middleware.FinalizeInput, handler middleware.FinalizeHandler) (middleware.FinalizeOutput, middleware.Metadata, error) { - request := getContext(ctx) - - if request != nil { - request.Service = awsmiddleware.GetServiceID(ctx) - request.OperationName = awsmiddleware.GetOperationName(ctx) - request.Region = awsmiddleware.GetRegion(ctx) - } - return handler.HandleFinalize(ctx, input) - }) -} - -// getAttemptContextMiddleware will capture StatusCode and ErrorCode from API call attempt. -// This will result in the StatusCode and ErrorCode captured for last attempt when publishing to metrics. -func getAttemptContextMiddleware() middleware.FinalizeMiddleware { - return middleware.FinalizeMiddlewareFunc("capa/AttemptMetricContextMiddleware", func(ctx context.Context, input middleware.FinalizeInput, handler middleware.FinalizeHandler) (middleware.FinalizeOutput, middleware.Metadata, error) { - request := getContext(ctx) - if request != nil { - request.Attempts++ - } - - out, metadata, err := handler.HandleFinalize(ctx, input) - - if request != nil { - if rawResp := awsmiddleware.GetRawResponse(metadata); rawResp != nil { - if httpResp, ok := rawResp.(*smithyhttp.Response); ok { - request.StatusCode = httpResp.StatusCode - } - } else { - request.StatusCode = -1 - } - - if err != nil { - smithyErr := awserrors.ParseSmithyError(err) - request.ErrorCode = smithyErr.ErrorCode() - request.StatusCode = smithyErr.StatusCode() - } - } - - return out, metadata, err - }) -} - -func getRecordAWSPermissionsIssueMiddleware(target runtime.Object) middleware.FinalizeMiddleware { - return middleware.FinalizeMiddlewareFunc("capa/RecordAWSPermissionsIssueMiddleware", func(ctx context.Context, input middleware.FinalizeInput, handler middleware.FinalizeHandler) (middleware.FinalizeOutput, middleware.Metadata, error) { - output, metadata, err := handler.HandleFinalize(ctx, input) - if err != nil { - request := getContext(ctx) - if request != nil { - var errMessage string - smithyErr := awserrors.ParseSmithyError(err) - request.ErrorCode = smithyErr.ErrorCode() - switch request.ErrorCode { - case "AccessDenied", "AuthFailure", "UnauthorizedOperation", "NoCredentialProviders", - "ExpiredToken", "InvalidClientTokenId", "SignatureDoesNotMatch", "ValidationError": - record.Warnf(target, request.ErrorCode, - "Operation %s failed with a credentials or permission issue: %s", - request.OperationName, - errMessage, - ) - } - } - } - return output, metadata, err - }) -} - -func initRequestContext(ctx context.Context, controller string, target runtime.Object) context.Context { - if middleware.GetStackValue(ctx, requestContextKey{}) == nil { - ctx = middleware.WithStackValue(ctx, requestContextKey{}, &RequestData{ - Controller: controller, - Target: target, - Attempts: 0, - }) - } - return ctx -} - -func getContext(ctx context.Context) *RequestData { - rctx := middleware.GetStackValue(ctx, requestContextKey{}) - if rctx == nil { - return nil - } - return rctx.(*RequestData) -} - -// CaptureRequestMetrics will monitor and capture request metrics. -func (r *RequestData) CaptureRequestMetrics() { - if !r.IsIncomplete() { - return - } - - requestDuration := r.RequestEndTime.Sub(r.RequestStartTime) - retryCount := max(r.Attempts-1, 0) - statusCode := strconv.Itoa(r.StatusCode) - errorCode := r.ErrorCode - - if errorCode == "" && r.StatusCode >= 400 { - errorCode = fmt.Sprintf("HTTP%d", r.StatusCode) - } - - awsRequestCount.WithLabelValues( - r.Controller, - r.Service, - r.Region, - r.OperationName, - statusCode, - errorCode, - ).Inc() - - awsRequestDurationSeconds.WithLabelValues( - r.Controller, - r.Service, - r.Region, - r.OperationName, - ).Observe(requestDuration.Seconds()) - - awsCallRetries.WithLabelValues( - r.Controller, - r.Service, - r.Region, - r.OperationName, - ).Observe(float64(retryCount)) -} - -// IsIncomplete will return true if the RequestData was incomplete. -func (r *RequestData) IsIncomplete() bool { - return r.Service == "" || r.Region == "" || r.OperationName == "" || r.Controller == "" -} diff --git a/pkg/cloud/scope/clients.go b/pkg/cloud/scope/clients.go index 45f48cc91c..cbb8f1bb6e 100644 --- a/pkg/cloud/scope/clients.go +++ b/pkg/cloud/scope/clients.go @@ -33,9 +33,9 @@ import ( "k8s.io/apimachinery/pkg/runtime" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud" - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/endpointsv2" + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/endpoints" awslogs "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/logs" - awsmetricsv2 "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/metricsv2" + awsmetrics "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/metrics" stsservice "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/services/sts" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/throttle" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/logger" @@ -48,11 +48,11 @@ func NewASGClient(scopeUser cloud.ScopeUsage, session cloud.Session, logger logg autoscalingOpts := []func(*autoscaling.Options){ func(o *autoscaling.Options) { o.Logger = logger.GetAWSLogger() - o.ClientLogMode = awslogs.GetAWSLogLevelV2(logger.GetLogger()) + o.ClientLogMode = awslogs.GetAWSLogLevel(logger.GetLogger()) }, autoscaling.WithAPIOptions( - awsmetricsv2.WithMiddlewares(scopeUser.ControllerName(), target), - awsmetricsv2.WithCAPAUserAgentMiddleware(), + awsmetrics.WithMiddlewares(scopeUser.ControllerName(), target), + awsmetrics.WithCAPAUserAgentMiddleware(), ), } @@ -62,20 +62,20 @@ func NewASGClient(scopeUser cloud.ScopeUsage, session cloud.Session, logger logg // NewEC2Client creates a new EC2 API client for a given session. func NewEC2Client(scopeUser cloud.ScopeUsage, session cloud.Session, logger logger.Wrapper, target runtime.Object) *ec2.Client { cfg := session.Session() - multiSvcEndpointResolver := endpointsv2.NewMultiServiceEndpointResolver() - ec2EndpointResolver := &endpointsv2.EC2EndpointResolver{ + multiSvcEndpointResolver := endpoints.NewMultiServiceEndpointResolver() + ec2EndpointResolver := &endpoints.EC2EndpointResolver{ MultiServiceEndpointResolver: multiSvcEndpointResolver, } ec2opts := []func(*ec2.Options){ func(o *ec2.Options) { o.Logger = logger.GetAWSLogger() - o.ClientLogMode = awslogs.GetAWSLogLevelV2(logger.GetLogger()) + o.ClientLogMode = awslogs.GetAWSLogLevel(logger.GetLogger()) o.EndpointResolverV2 = ec2EndpointResolver }, ec2.WithAPIOptions( - awsmetricsv2.WithMiddlewares(scopeUser.ControllerName(), target), - awsmetricsv2.WithCAPAUserAgentMiddleware(), + awsmetrics.WithMiddlewares(scopeUser.ControllerName(), target), + awsmetrics.WithCAPAUserAgentMiddleware(), throttle.WithServiceLimiterMiddleware(session.ServiceLimiter(ec2.ServiceID)), ), } @@ -86,20 +86,20 @@ func NewEC2Client(scopeUser cloud.ScopeUsage, session cloud.Session, logger logg // NewELBClient creates a new ELB API client for a given session. func NewELBClient(scopeUser cloud.ScopeUsage, session cloud.Session, logger logger.Wrapper, target runtime.Object) *elb.Client { cfg := session.Session() - multiSvcEndpointResolver := endpointsv2.NewMultiServiceEndpointResolver() - endpointResolver := &endpointsv2.ELBEndpointResolver{ + multiSvcEndpointResolver := endpoints.NewMultiServiceEndpointResolver() + endpointResolver := &endpoints.ELBEndpointResolver{ MultiServiceEndpointResolver: multiSvcEndpointResolver, } opts := []func(*elb.Options){ func(o *elb.Options) { o.Logger = logger.GetAWSLogger() - o.ClientLogMode = awslogs.GetAWSLogLevelV2(logger.GetLogger()) + o.ClientLogMode = awslogs.GetAWSLogLevel(logger.GetLogger()) o.EndpointResolverV2 = endpointResolver }, elb.WithAPIOptions( - awsmetricsv2.WithMiddlewares(scopeUser.ControllerName(), target), - awsmetricsv2.WithCAPAUserAgentMiddleware(), + awsmetrics.WithMiddlewares(scopeUser.ControllerName(), target), + awsmetrics.WithCAPAUserAgentMiddleware(), throttle.WithServiceLimiterMiddleware(session.ServiceLimiter(elb.ServiceID)), ), } @@ -110,20 +110,20 @@ func NewELBClient(scopeUser cloud.ScopeUsage, session cloud.Session, logger logg // NewELBv2Client creates a new ELB v2 API client for a given session. func NewELBv2Client(scopeUser cloud.ScopeUsage, session cloud.Session, logger logger.Wrapper, target runtime.Object) *elbv2.Client { cfg := session.Session() - multiSvcEndpointResolver := endpointsv2.NewMultiServiceEndpointResolver() - endpointResolver := &endpointsv2.ELBV2EndpointResolver{ + multiSvcEndpointResolver := endpoints.NewMultiServiceEndpointResolver() + endpointResolver := &endpoints.ELBV2EndpointResolver{ MultiServiceEndpointResolver: multiSvcEndpointResolver, } opts := []func(*elbv2.Options){ func(o *elbv2.Options) { o.Logger = logger.GetAWSLogger() - o.ClientLogMode = awslogs.GetAWSLogLevelV2(logger.GetLogger()) + o.ClientLogMode = awslogs.GetAWSLogLevel(logger.GetLogger()) o.EndpointResolverV2 = endpointResolver }, elbv2.WithAPIOptions( - awsmetricsv2.WithMiddlewares(scopeUser.ControllerName(), target), - awsmetricsv2.WithCAPAUserAgentMiddleware(), + awsmetrics.WithMiddlewares(scopeUser.ControllerName(), target), + awsmetrics.WithCAPAUserAgentMiddleware(), throttle.WithServiceLimiterMiddleware(session.ServiceLimiter(elbv2.ServiceID)), ), } @@ -134,8 +134,8 @@ func NewELBv2Client(scopeUser cloud.ScopeUsage, session cloud.Session, logger lo // NewEventBridgeClient creates a new EventBridge API client for a given session. func NewEventBridgeClient(scopeUser cloud.ScopeUsage, session cloud.Session, target runtime.Object) *eventbridge.Client { cfg := session.Session() - multiSvcEndpointResolver := endpointsv2.NewMultiServiceEndpointResolver() - endpointResolver := &endpointsv2.EventBridgeEndpointResolver{ + multiSvcEndpointResolver := endpoints.NewMultiServiceEndpointResolver() + endpointResolver := &endpoints.EventBridgeEndpointResolver{ MultiServiceEndpointResolver: multiSvcEndpointResolver, } @@ -144,8 +144,8 @@ func NewEventBridgeClient(scopeUser cloud.ScopeUsage, session cloud.Session, tar o.EndpointResolverV2 = endpointResolver }, eventbridge.WithAPIOptions( - awsmetricsv2.WithMiddlewares(scopeUser.ControllerName(), target), - awsmetricsv2.WithCAPAUserAgentMiddleware(), + awsmetrics.WithMiddlewares(scopeUser.ControllerName(), target), + awsmetrics.WithCAPAUserAgentMiddleware(), ), } @@ -155,8 +155,8 @@ func NewEventBridgeClient(scopeUser cloud.ScopeUsage, session cloud.Session, tar // NewSQSClient creates a new SQS API client for a given session. func NewSQSClient(scopeUser cloud.ScopeUsage, session cloud.Session, target runtime.Object) *sqs.Client { cfg := session.Session() - multiSvcEndpointResolver := endpointsv2.NewMultiServiceEndpointResolver() - endpointResolver := &endpointsv2.SQSEndpointResolver{ + multiSvcEndpointResolver := endpoints.NewMultiServiceEndpointResolver() + endpointResolver := &endpoints.SQSEndpointResolver{ MultiServiceEndpointResolver: multiSvcEndpointResolver, } @@ -165,8 +165,8 @@ func NewSQSClient(scopeUser cloud.ScopeUsage, session cloud.Session, target runt o.EndpointResolverV2 = endpointResolver }, sqs.WithAPIOptions( - awsmetricsv2.WithMiddlewares(scopeUser.ControllerName(), target), - awsmetricsv2.WithCAPAUserAgentMiddleware(), + awsmetrics.WithMiddlewares(scopeUser.ControllerName(), target), + awsmetrics.WithCAPAUserAgentMiddleware(), ), } @@ -176,8 +176,8 @@ func NewSQSClient(scopeUser cloud.ScopeUsage, session cloud.Session, target runt // NewGlobalSQSClient for creating a new SQS API client that isn't tied to a cluster. func NewGlobalSQSClient(scopeUser cloud.ScopeUsage, session cloud.Session) *sqs.Client { cfg := session.Session() - multiSvcEndpointResolver := endpointsv2.NewMultiServiceEndpointResolver() - endpointResolver := &endpointsv2.SQSEndpointResolver{ + multiSvcEndpointResolver := endpoints.NewMultiServiceEndpointResolver() + endpointResolver := &endpoints.SQSEndpointResolver{ MultiServiceEndpointResolver: multiSvcEndpointResolver, } @@ -186,8 +186,8 @@ func NewGlobalSQSClient(scopeUser cloud.ScopeUsage, session cloud.Session) *sqs. o.EndpointResolverV2 = endpointResolver }, sqs.WithAPIOptions( - awsmetricsv2.WithRequestMetricContextMiddleware(), - awsmetricsv2.WithCAPAUserAgentMiddleware(), + awsmetrics.WithRequestMetricContextMiddleware(), + awsmetrics.WithCAPAUserAgentMiddleware(), ), } @@ -197,18 +197,18 @@ func NewGlobalSQSClient(scopeUser cloud.ScopeUsage, session cloud.Session) *sqs. // NewResourgeTaggingClient creates a new Resource Tagging API client for a given session. func NewResourgeTaggingClient(scopeUser cloud.ScopeUsage, session cloud.Session, logger logger.Wrapper, target runtime.Object) *rgapi.Client { cfg := session.Session() - multiSvcEndpointResolver := endpointsv2.NewMultiServiceEndpointResolver() - endpointResolver := &endpointsv2.RGAPIEndpointResolver{ + multiSvcEndpointResolver := endpoints.NewMultiServiceEndpointResolver() + endpointResolver := &endpoints.RGAPIEndpointResolver{ MultiServiceEndpointResolver: multiSvcEndpointResolver, } opts := []func(*rgapi.Options){ func(o *rgapi.Options) { o.Logger = logger.GetAWSLogger() - o.ClientLogMode = awslogs.GetAWSLogLevelV2(logger.GetLogger()) + o.ClientLogMode = awslogs.GetAWSLogLevel(logger.GetLogger()) o.EndpointResolverV2 = endpointResolver }, - rgapi.WithAPIOptions(awsmetricsv2.WithMiddlewares(scopeUser.ControllerName(), target), awsmetricsv2.WithCAPAUserAgentMiddleware()), + rgapi.WithAPIOptions(awsmetrics.WithMiddlewares(scopeUser.ControllerName(), target), awsmetrics.WithCAPAUserAgentMiddleware()), } return rgapi.NewFromConfig(cfg, opts...) @@ -217,19 +217,19 @@ func NewResourgeTaggingClient(scopeUser cloud.ScopeUsage, session cloud.Session, // NewSecretsManagerClient creates a new Secrets API client for a given session.. func NewSecretsManagerClient(scopeUser cloud.ScopeUsage, session cloud.Session, logger logger.Wrapper, target runtime.Object) *secretsmanager.Client { cfg := session.Session() - multiSvcEndpointResolver := endpointsv2.NewMultiServiceEndpointResolver() - secretsManagerEndpointResolver := &endpointsv2.SecretsManagerEndpointResolver{ + multiSvcEndpointResolver := endpoints.NewMultiServiceEndpointResolver() + secretsManagerEndpointResolver := &endpoints.SecretsManagerEndpointResolver{ MultiServiceEndpointResolver: multiSvcEndpointResolver, } secretsManagerOpts := []func(*secretsmanager.Options){ func(o *secretsmanager.Options) { o.Logger = logger.GetAWSLogger() - o.ClientLogMode = awslogs.GetAWSLogLevelV2(logger.GetLogger()) + o.ClientLogMode = awslogs.GetAWSLogLevel(logger.GetLogger()) o.EndpointResolverV2 = secretsManagerEndpointResolver }, secretsmanager.WithAPIOptions( - awsmetricsv2.WithMiddlewares(scopeUser.ControllerName(), target), - awsmetricsv2.WithCAPAUserAgentMiddleware(), + awsmetrics.WithMiddlewares(scopeUser.ControllerName(), target), + awsmetrics.WithCAPAUserAgentMiddleware(), ), } @@ -239,17 +239,17 @@ func NewSecretsManagerClient(scopeUser cloud.ScopeUsage, session cloud.Session, // NewEKSClient creates a new EKS API client for a given session. func NewEKSClient(scopeUser cloud.ScopeUsage, session cloud.Session, logger logger.Wrapper, target runtime.Object) *eks.Client { cfg := session.Session() - multiSvcEndpointResolver := endpointsv2.NewMultiServiceEndpointResolver() - eksEndpointResolver := &endpointsv2.EKSEndpointResolver{ + multiSvcEndpointResolver := endpoints.NewMultiServiceEndpointResolver() + eksEndpointResolver := &endpoints.EKSEndpointResolver{ MultiServiceEndpointResolver: multiSvcEndpointResolver, } s3Opts := []func(*eks.Options){ func(o *eks.Options) { o.Logger = logger.GetAWSLogger() - o.ClientLogMode = awslogs.GetAWSLogLevelV2(logger.GetLogger()) + o.ClientLogMode = awslogs.GetAWSLogLevel(logger.GetLogger()) o.EndpointResolverV2 = eksEndpointResolver }, - eks.WithAPIOptions(awsmetricsv2.WithMiddlewares(scopeUser.ControllerName(), target), awsmetricsv2.WithCAPAUserAgentMiddleware()), + eks.WithAPIOptions(awsmetrics.WithMiddlewares(scopeUser.ControllerName(), target), awsmetrics.WithCAPAUserAgentMiddleware()), } return eks.NewFromConfig(cfg, s3Opts...) } @@ -261,11 +261,11 @@ func NewIAMClient(scopeUser cloud.ScopeUsage, session cloud.Session, logger logg iamOpts := []func(*iam.Options){ func(o *iam.Options) { o.Logger = logger.GetAWSLogger() - o.ClientLogMode = awslogs.GetAWSLogLevelV2(logger.GetLogger()) + o.ClientLogMode = awslogs.GetAWSLogLevel(logger.GetLogger()) }, iam.WithAPIOptions( - awsmetricsv2.WithMiddlewares(scopeUser.ControllerName(), target), - awsmetricsv2.WithCAPAUserAgentMiddleware(), + awsmetrics.WithMiddlewares(scopeUser.ControllerName(), target), + awsmetrics.WithCAPAUserAgentMiddleware(), ), } @@ -275,20 +275,20 @@ func NewIAMClient(scopeUser cloud.ScopeUsage, session cloud.Session, logger logg // NewSTSClient creates a new STS API client for a given session. func NewSTSClient(scopeUser cloud.ScopeUsage, session cloud.Session, logger logger.Wrapper, target runtime.Object) stsservice.STSClient { cfg := session.Session() - multiSvcEndpointResolver := endpointsv2.NewMultiServiceEndpointResolver() - stsEndpointResolver := &endpointsv2.STSEndpointResolver{ + multiSvcEndpointResolver := endpoints.NewMultiServiceEndpointResolver() + stsEndpointResolver := &endpoints.STSEndpointResolver{ MultiServiceEndpointResolver: multiSvcEndpointResolver, } stsOpts := []func(*stsv2.Options){ func(o *stsv2.Options) { o.Logger = logger.GetAWSLogger() - o.ClientLogMode = awslogs.GetAWSLogLevelV2(logger.GetLogger()) + o.ClientLogMode = awslogs.GetAWSLogLevel(logger.GetLogger()) o.EndpointResolverV2 = stsEndpointResolver }, stsv2.WithAPIOptions( - awsmetricsv2.WithMiddlewares(scopeUser.ControllerName(), target), - awsmetricsv2.WithCAPAUserAgentMiddleware(), + awsmetrics.WithMiddlewares(scopeUser.ControllerName(), target), + awsmetrics.WithCAPAUserAgentMiddleware(), ), } @@ -298,19 +298,19 @@ func NewSTSClient(scopeUser cloud.ScopeUsage, session cloud.Session, logger logg // NewSSMClient creates a new Secrets API client for a given session. func NewSSMClient(scopeUser cloud.ScopeUsage, session cloud.Session, logger logger.Wrapper, target runtime.Object) *ssm.Client { cfg := session.Session() - multiSvcEndpointResolver := endpointsv2.NewMultiServiceEndpointResolver() - ssmEndpointResolver := &endpointsv2.SSMEndpointResolver{ + multiSvcEndpointResolver := endpoints.NewMultiServiceEndpointResolver() + ssmEndpointResolver := &endpoints.SSMEndpointResolver{ MultiServiceEndpointResolver: multiSvcEndpointResolver, } ssmOpts := []func(*ssm.Options){ func(o *ssm.Options) { o.Logger = logger.GetAWSLogger() - o.ClientLogMode = awslogs.GetAWSLogLevelV2(logger.GetLogger()) + o.ClientLogMode = awslogs.GetAWSLogLevel(logger.GetLogger()) o.EndpointResolverV2 = ssmEndpointResolver }, ssm.WithAPIOptions( - awsmetricsv2.WithMiddlewares(scopeUser.ControllerName(), target), - awsmetricsv2.WithCAPAUserAgentMiddleware(), + awsmetrics.WithMiddlewares(scopeUser.ControllerName(), target), + awsmetrics.WithCAPAUserAgentMiddleware(), ), } @@ -320,17 +320,17 @@ func NewSSMClient(scopeUser cloud.ScopeUsage, session cloud.Session, logger logg // NewS3Client creates a new S3 API client for a given session. func NewS3Client(scopeUser cloud.ScopeUsage, session cloud.Session, logger logger.Wrapper, target runtime.Object) *s3.Client { cfg := session.Session() - multiSvcEndpointResolver := endpointsv2.NewMultiServiceEndpointResolver() - s3EndpointResolver := &endpointsv2.S3EndpointResolver{ + multiSvcEndpointResolver := endpoints.NewMultiServiceEndpointResolver() + s3EndpointResolver := &endpoints.S3EndpointResolver{ MultiServiceEndpointResolver: multiSvcEndpointResolver, } s3Opts := []func(*s3.Options){ func(o *s3.Options) { o.Logger = logger.GetAWSLogger() - o.ClientLogMode = awslogs.GetAWSLogLevelV2(logger.GetLogger()) + o.ClientLogMode = awslogs.GetAWSLogLevel(logger.GetLogger()) o.EndpointResolverV2 = s3EndpointResolver }, - s3.WithAPIOptions(awsmetricsv2.WithMiddlewares(scopeUser.ControllerName(), target), awsmetricsv2.WithCAPAUserAgentMiddleware()), + s3.WithAPIOptions(awsmetrics.WithMiddlewares(scopeUser.ControllerName(), target), awsmetrics.WithCAPAUserAgentMiddleware()), } return s3.NewFromConfig(cfg, s3Opts...) } diff --git a/pkg/cloud/scope/cluster.go b/pkg/cloud/scope/cluster.go index 51b6315bb6..730b977578 100644 --- a/pkg/cloud/scope/cluster.go +++ b/pkg/cloud/scope/cluster.go @@ -21,8 +21,7 @@ import ( "fmt" "time" - awsv2 "github.com/aws/aws-sdk-go-v2/aws" - awsclient "github.com/aws/aws-sdk-go/aws/client" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/pkg/errors" "k8s.io/apimachinery/pkg/apis/meta/v1/unstructured" "k8s.io/klog/v2" @@ -30,9 +29,9 @@ import ( infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud" + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/endpoints" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/throttle" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/logger" - "sigs.k8s.io/cluster-api-provider-aws/v2/util/system" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" "sigs.k8s.io/cluster-api/util/conditions" "sigs.k8s.io/cluster-api/util/patch" @@ -45,9 +44,7 @@ type ClusterScopeParams struct { Cluster *clusterv1.Cluster AWSCluster *infrav1.AWSCluster ControllerName string - Endpoints []ServiceEndpoint - Session awsclient.ConfigProvider - SessionV2 awsv2.Config + Session aws.Config TagUnmanagedNetworkResources bool MaxWaitActiveUpdateDelete time.Duration } @@ -77,7 +74,7 @@ func NewClusterScope(params ClusterScopeParams) (*ClusterScope, error) { maxWaitActiveUpdateDelete: params.MaxWaitActiveUpdateDelete, } - sessionv2, serviceLimitersv2, err := sessionForClusterWithRegionV2(params.Client, clusterScope, params.AWSCluster.Spec.Region, params.Endpoints, params.Logger) + session, serviceLimiters, err := sessionForClusterWithRegion(params.Client, clusterScope, params.AWSCluster.Spec.Region, params.Logger) if err != nil { return nil, errors.Errorf("failed to create aws V2 session: %v", err) } @@ -88,8 +85,8 @@ func NewClusterScope(params ClusterScopeParams) (*ClusterScope, error) { } clusterScope.patchHelper = helper - clusterScope.session = *sessionv2 - clusterScope.serviceLimiters = serviceLimitersv2 + clusterScope.session = *session + clusterScope.serviceLimiters = serviceLimiters return clusterScope, nil } @@ -103,7 +100,7 @@ type ClusterScope struct { Cluster *clusterv1.Cluster AWSCluster *infrav1.AWSCluster - session awsv2.Config + session aws.Config serviceLimiters throttle.ServiceLimiters controllerName string @@ -353,7 +350,7 @@ func (s *ClusterScope) ClusterObj() cloud.ClusterObject { } // Session returns the AWS SDK V2 session. Used for creating clients. -func (s *ClusterScope) Session() awsv2.Config { +func (s *ClusterScope) Session() aws.Config { return s.session } @@ -414,7 +411,7 @@ func (s *ClusterScope) ImageLookupBaseOS() string { // Partition returns the cluster partition. func (s *ClusterScope) Partition() string { if s.AWSCluster.Spec.Partition == "" { - s.AWSCluster.Spec.Partition = system.GetPartitionFromRegion(s.Region()) + s.AWSCluster.Spec.Partition = endpoints.GetPartitionFromRegion(s.Region()) } return s.AWSCluster.Spec.Partition } diff --git a/pkg/cloud/scope/fargate.go b/pkg/cloud/scope/fargate.go index 96aa21cf34..6e0fe0e1ef 100644 --- a/pkg/cloud/scope/fargate.go +++ b/pkg/cloud/scope/fargate.go @@ -19,8 +19,7 @@ package scope import ( "context" - awsv2 "github.com/aws/aws-sdk-go-v2/aws" - awsclient "github.com/aws/aws-sdk-go/aws/client" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/pkg/errors" "k8s.io/klog/v2" "sigs.k8s.io/controller-runtime/pkg/client" @@ -29,9 +28,9 @@ import ( ekscontrolplanev1 "sigs.k8s.io/cluster-api-provider-aws/v2/controlplane/eks/api/v1beta2" expinfrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/exp/api/v1beta2" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud" + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/endpoints" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/throttle" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/logger" - "sigs.k8s.io/cluster-api-provider-aws/v2/util/system" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" "sigs.k8s.io/cluster-api/util/conditions" "sigs.k8s.io/cluster-api/util/patch" @@ -45,8 +44,7 @@ type FargateProfileScopeParams struct { ControlPlane *ekscontrolplanev1.AWSManagedControlPlane FargateProfile *expinfrav1.AWSFargateProfile ControllerName string - Endpoints []ServiceEndpoint - Session awsclient.ConfigProvider + Session aws.Config EnableIAM bool } @@ -70,7 +68,7 @@ func NewFargateProfileScope(params FargateProfileScopeParams) (*FargateProfileSc controllerName: params.ControllerName, } - sessionv2, serviceLimitersv2, err := sessionForClusterWithRegionV2(params.Client, managedScope, params.ControlPlane.Spec.Region, params.Endpoints, params.Logger) + session, serviceLimiters, err := sessionForClusterWithRegion(params.Client, managedScope, params.ControlPlane.Spec.Region, params.Logger) if err != nil { return nil, errors.Errorf("failed to create aws v2 session: %v", err) } @@ -87,8 +85,8 @@ func NewFargateProfileScope(params FargateProfileScopeParams) (*FargateProfileSc ControlPlane: params.ControlPlane, FargateProfile: params.FargateProfile, patchHelper: helper, - session: *sessionv2, - serviceLimiters: serviceLimitersv2, + session: *session, + serviceLimiters: serviceLimiters, controllerName: params.ControllerName, enableIAM: params.EnableIAM, }, nil @@ -104,7 +102,7 @@ type FargateProfileScope struct { ControlPlane *ekscontrolplanev1.AWSManagedControlPlane FargateProfile *expinfrav1.AWSFargateProfile - session awsv2.Config + session aws.Config serviceLimiters throttle.ServiceLimiters controllerName string @@ -162,7 +160,7 @@ func (s *FargateProfileScope) SubnetIDs() []string { // Partition returns the machine pool subnet IDs. func (s *FargateProfileScope) Partition() string { if s.ControlPlane.Spec.Partition == "" { - s.ControlPlane.Spec.Partition = system.GetPartitionFromRegion(s.ControlPlane.Spec.Region) + s.ControlPlane.Spec.Partition = endpoints.GetPartitionFromRegion(s.ControlPlane.Spec.Region) } return s.ControlPlane.Spec.Partition } @@ -217,7 +215,7 @@ func (s *FargateProfileScope) ClusterObj() cloud.ClusterObject { } // Session returns the AWS SDK V2 session. Used for creating clients. -func (s *FargateProfileScope) Session() awsv2.Config { +func (s *FargateProfileScope) Session() aws.Config { return s.session } diff --git a/pkg/cloud/scope/global.go b/pkg/cloud/scope/global.go index dc084ab717..d2d6436bfb 100644 --- a/pkg/cloud/scope/global.go +++ b/pkg/cloud/scope/global.go @@ -32,12 +32,8 @@ func NewGlobalScope(params GlobalScopeParams) (*GlobalScope, error) { if params.ControllerName == "" { return nil, errors.New("controller name required to generate global scope") } - _, limiters, err := sessionForRegion(params.Region, params.Endpoints) - if err != nil { - return nil, errors.Wrap(err, "failed to create aws session") - } - ns2, _, err := sessionForRegionV2(params.Region) + ns2, limiters, err := sessionForRegion(params.Region) if err != nil { return nil, errors.Wrap(err, "failed to create aws V2 session") } @@ -52,7 +48,6 @@ func NewGlobalScope(params GlobalScopeParams) (*GlobalScope, error) { type GlobalScopeParams struct { ControllerName string Region string - Endpoints []ServiceEndpoint } // GlobalScope defines the specs for the GlobalScope. diff --git a/pkg/cloud/scope/managedcontrolplane.go b/pkg/cloud/scope/managedcontrolplane.go index 856eb29dfe..be0bc76864 100644 --- a/pkg/cloud/scope/managedcontrolplane.go +++ b/pkg/cloud/scope/managedcontrolplane.go @@ -22,8 +22,7 @@ import ( "time" amazoncni "github.com/aws/amazon-vpc-cni-k8s/pkg/apis/crd/v1alpha1" - awsv2 "github.com/aws/aws-sdk-go-v2/aws" - awsclient "github.com/aws/aws-sdk-go/aws/client" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/pkg/errors" appsv1 "k8s.io/api/apps/v1" corev1 "k8s.io/api/core/v1" @@ -36,9 +35,9 @@ import ( infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" ekscontrolplanev1 "sigs.k8s.io/cluster-api-provider-aws/v2/controlplane/eks/api/v1beta2" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud" + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/endpoints" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/throttle" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/logger" - "sigs.k8s.io/cluster-api-provider-aws/v2/util/system" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" "sigs.k8s.io/cluster-api/controllers/remote" "sigs.k8s.io/cluster-api/util/patch" @@ -62,8 +61,7 @@ type ManagedControlPlaneScopeParams struct { Cluster *clusterv1.Cluster ControlPlane *ekscontrolplanev1.AWSManagedControlPlane ControllerName string - Endpoints []ServiceEndpoint - Session awsclient.ConfigProvider + Session aws.Config MaxWaitActiveUpdateDelete time.Duration EnableIAM bool @@ -98,13 +96,13 @@ func NewManagedControlPlaneScope(params ManagedControlPlaneScopeParams) (*Manage enableIAM: params.EnableIAM, tagUnmanagedNetworkResources: params.TagUnmanagedNetworkResources, } - sessionv2, serviceLimitersv2, err := sessionForClusterWithRegionV2(params.Client, managedScope, params.ControlPlane.Spec.Region, params.Endpoints, params.Logger) + session, serviceLimiters, err := sessionForClusterWithRegion(params.Client, managedScope, params.ControlPlane.Spec.Region, params.Logger) if err != nil { return nil, errors.Errorf("failed to create aws V2 session: %v", err) } - managedScope.session = *sessionv2 - managedScope.serviceLimiters = serviceLimitersv2 + managedScope.session = *session + managedScope.serviceLimiters = serviceLimiters helper, err := patch.NewHelper(params.ControlPlane, params.Client) if err != nil { @@ -125,7 +123,7 @@ type ManagedControlPlaneScope struct { ControlPlane *ekscontrolplanev1.AWSManagedControlPlane MaxWaitActiveUpdateDelete time.Duration - session awsv2.Config + session aws.Config serviceLimiters throttle.ServiceLimiters controllerName string @@ -325,7 +323,7 @@ func (s *ManagedControlPlaneScope) ClusterObj() cloud.ClusterObject { } // Session returns the AWS SDK V2 config. Used for creating clients. -func (s *ManagedControlPlaneScope) Session() awsv2.Config { +func (s *ManagedControlPlaneScope) Session() aws.Config { return s.session } @@ -473,7 +471,7 @@ func (s *ManagedControlPlaneScope) ControlPlaneLoadBalancers() []*infrav1.AWSLoa // Partition returns the cluster partition. func (s *ManagedControlPlaneScope) Partition() string { if s.ControlPlane.Spec.Partition == "" { - s.ControlPlane.Spec.Partition = system.GetPartitionFromRegion(s.Region()) + s.ControlPlane.Spec.Partition = endpoints.GetPartitionFromRegion(s.Region()) } return s.ControlPlane.Spec.Partition } diff --git a/pkg/cloud/scope/managednodegroup.go b/pkg/cloud/scope/managednodegroup.go index 2ce1890438..7ef4663a24 100644 --- a/pkg/cloud/scope/managednodegroup.go +++ b/pkg/cloud/scope/managednodegroup.go @@ -34,9 +34,9 @@ import ( ekscontrolplanev1 "sigs.k8s.io/cluster-api-provider-aws/v2/controlplane/eks/api/v1beta2" expinfrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/exp/api/v1beta2" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud" + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/endpoints" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/throttle" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/logger" - "sigs.k8s.io/cluster-api-provider-aws/v2/util/system" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" expclusterv1 "sigs.k8s.io/cluster-api/exp/api/v1beta1" "sigs.k8s.io/cluster-api/util/conditions" @@ -52,7 +52,6 @@ type ManagedMachinePoolScopeParams struct { ManagedMachinePool *expinfrav1.AWSManagedMachinePool MachinePool *expclusterv1.MachinePool ControllerName string - Endpoints []ServiceEndpoint Session awsv2.Config MaxWaitActiveUpdateDelete time.Duration @@ -88,7 +87,7 @@ func NewManagedMachinePoolScope(params ManagedMachinePoolScopeParams) (*ManagedM controllerName: params.ControllerName, } - sessionv2, serviceLimitersv2, err := sessionForClusterWithRegionV2(params.Client, managedScope, params.ControlPlane.Spec.Region, params.Endpoints, params.Logger) + session, serviceLimiters, err := sessionForClusterWithRegion(params.Client, managedScope, params.ControlPlane.Spec.Region, params.Logger) if err != nil { return nil, errors.Errorf("failed to create aws V2 session: %v", err) } @@ -114,8 +113,8 @@ func NewManagedMachinePoolScope(params ManagedMachinePoolScopeParams) (*ManagedM MachinePool: params.MachinePool, MaxWaitActiveUpdateDelete: params.MaxWaitActiveUpdateDelete, EC2Scope: params.InfraCluster, - session: *sessionv2, - serviceLimiters: serviceLimitersv2, + session: *session, + serviceLimiters: serviceLimiters, controllerName: params.ControllerName, enableIAM: params.EnableIAM, allowAdditionalRoles: params.AllowAdditionalRoles, @@ -174,7 +173,7 @@ func (s *ManagedMachinePoolScope) AllowAdditionalRoles() bool { // Partition returns the machine pool subnet IDs. func (s *ManagedMachinePoolScope) Partition() string { - return system.GetPartitionFromRegion(s.ControlPlane.Spec.Region) + return endpoints.GetPartitionFromRegion(s.ControlPlane.Spec.Region) } // IdentityRef returns the cluster identityRef. diff --git a/pkg/cloud/scope/rosacontrolplane.go b/pkg/cloud/scope/rosacontrolplane.go index 5d8ab5e265..4aac52bd01 100644 --- a/pkg/cloud/scope/rosacontrolplane.go +++ b/pkg/cloud/scope/rosacontrolplane.go @@ -46,7 +46,6 @@ type ROSAControlPlaneScopeParams struct { Cluster *clusterv1.Cluster ControlPlane *rosacontrolplanev1.ROSAControlPlane ControllerName string - Endpoints []ServiceEndpoint NewStsClient func(cloud.ScopeUsage, cloud.Session, logger.Wrapper, runtime.Object) stsservice.STSClient } @@ -72,7 +71,7 @@ func NewROSAControlPlaneScope(params ROSAControlPlaneScopeParams) (*ROSAControlP controllerName: params.ControllerName, } - sessionv2, serviceLimitersv2, err := sessionForClusterWithRegionV2(params.Client, managedScope, params.ControlPlane.Spec.Region, params.Endpoints, params.Logger) + session, serviceLimiters, err := sessionForClusterWithRegion(params.Client, managedScope, params.ControlPlane.Spec.Region, params.Logger) if err != nil { return nil, errors.Errorf("failed to create aws V2 session: %v", err) } @@ -83,8 +82,8 @@ func NewROSAControlPlaneScope(params ROSAControlPlaneScopeParams) (*ROSAControlP } managedScope.patchHelper = helper - managedScope.session = *sessionv2 - managedScope.serviceLimiters = serviceLimitersv2 + managedScope.session = *session + managedScope.serviceLimiters = serviceLimiters stsClient := params.NewStsClient(managedScope, managedScope, managedScope, managedScope.ControlPlane) identity, err := stsClient.GetCallerIdentity(context.TODO(), &stsv2.GetCallerIdentityInput{}) diff --git a/pkg/cloud/scope/rosamachinepool.go b/pkg/cloud/scope/rosamachinepool.go index 1186c8d883..5c53635b5b 100644 --- a/pkg/cloud/scope/rosamachinepool.go +++ b/pkg/cloud/scope/rosamachinepool.go @@ -45,8 +45,6 @@ type RosaMachinePoolScopeParams struct { RosaMachinePool *expinfrav1.ROSAMachinePool MachinePool *expclusterv1.MachinePool ControllerName string - - Endpoints []ServiceEndpoint } // NewRosaMachinePoolScope creates a new Scope from the supplied parameters. @@ -88,13 +86,13 @@ func NewRosaMachinePoolScope(params RosaMachinePoolScopeParams) (*RosaMachinePoo controllerName: params.ControllerName, } - sessionv2, serviceLimitersv2, err := sessionForClusterWithRegionV2(params.Client, scope, params.ControlPlane.Spec.Region, params.Endpoints, params.Logger) + session, serviceLimiters, err := sessionForClusterWithRegion(params.Client, scope, params.ControlPlane.Spec.Region, params.Logger) if err != nil { return nil, errors.Errorf("failed to create aws V2 session: %v", err) } - scope.session = *sessionv2 - scope.serviceLimiters = serviceLimitersv2 + scope.session = *session + scope.serviceLimiters = serviceLimiters return scope, nil } diff --git a/pkg/cloud/scope/session.go b/pkg/cloud/scope/session.go index d501e349c7..ae6ff23244 100644 --- a/pkg/cloud/scope/session.go +++ b/pkg/cloud/scope/session.go @@ -21,16 +21,13 @@ import ( "fmt" "sync" - awsv2 "github.com/aws/aws-sdk-go-v2/aws" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/config" "github.com/aws/aws-sdk-go-v2/service/ec2" elb "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancing" elbv2 "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancingv2" "github.com/aws/aws-sdk-go-v2/service/resourcegroupstaggingapi" "github.com/aws/aws-sdk-go-v2/service/secretsmanager" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/endpoints" - "github.com/aws/aws-sdk-go/aws/session" "github.com/google/go-cmp/cmp" "github.com/pkg/errors" corev1 "k8s.io/api/core/v1" @@ -40,7 +37,6 @@ import ( infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/identity" - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/identityv2" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/throttle" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/logger" "sigs.k8s.io/cluster-api-provider-aws/v2/util/system" @@ -54,92 +50,45 @@ const ( notPermittedError = "Namespace is not permitted to use %s: %s" ) -// ServiceEndpoint defines a tuple containing AWS Service resolution information. -type ServiceEndpoint struct { - ServiceID string - URL string - SigningRegion string -} - var sessionCache sync.Map -var sessionCacheV2 sync.Map -var providerCacheV2 sync.Map +var providerCache sync.Map type sessionCacheEntry struct { - session *session.Session - sessionV2 *awsv2.Config + session *aws.Config serviceLimiters throttle.ServiceLimiters } // ChainCredentialsProvider defines custom CredentialsProvider chain // NewChainCredentialsProvider can be used to initialize this struct. type ChainCredentialsProvider struct { - providers []awsv2.CredentialsProvider + providers []aws.CredentialsProvider } -func sessionForRegion(region string, endpoint []ServiceEndpoint) (*session.Session, throttle.ServiceLimiters, error) { +func sessionForRegion(region string) (*aws.Config, throttle.ServiceLimiters, error) { if s, ok := sessionCache.Load(region); ok { entry := s.(*sessionCacheEntry) return entry.session, entry.serviceLimiters, nil } - resolver := func(service, region string, optFns ...func(*endpoints.Options)) (endpoints.ResolvedEndpoint, error) { - for _, s := range endpoint { - if service == s.ServiceID { - return endpoints.ResolvedEndpoint{ - URL: s.URL, - SigningRegion: s.SigningRegion, - }, nil - } - } - return endpoints.DefaultResolver().EndpointFor(service, region, optFns...) - } - ns, err := session.NewSession(&aws.Config{ - Region: aws.String(region), - EndpointResolver: endpoints.ResolverFunc(resolver), - }) - if err != nil { - return nil, nil, err - } - - sl := newServiceLimiters() - sessionCache.Store(region, &sessionCacheEntry{ - session: ns, - serviceLimiters: sl, - sessionV2: nil, - }) - return ns, sl, nil -} - -func sessionForRegionV2(region string) (*awsv2.Config, throttle.ServiceLimiters, error) { - if s, ok := sessionCacheV2.Load(region); ok { - entry := s.(*sessionCacheEntry) - return entry.sessionV2, entry.serviceLimiters, nil - } - - optFns := []func(*config.LoadOptions) error{ - config.WithRegion(region), - } - ns, err := config.LoadDefaultConfig(context.Background(), optFns...) + ns, err := config.LoadDefaultConfig(context.Background(), config.WithRegion(region)) if err != nil { return nil, nil, err } sl := newServiceLimiters() - sessionCacheV2.Store(region, &sessionCacheEntry{ - sessionV2: &ns, + sessionCache.Store(region, &sessionCacheEntry{ + session: &ns, serviceLimiters: sl, - session: nil, }) return &ns, sl, nil } -func sessionForClusterWithRegionV2(k8sClient client.Client, clusterScoper cloud.SessionMetadata, region string, _ []ServiceEndpoint, log logger.Wrapper) (*awsv2.Config, throttle.ServiceLimiters, error) { +func sessionForClusterWithRegion(k8sClient client.Client, clusterScoper cloud.SessionMetadata, region string, log logger.Wrapper) (*aws.Config, throttle.ServiceLimiters, error) { log = log.WithName("identity") log.Trace("Creating an AWS Session") - providers, err := getProvidersForClusterV2(context.Background(), k8sClient, clusterScoper, region, log) + providers, err := getProvidersForCluster(context.Background(), k8sClient, clusterScoper, region, log) if err != nil { // could not get providers and retrieve the credentials conditions.MarkFalse(clusterScoper.InfraCluster(), infrav1.PrincipalCredentialRetrievedCondition, infrav1.PrincipalCredentialRetrievalFailedReason, clusterv1.ConditionSeverityError, "%s", err.Error()) @@ -147,28 +96,28 @@ func sessionForClusterWithRegionV2(k8sClient client.Client, clusterScoper cloud. } isChanged := false - awsProviders := make([]awsv2.CredentialsProvider, len(providers)) + awsProviders := make([]aws.CredentialsProvider, len(providers)) for i, provider := range providers { // load an existing matching providers from the cache if such a providers exists providerHash, err := provider.Hash() if err != nil { return nil, nil, errors.Wrap(err, "Failed to calculate provider hash") } - cachedProvider, ok := providerCacheV2.Load(providerHash) + cachedProvider, ok := providerCache.Load(providerHash) if ok { - provider = cachedProvider.(identityv2.AWSPrincipalTypeProvider) + provider = cachedProvider.(identity.AWSPrincipalTypeProvider) } else { isChanged = true // add this provider to the cache - providerCacheV2.Store(providerHash, provider) + providerCache.Store(providerHash, provider) } - awsProviders[i] = provider.(awsv2.CredentialsProvider) + awsProviders[i] = provider.(aws.CredentialsProvider) } if !isChanged { - if s, ok := sessionCacheV2.Load(getSessionName(region, clusterScoper)); ok { + if s, ok := sessionCache.Load(getSessionName(region, clusterScoper)); ok { entry := s.(*sessionCacheEntry) - return entry.sessionV2, entry.serviceLimiters, nil + return entry.session, entry.serviceLimiters, nil } } @@ -198,10 +147,9 @@ func sessionForClusterWithRegionV2(k8sClient client.Client, clusterScoper cloud. return nil, nil, errors.Wrap(err, "Failed to create a new AWS session") } sl := newServiceLimiters() - sessionCacheV2.Store(getSessionName(region, clusterScoper), &sessionCacheEntry{ - sessionV2: &ns, + sessionCache.Store(getSessionName(region, clusterScoper), &sessionCacheEntry{ + session: &ns, serviceLimiters: sl, - session: nil, }) return &ns, sl, nil @@ -344,79 +292,6 @@ func buildProvidersForRef( return providers, nil } -func buildProvidersForRefV2( - ctx context.Context, - providers []identityv2.AWSPrincipalTypeProvider, - k8sClient client.Client, - clusterScoper cloud.SessionMetadata, - ref *infrav1.AWSIdentityReference, - region string, - log logger.Wrapper) ([]identityv2.AWSPrincipalTypeProvider, error) { - if ref == nil { - log.Trace("AWSCluster does not have a IdentityRef specified") - return providers, nil - } - - var provider identityv2.AWSPrincipalTypeProvider - identityObjectKey := client.ObjectKey{Name: ref.Name} - log = log.WithValues("identityKey", identityObjectKey) - log.Trace("Getting identity") - - switch ref.Kind { - case infrav1.ControllerIdentityKind: - err := buildAWSClusterControllerIdentity(ctx, identityObjectKey, k8sClient, clusterScoper) - if err != nil { - return providers, err - } - // returning empty provider list to default to Controller Principal. - return []identityv2.AWSPrincipalTypeProvider{}, nil - case infrav1.ClusterStaticIdentityKind: - provider, err := buildAWSClusterStaticIdentityV2(ctx, identityObjectKey, k8sClient, clusterScoper) - if err != nil { - return providers, err - } - providers = append(providers, provider) - case infrav1.ClusterRoleIdentityKind: - roleIdentity := &infrav1.AWSClusterRoleIdentity{} - err := k8sClient.Get(ctx, identityObjectKey, roleIdentity) - if err != nil { - return providers, err - } - log.Trace("Principal retrieved") - canUse, err := isClusterPermittedToUsePrincipal(k8sClient, roleIdentity.Spec.AllowedNamespaces, clusterScoper.Namespace()) - if err != nil { - return providers, err - } - if !canUse { - setPrincipalUsageNotAllowedCondition(infrav1.ClusterRoleIdentityKind, identityObjectKey, clusterScoper) - return providers, errors.Errorf(notPermittedError, infrav1.ClusterRoleIdentityKind, roleIdentity.Name) - } - setPrincipalUsageAllowedCondition(clusterScoper) - - if roleIdentity.Spec.SourceIdentityRef != nil { - providers, err = buildProvidersForRefV2(ctx, providers, k8sClient, clusterScoper, roleIdentity.Spec.SourceIdentityRef, region, log) - if err != nil { - return providers, err - } - } - var sourceProvider identityv2.AWSPrincipalTypeProvider - if len(providers) > 0 { - sourceProvider = providers[len(providers)-1] - // Remove last provider - if len(providers) > 0 { - providers = providers[:len(providers)-1] - } - } - - provider = identityv2.NewAWSRolePrincipalTypeProvider(roleIdentity, sourceProvider, region, log) - providers = append(providers, provider) - default: - return providers, errors.Errorf("No such provider known: '%s'", ref.Kind) - } - conditions.MarkTrue(clusterScoper.InfraCluster(), infrav1.PrincipalUsageAllowedCondition) - return providers, nil -} - func setPrincipalUsageAllowedCondition(clusterScoper cloud.SessionMetadata) { conditions.MarkTrue(clusterScoper.InfraCluster(), infrav1.PrincipalUsageAllowedCondition) } @@ -473,48 +348,6 @@ func buildAWSClusterStaticIdentity(ctx context.Context, identityObjectKey client return identity.NewAWSStaticPrincipalTypeProvider(staticPrincipal, secret), nil } -func buildAWSClusterStaticIdentityV2(ctx context.Context, identityObjectKey client.ObjectKey, k8sClient client.Client, clusterScoper cloud.SessionMetadata) (*identityv2.AWSStaticPrincipalTypeProvider, error) { - staticPrincipal := &infrav1.AWSClusterStaticIdentity{} - err := k8sClient.Get(ctx, identityObjectKey, staticPrincipal) - if err != nil { - return nil, err - } - secret := &corev1.Secret{} - err = k8sClient.Get(ctx, client.ObjectKey{Name: staticPrincipal.Spec.SecretRef, Namespace: system.GetManagerNamespace()}, secret) - if err != nil { - return nil, err - } - - // Set ClusterStaticPrincipal as Secret's owner reference for 'clusterctl move'. - patchHelper, err := patch.NewHelper(secret, k8sClient) - if err != nil { - return nil, errors.Wrapf(err, "failed to init patch helper for secret name:%s namespace:%s", secret.Name, secret.Namespace) - } - - secret.OwnerReferences = util.EnsureOwnerRef(secret.OwnerReferences, metav1.OwnerReference{ - APIVersion: infrav1.GroupVersion.String(), - Kind: string(infrav1.ClusterStaticIdentityKind), - Name: staticPrincipal.Name, - UID: staticPrincipal.UID, - }) - - if err := patchHelper.Patch(ctx, secret); err != nil { - return nil, errors.Wrapf(err, "failed to patch secret name:%s namespace:%s", secret.Name, secret.Namespace) - } - - canUse, err := isClusterPermittedToUsePrincipal(k8sClient, staticPrincipal.Spec.AllowedNamespaces, clusterScoper.Namespace()) - if err != nil { - return nil, err - } - if !canUse { - setPrincipalUsageNotAllowedCondition(infrav1.ClusterStaticIdentityKind, identityObjectKey, clusterScoper) - return nil, errors.Errorf(notPermittedError, infrav1.ClusterStaticIdentityKind, identityObjectKey.Name) - } - setPrincipalUsageAllowedCondition(clusterScoper) - - return identityv2.NewAWSStaticPrincipalTypeProvider(staticPrincipal, secret), nil -} - func buildAWSClusterControllerIdentity(ctx context.Context, identityObjectKey client.ObjectKey, k8sClient client.Client, clusterScoper cloud.SessionMetadata) error { controllerIdentity := &infrav1.AWSClusterControllerIdentity{} controllerIdentity.Kind = string(infrav1.ControllerIdentityKind) @@ -551,16 +384,6 @@ func getProvidersForCluster(ctx context.Context, k8sClient client.Client, cluste return providers, nil } -func getProvidersForClusterV2(ctx context.Context, k8sClient client.Client, clusterScoper cloud.SessionMetadata, region string, log logger.Wrapper) ([]identityv2.AWSPrincipalTypeProvider, error) { - providers := make([]identityv2.AWSPrincipalTypeProvider, 0) - providers, err := buildProvidersForRefV2(ctx, providers, k8sClient, clusterScoper, clusterScoper.IdentityRef(), region, log) - if err != nil { - return nil, err - } - - return providers, nil -} - func isClusterPermittedToUsePrincipal(k8sClient client.Client, allowedNs *infrav1.AllowedNamespaces, clusterNamespace string) (bool, error) { // nil value does not match with any namespaces if allowedNs == nil { @@ -604,7 +427,7 @@ func isClusterPermittedToUsePrincipal(k8sClient client.Client, allowedNs *infrav } // NewChainCredentialsProvider initializes a new ChainCredentialsProvider. -func NewChainCredentialsProvider(providers []awsv2.CredentialsProvider) *ChainCredentialsProvider { +func NewChainCredentialsProvider(providers []aws.CredentialsProvider) *ChainCredentialsProvider { return &ChainCredentialsProvider{ providers: providers, } @@ -612,7 +435,7 @@ func NewChainCredentialsProvider(providers []awsv2.CredentialsProvider) *ChainCr // Retrieve implements aws.CredentialsProvider for custom list of credenetials providers. // The first provider in the list without error will be used to return credentials. -func (c *ChainCredentialsProvider) Retrieve(ctx context.Context) (awsv2.Credentials, error) { +func (c *ChainCredentialsProvider) Retrieve(ctx context.Context) (aws.Credentials, error) { var lastErr error for _, provider := range c.providers { creds, err := provider.Retrieve(ctx) @@ -624,5 +447,5 @@ func (c *ChainCredentialsProvider) Retrieve(ctx context.Context) (awsv2.Credenti return creds, nil } } - return awsv2.Credentials{}, lastErr + return aws.Credentials{}, lastErr } diff --git a/pkg/cloud/services/autoscaling/autoscalinggroup.go b/pkg/cloud/services/autoscaling/autoscalinggroup.go index aa5891809c..f09538e56f 100644 --- a/pkg/cloud/services/autoscaling/autoscalinggroup.go +++ b/pkg/cloud/services/autoscaling/autoscalinggroup.go @@ -24,11 +24,11 @@ import ( "strings" "time" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/autoscaling" autoscalingtypes "github.com/aws/aws-sdk-go-v2/service/autoscaling/types" "github.com/aws/aws-sdk-go-v2/service/ec2" ec2types "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/pkg/errors" "k8s.io/utils/ptr" @@ -45,13 +45,13 @@ import ( // SDKToAutoScalingGroup converts an AWS EC2 SDK AutoScalingGroup to the CAPA AutoScalingGroup type. func (s *Service) SDKToAutoScalingGroup(v *autoscalingtypes.AutoScalingGroup) (*expinfrav1.AutoScalingGroup, error) { i := &expinfrav1.AutoScalingGroup{ - ID: aws.StringValue(v.AutoScalingGroupARN), - Name: aws.StringValue(v.AutoScalingGroupName), + ID: aws.ToString(v.AutoScalingGroupARN), + Name: aws.ToString(v.AutoScalingGroupName), // TODO(rudoi): this is just terrible DesiredCapacity: v.DesiredCapacity, - MaxSize: aws.Int32Value(v.MaxSize), //#nosec G115 - MinSize: aws.Int32Value(v.MinSize), //#nosec G115 - CapacityRebalance: aws.BoolValue(v.CapacityRebalance), + MaxSize: aws.ToInt32(v.MaxSize), //#nosec G115 + MinSize: aws.ToInt32(v.MinSize), //#nosec G115 + CapacityRebalance: aws.ToBool(v.CapacityRebalance), // TODO: determine what additional values go here and what else should be in the struct } @@ -68,10 +68,10 @@ func (s *Service) SDKToAutoScalingGroup(v *autoscalingtypes.AutoScalingGroup) (* } for _, override := range v.MixedInstancesPolicy.LaunchTemplate.Overrides { - i.MixedInstancesPolicy.Overrides = append(i.MixedInstancesPolicy.Overrides, expinfrav1.Overrides{InstanceType: aws.StringValue(override.InstanceType)}) + i.MixedInstancesPolicy.Overrides = append(i.MixedInstancesPolicy.Overrides, expinfrav1.Overrides{InstanceType: aws.ToString(override.InstanceType)}) } - onDemandAllocationStrategy := aws.StringValue(v.MixedInstancesPolicy.InstancesDistribution.OnDemandAllocationStrategy) + onDemandAllocationStrategy := aws.ToString(v.MixedInstancesPolicy.InstancesDistribution.OnDemandAllocationStrategy) switch onDemandAllocationStrategy { case string(expinfrav1.OnDemandAllocationStrategyPrioritized): i.MixedInstancesPolicy.InstancesDistribution.OnDemandAllocationStrategy = expinfrav1.OnDemandAllocationStrategyPrioritized @@ -81,7 +81,7 @@ func (s *Service) SDKToAutoScalingGroup(v *autoscalingtypes.AutoScalingGroup) (* return nil, fmt.Errorf("unsupported on-demand allocation strategy: %s", onDemandAllocationStrategy) } - spotAllocationStrategy := aws.StringValue(v.MixedInstancesPolicy.InstancesDistribution.SpotAllocationStrategy) + spotAllocationStrategy := aws.ToString(v.MixedInstancesPolicy.InstancesDistribution.SpotAllocationStrategy) switch spotAllocationStrategy { case string(expinfrav1.SpotAllocationStrategyLowestPrice): i.MixedInstancesPolicy.InstancesDistribution.SpotAllocationStrategy = expinfrav1.SpotAllocationStrategyLowestPrice @@ -107,7 +107,7 @@ func (s *Service) SDKToAutoScalingGroup(v *autoscalingtypes.AutoScalingGroup) (* if len(v.Instances) > 0 { for _, autoscalingInstance := range v.Instances { tmp := &infrav1.Instance{ - ID: aws.StringValue(autoscalingInstance.InstanceId), + ID: aws.ToString(autoscalingInstance.InstanceId), State: infrav1.InstanceState(autoscalingInstance.LifecycleState), AvailabilityZone: *autoscalingInstance.AvailabilityZone, } @@ -118,7 +118,7 @@ func (s *Service) SDKToAutoScalingGroup(v *autoscalingtypes.AutoScalingGroup) (* if len(v.SuspendedProcesses) > 0 { currentlySuspendedProcesses := make([]string, len(v.SuspendedProcesses)) for i, service := range v.SuspendedProcesses { - currentlySuspendedProcesses[i] = aws.StringValue(service.ProcessName) + currentlySuspendedProcesses[i] = aws.ToString(service.ProcessName) } i.CurrentlySuspendProcesses = currentlySuspendedProcesses } @@ -508,7 +508,7 @@ func (s *Service) SubnetIDs(scope *scope.MachinePoolScope) ([]string, error) { for _, subnet := range scope.AWSMachinePool.Spec.Subnets { switch { case subnet.ID != nil: - subnetIDs = append(subnetIDs, aws.StringValue(subnet.ID)) + subnetIDs = append(subnetIDs, aws.ToString(subnet.ID)) case subnet.Filters != nil: for _, eachFilter := range subnet.Filters { inputFilters = append(inputFilters, ec2types.Filter{ diff --git a/pkg/cloud/services/autoscaling/autoscalinggroup_test.go b/pkg/cloud/services/autoscaling/autoscalinggroup_test.go index 0de5f7ecea..53f1222072 100644 --- a/pkg/cloud/services/autoscaling/autoscalinggroup_test.go +++ b/pkg/cloud/services/autoscaling/autoscalinggroup_test.go @@ -21,12 +21,11 @@ import ( "sort" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/autoscaling" autoscalingtypes "github.com/aws/aws-sdk-go-v2/service/autoscaling/types" "github.com/aws/aws-sdk-go-v2/service/ec2" ec2types "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/request" "github.com/golang/mock/gomock" "github.com/google/go-cmp/cmp" "github.com/google/go-cmp/cmp/cmpopts" @@ -551,7 +550,7 @@ func TestServiceCreateASG(t *testing.T) { } m.CreateAutoScalingGroup(context.TODO(), gomock.AssignableToTypeOf(&autoscaling.CreateAutoScalingGroupInput{})).Do( - func(ctx context.Context, actual *autoscaling.CreateAutoScalingGroupInput, requestOptions ...request.Option) (*autoscaling.CreateAutoScalingGroupOutput, error) { + func(ctx context.Context, actual *autoscaling.CreateAutoScalingGroupInput, requestOptions ...autoscaling.Options) (*autoscaling.CreateAutoScalingGroupOutput, error) { sortTagsByKey := func(tags []autoscalingtypes.Tag) { sort.Slice(tags, func(i, j int) bool { return *(tags[i].Key) < *(tags[j].Key) @@ -589,7 +588,7 @@ func TestServiceCreateASG(t *testing.T) { wantErr: false, expect: func(m *mock_autoscalingiface.MockAutoScalingAPIMockRecorder) { m.CreateAutoScalingGroup(context.TODO(), gomock.AssignableToTypeOf(&autoscaling.CreateAutoScalingGroupInput{})).Do( - func(ctx context.Context, actual *autoscaling.CreateAutoScalingGroupInput, requestOptions ...request.Option) (*autoscaling.CreateAutoScalingGroupOutput, error) { + func(ctx context.Context, actual *autoscaling.CreateAutoScalingGroupInput, requestOptions ...autoscaling.Options) (*autoscaling.CreateAutoScalingGroupOutput, error) { if actual.DesiredCapacity != nil { t.Fatalf("Actual DesiredCapacity did not match expected, Actual: %d, Expected: ", *actual.DesiredCapacity) } @@ -611,7 +610,7 @@ func TestServiceCreateASG(t *testing.T) { wantErr: false, expect: func(m *mock_autoscalingiface.MockAutoScalingAPIMockRecorder) { m.CreateAutoScalingGroup(context.TODO(), gomock.AssignableToTypeOf(&autoscaling.CreateAutoScalingGroupInput{})).Do( - func(ctx context.Context, actual *autoscaling.CreateAutoScalingGroupInput, requestOptions ...request.Option) (*autoscaling.CreateAutoScalingGroupOutput, error) { + func(ctx context.Context, actual *autoscaling.CreateAutoScalingGroupInput, requestOptions ...autoscaling.Options) (*autoscaling.CreateAutoScalingGroupOutput, error) { if actual.DesiredCapacity != nil { t.Fatalf("Actual DesiredCapacity did not match expected, Actual: %d, Expected: ", *actual.DesiredCapacity) } @@ -724,7 +723,7 @@ func TestServiceUpdateASG(t *testing.T) { mps.AWSMachinePool.Spec.MaxSize = 5 }, expect: func(e *mocks.MockEC2APIMockRecorder, m *mock_autoscalingiface.MockAutoScalingAPIMockRecorder, g *WithT) { - m.UpdateAutoScalingGroup(context.TODO(), gomock.AssignableToTypeOf(&autoscaling.UpdateAutoScalingGroupInput{})).DoAndReturn(func(ctx context.Context, input *autoscaling.UpdateAutoScalingGroupInput, options ...request.Option) (*autoscaling.UpdateAutoScalingGroupOutput, error) { + m.UpdateAutoScalingGroup(context.TODO(), gomock.AssignableToTypeOf(&autoscaling.UpdateAutoScalingGroupInput{})).DoAndReturn(func(ctx context.Context, input *autoscaling.UpdateAutoScalingGroupInput, options ...autoscaling.Options) (*autoscaling.UpdateAutoScalingGroupOutput, error) { // CAPA should set min/max, and because there's no "externally managed" annotation, also the // "desired" number of instances g.Expect(input.MinSize).To(BeComparableTo(ptr.To[int32](2))) @@ -757,7 +756,7 @@ func TestServiceUpdateASG(t *testing.T) { mps.AWSMachinePool.Spec.MaxSize = 50 }, expect: func(e *mocks.MockEC2APIMockRecorder, m *mock_autoscalingiface.MockAutoScalingAPIMockRecorder, g *WithT) { - m.UpdateAutoScalingGroup(context.TODO(), gomock.AssignableToTypeOf(&autoscaling.UpdateAutoScalingGroupInput{})).DoAndReturn(func(ctx context.Context, input *autoscaling.UpdateAutoScalingGroupInput, options ...request.Option) (*autoscaling.UpdateAutoScalingGroupOutput, error) { + m.UpdateAutoScalingGroup(context.TODO(), gomock.AssignableToTypeOf(&autoscaling.UpdateAutoScalingGroupInput{})).DoAndReturn(func(ctx context.Context, input *autoscaling.UpdateAutoScalingGroupInput, options ...autoscaling.Options) (*autoscaling.UpdateAutoScalingGroupOutput, error) { // CAPA should set min/max, but not the externally managed "desired" number of instances g.Expect(input.MinSize).To(BeComparableTo(ptr.To[int32](20))) g.Expect(input.MaxSize).To(BeComparableTo(ptr.To[int32](50))) diff --git a/pkg/cloud/services/autoscaling/lifecyclehook.go b/pkg/cloud/services/autoscaling/lifecyclehook.go index 9f153fe0f4..293070fab1 100644 --- a/pkg/cloud/services/autoscaling/lifecyclehook.go +++ b/pkg/cloud/services/autoscaling/lifecyclehook.go @@ -20,9 +20,9 @@ import ( "context" "time" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/autoscaling" autoscalingtypes "github.com/aws/aws-sdk-go-v2/service/autoscaling/types" - "github.com/aws/aws-sdk-go/aws" "github.com/pkg/errors" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/utils/ptr" diff --git a/pkg/cloud/services/ec2/ami.go b/pkg/cloud/services/ec2/ami.go index e6f476b780..769280cd8e 100644 --- a/pkg/cloud/services/ec2/ami.go +++ b/pkg/cloud/services/ec2/ami.go @@ -25,19 +25,19 @@ import ( "text/template" "time" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" ec2types "github.com/aws/aws-sdk-go-v2/service/ec2/types" "github.com/aws/aws-sdk-go-v2/service/ssm" - "github.com/aws/aws-sdk-go/aws" "github.com/blang/semver" "github.com/pkg/errors" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" "sigs.k8s.io/cluster-api-provider-aws/v2/cmd/clusterawsadm/api/bootstrap/v1beta1" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/awserrors" + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/endpoints" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/services/common" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/record" - "sigs.k8s.io/cluster-api-provider-aws/v2/util/system" ) const ( @@ -234,8 +234,8 @@ func (s *Service) defaultAMIIDLookup(amiNameFormat, ownerID, baseOS, architectur return "", errors.Wrapf(err, "failed to find ami") } - s.scope.Debug("Found and using an existing AMI", "ami-id", aws.StringValue(latestImage.ImageId)) - return aws.StringValue(latestImage.ImageId), nil + s.scope.Debug("Found and using an existing AMI", "ami-id", aws.ToString(latestImage.ImageId)) + return aws.ToString(latestImage.ImageId), nil } type images []ec2types.Image @@ -249,8 +249,8 @@ func (i images) Len() int { // index i should sort before the element with index j. // At this point all CreationDates have been checked for errors so ignoring the error is ok. func (i images) Less(k, j int) bool { - firstTime, _ := time.Parse(createDateTimestampFormat, aws.StringValue(i[k].CreationDate)) - secondTime, _ := time.Parse(createDateTimestampFormat, aws.StringValue(i[j].CreationDate)) + firstTime, _ := time.Parse(createDateTimestampFormat, aws.ToString(i[k].CreationDate)) + secondTime, _ := time.Parse(createDateTimestampFormat, aws.ToString(i[j].CreationDate)) return firstTime.Before(secondTime) } @@ -262,7 +262,7 @@ func (i images) Swap(k, j int) { // GetLatestImage assumes imgs is not empty. Responsibility of the caller to check. func GetLatestImage(imgs []ec2types.Image) (*ec2types.Image, error) { for _, img := range imgs { - if _, err := time.Parse(createDateTimestampFormat, aws.StringValue(img.CreationDate)); err != nil { + if _, err := time.Parse(createDateTimestampFormat, aws.ToString(img.CreationDate)); err != nil { return nil, err } } @@ -294,7 +294,7 @@ func (s *Service) defaultBastionAMILookup() (string, error) { } ownerID := ubuntuOwnerID - partition := system.GetPartitionFromRegion(s.scope.Region()) + partition := endpoints.GetPartitionFromRegion(s.scope.Region()) if strings.Contains(partition, v1beta1.PartitionNameUSGov) { ownerID = ubuntuOwnerIDUsGov } @@ -371,7 +371,7 @@ func (s *Service) eksAMILookup(ctx context.Context, kubernetesVersion string, ar return "", errors.Errorf("SSM parameter returned with nil value: %q", paramName) } - id := aws.StringValue(out.Parameter.Value) + id := aws.ToString(out.Parameter.Value) s.scope.Info("found AMI", "id", id, "version", formattedVersion) return id, nil diff --git a/pkg/cloud/services/ec2/ami_test.go b/pkg/cloud/services/ec2/ami_test.go index b2e7e831b4..af859b8434 100644 --- a/pkg/cloud/services/ec2/ami_test.go +++ b/pkg/cloud/services/ec2/ami_test.go @@ -20,11 +20,11 @@ import ( "context" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" ec2types "github.com/aws/aws-sdk-go-v2/service/ec2/types" "github.com/aws/aws-sdk-go-v2/service/ssm" ssmtypes "github.com/aws/aws-sdk-go-v2/service/ssm/types" - "github.com/aws/aws-sdk-go/aws" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" "sigs.k8s.io/controller-runtime/pkg/client/fake" diff --git a/pkg/cloud/services/ec2/bastion.go b/pkg/cloud/services/ec2/bastion.go index 72c4f7fd0d..8d31916530 100644 --- a/pkg/cloud/services/ec2/bastion.go +++ b/pkg/cloud/services/ec2/bastion.go @@ -22,9 +22,9 @@ import ( "fmt" "strings" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/pkg/errors" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" diff --git a/pkg/cloud/services/ec2/bastion_test.go b/pkg/cloud/services/ec2/bastion_test.go index 511f8a916d..e48a540935 100644 --- a/pkg/cloud/services/ec2/bastion_test.go +++ b/pkg/cloud/services/ec2/bastion_test.go @@ -21,9 +21,9 @@ import ( "fmt" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" "github.com/pkg/errors" diff --git a/pkg/cloud/services/ec2/eip.go b/pkg/cloud/services/ec2/eip.go index 2822ae80b4..449272da48 100644 --- a/pkg/cloud/services/ec2/eip.go +++ b/pkg/cloud/services/ec2/eip.go @@ -4,8 +4,8 @@ import ( "context" "fmt" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" - "github.com/aws/aws-sdk-go/aws" "k8s.io/utils/ptr" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" diff --git a/pkg/cloud/services/ec2/helper_test.go b/pkg/cloud/services/ec2/helper_test.go index 7e77aa34db..bd40c2b7bb 100644 --- a/pkg/cloud/services/ec2/helper_test.go +++ b/pkg/cloud/services/ec2/helper_test.go @@ -19,8 +19,8 @@ package ec2 import ( "sort" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" corev1 "k8s.io/api/core/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" diff --git a/pkg/cloud/services/ec2/instances_test.go b/pkg/cloud/services/ec2/instances_test.go index f454a36727..71ec44c01a 100644 --- a/pkg/cloud/services/ec2/instances_test.go +++ b/pkg/cloud/services/ec2/instances_test.go @@ -22,11 +22,10 @@ import ( "strings" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/awserr" - "github.com/aws/aws-sdk-go/aws/request" + "github.com/aws/smithy-go" "github.com/golang/mock/gomock" "github.com/google/go-cmp/cmp" "github.com/google/go-cmp/cmp/cmpopts" @@ -83,7 +82,10 @@ func TestInstanceIfExists(t *testing.T) { m.DescribeInstances(context.TODO(), gomock.Eq(&ec2.DescribeInstancesInput{ InstanceIds: []string{"hello-does-not-exist"}, })). - Return(nil, awserr.New(awserrors.InvalidInstanceID, "does not exist", nil)) + Return(nil, &smithy.GenericAPIError{ + Code: awserrors.InvalidInstanceID, + Message: "does not exist", + }) }, check: func(instance *infrav1.Instance, err error) { if err == nil { @@ -2397,14 +2399,14 @@ func TestCreateInstance(t *testing.T) { }, nil) m. RunInstances(context.TODO(), gomock.Any()). - Do(func(_ context.Context, in *ec2.RunInstancesInput, _ ...request.Option) { + Do(func(_ context.Context, in *ec2.RunInstancesInput, _ ...ec2.Options) { if len(in.NetworkInterfaces) == 0 { t.Fatalf("expected a NetworkInterface to be defined") } - if !aws.BoolValue(in.NetworkInterfaces[0].AssociatePublicIpAddress) { + if !aws.ToBool(in.NetworkInterfaces[0].AssociatePublicIpAddress) { t.Fatalf("expected AssociatePublicIpAddress to be set and true") } - if subnet := aws.StringValue(in.NetworkInterfaces[0].SubnetId); subnet != "public-subnet-1" { + if subnet := aws.ToString(in.NetworkInterfaces[0].SubnetId); subnet != "public-subnet-1" { t.Fatalf("expected subnet ID to be \"public-subnet-1\", got %q", subnet) } if in.NetworkInterfaces[0].Groups == nil { @@ -2528,14 +2530,14 @@ func TestCreateInstance(t *testing.T) { }, nil) m. RunInstances(context.TODO(), gomock.Any()). - Do(func(_ context.Context, in *ec2.RunInstancesInput, _ ...request.Option) { + Do(func(_ context.Context, in *ec2.RunInstancesInput, _ ...ec2.Options) { if len(in.NetworkInterfaces) == 0 { t.Fatalf("expected a NetworkInterface to be defined") } if in.NetworkInterfaces[0].Groups == nil { t.Fatalf("expected security groups to be set") } - if interfaceType := aws.StringValue(in.NetworkInterfaces[0].InterfaceType); interfaceType != "efa" { + if interfaceType := aws.ToString(in.NetworkInterfaces[0].InterfaceType); interfaceType != "efa" { t.Fatalf("expected interface type to be \"efa\": got %q", interfaceType) } }). @@ -2911,14 +2913,14 @@ func TestCreateInstance(t *testing.T) { }, nil) m. RunInstances(context.TODO(), gomock.Any()). - Do(func(_ context.Context, in *ec2.RunInstancesInput, _ ...request.Option) { + Do(func(_ context.Context, in *ec2.RunInstancesInput, _ ...ec2.Options) { if len(in.NetworkInterfaces) == 0 { t.Fatalf("expected a NetworkInterface to be defined") } - if !aws.BoolValue(in.NetworkInterfaces[0].AssociatePublicIpAddress) { + if !aws.ToBool(in.NetworkInterfaces[0].AssociatePublicIpAddress) { t.Fatalf("expected AssociatePublicIpAddress to be set and true") } - if subnet := aws.StringValue(in.NetworkInterfaces[0].SubnetId); subnet != "public-subnet-1" { + if subnet := aws.ToString(in.NetworkInterfaces[0].SubnetId); subnet != "public-subnet-1" { t.Fatalf("expected subnet ID to be \"public-subnet-1\", got %q", subnet) } if in.NetworkInterfaces[0].Groups == nil { @@ -3161,14 +3163,14 @@ func TestCreateInstance(t *testing.T) { }, nil) m. RunInstances(context.TODO(), gomock.Any()). - Do(func(_ context.Context, in *ec2.RunInstancesInput, _ ...request.Option) { + Do(func(_ context.Context, in *ec2.RunInstancesInput, _ ...ec2.Options) { if len(in.NetworkInterfaces) == 0 { t.Fatalf("expected a NetworkInterface to be defined") } - if !aws.BoolValue(in.NetworkInterfaces[0].AssociatePublicIpAddress) { + if !aws.ToBool(in.NetworkInterfaces[0].AssociatePublicIpAddress) { t.Fatalf("expected AssociatePublicIpAddress to be set and true") } - if subnet := aws.StringValue(in.NetworkInterfaces[0].SubnetId); subnet != "public-subnet-1" { + if subnet := aws.ToString(in.NetworkInterfaces[0].SubnetId); subnet != "public-subnet-1" { t.Fatalf("expected subnet ID to be \"public-subnet-1\", got %q", subnet) } if in.NetworkInterfaces[0].Groups == nil { @@ -4452,7 +4454,7 @@ func TestCreateInstance(t *testing.T) { }, nil) m. // TODO: Restore these parameters, but with the tags as well RunInstances(context.TODO(), gomock.Any()). - DoAndReturn(func(ctx context.Context, input *ec2.RunInstancesInput, requestOptions ...request.Option) (*ec2.RunInstancesOutput, error) { + DoAndReturn(func(ctx context.Context, input *ec2.RunInstancesInput, requestOptions ...ec2.Options) (*ec2.RunInstancesOutput, error) { if input.KeyName == nil { t.Fatal("Expected key name not to be nil") } @@ -4585,7 +4587,7 @@ func TestCreateInstance(t *testing.T) { }, nil) m. // TODO: Restore these parameters, but with the tags as well RunInstances(context.TODO(), gomock.Any()). - DoAndReturn(func(ctx context.Context, input *ec2.RunInstancesInput, requestOptions ...request.Option) (*ec2.RunInstancesOutput, error) { + DoAndReturn(func(ctx context.Context, input *ec2.RunInstancesInput, requestOptions ...ec2.Options) (*ec2.RunInstancesOutput, error) { if input.KeyName == nil { t.Fatal("Expected key name not to be nil") } @@ -4719,7 +4721,7 @@ func TestCreateInstance(t *testing.T) { }, nil) m. // TODO: Restore these parameters, but with the tags as well RunInstances(context.TODO(), gomock.Any()). - DoAndReturn(func(ctx context.Context, input *ec2.RunInstancesInput, requestOptions ...request.Option) (*ec2.RunInstancesOutput, error) { + DoAndReturn(func(ctx context.Context, input *ec2.RunInstancesInput, requestOptions ...ec2.Options) (*ec2.RunInstancesOutput, error) { if input.KeyName == nil { t.Fatal("Expected key name not to be nil") } @@ -4853,7 +4855,7 @@ func TestCreateInstance(t *testing.T) { }, nil) m. // TODO: Restore these parameters, but with the tags as well RunInstances(context.TODO(), gomock.Any()). - DoAndReturn(func(ctx context.Context, input *ec2.RunInstancesInput, requestOptions ...request.Option) (*ec2.RunInstancesOutput, error) { + DoAndReturn(func(ctx context.Context, input *ec2.RunInstancesInput, requestOptions ...ec2.Options) (*ec2.RunInstancesOutput, error) { if input.KeyName != nil { t.Fatalf("Expected key name to be nil/unspecified, not '%s'", *input.KeyName) } @@ -4984,7 +4986,7 @@ func TestCreateInstance(t *testing.T) { }, nil) m. // TODO: Restore these parameters, but with the tags as well RunInstances(context.TODO(), gomock.Any()). - DoAndReturn(func(ctx context.Context, input *ec2.RunInstancesInput, requestOptions ...request.Option) (*ec2.RunInstancesOutput, error) { + DoAndReturn(func(ctx context.Context, input *ec2.RunInstancesInput, requestOptions ...ec2.Options) (*ec2.RunInstancesOutput, error) { if input.KeyName != nil { t.Fatalf("Expected key name to be nil/unspecified, not '%s'", *input.KeyName) } @@ -5115,7 +5117,7 @@ func TestCreateInstance(t *testing.T) { }, nil) m. // TODO: Restore these parameters, but with the tags as well RunInstances(context.TODO(), gomock.Any()). - DoAndReturn(func(ctx context.Context, input *ec2.RunInstancesInput, requestOptions ...request.Option) (*ec2.RunInstancesOutput, error) { + DoAndReturn(func(ctx context.Context, input *ec2.RunInstancesInput, requestOptions ...ec2.Options) (*ec2.RunInstancesOutput, error) { if input.KeyName != nil { t.Fatalf("Expected key name to be nil/unspecified, not '%s'", *input.KeyName) } diff --git a/pkg/cloud/services/ec2/launchtemplate.go b/pkg/cloud/services/ec2/launchtemplate.go index ad664ebe6d..3eefb51ed0 100644 --- a/pkg/cloud/services/ec2/launchtemplate.go +++ b/pkg/cloud/services/ec2/launchtemplate.go @@ -24,9 +24,9 @@ import ( "strconv" "strings" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/blang/semver" ignTypes "github.com/coreos/ignition/config/v2_3/types" ignV3Types "github.com/coreos/ignition/v2/config/v3_4/types" @@ -519,7 +519,7 @@ func (s *Service) GetLaunchTemplateID(launchTemplateName string) (string, error) return "", nil } - return aws.StringValue(out.LaunchTemplateVersions[0].LaunchTemplateId), nil + return aws.ToString(out.LaunchTemplateVersions[0].LaunchTemplateId), nil } // CreateLaunchTemplate generates a launch template to be used with the autoscaling group. @@ -563,7 +563,7 @@ func (s *Service) CreateLaunchTemplate(scope scope.LaunchTemplateScope, imageID if err != nil { return "", err } - return aws.StringValue(result.LaunchTemplate.LaunchTemplateId), nil + return aws.ToString(result.LaunchTemplate.LaunchTemplateId), nil } // CreateLaunchTemplateVersion will create a launch template. @@ -661,7 +661,7 @@ func (s *Service) createLaunchTemplateData(scope scope.LaunchTemplateScope, imag return nil, err } - lt.RootVolume.DeviceName = aws.StringValue(rootDeviceName) + lt.RootVolume.DeviceName = aws.ToString(rootDeviceName) req := volumeToLaunchTemplateBlockDeviceMappingRequest(lt.RootVolume) blockDeviceMappings = append(blockDeviceMappings, *req) @@ -882,7 +882,7 @@ func CapacityReservationPreferenceToSDK(preference infrav1.CapacityReservationPr func (s *Service) SDKToLaunchTemplate(d types.LaunchTemplateVersion) (*expinfrav1.AWSLaunchTemplate, string, *apimachinerytypes.NamespacedName, *string, error) { v := d.LaunchTemplateData i := &expinfrav1.AWSLaunchTemplate{ - Name: aws.StringValue(d.LaunchTemplateName), + Name: aws.ToString(d.LaunchTemplateName), AMI: infrav1.AMIReference{ ID: v.ImageId, }, @@ -922,12 +922,12 @@ func (s *Service) SDKToLaunchTemplate(d types.LaunchTemplateVersion) (*expinfrav } if v.IamInstanceProfile != nil { - i.IamInstanceProfile = aws.StringValue(v.IamInstanceProfile.Name) + i.IamInstanceProfile = aws.ToString(v.IamInstanceProfile.Name) } // Extract IAM Instance Profile name from ARN if v.IamInstanceProfile != nil && v.IamInstanceProfile.Arn != nil { - split := strings.Split(aws.StringValue(v.IamInstanceProfile.Arn), "instance-profile/") + split := strings.Split(aws.ToString(v.IamInstanceProfile.Arn), "instance-profile/") if len(split) > 1 && split[1] != "" { i.IamInstanceProfile = split[1] } @@ -1227,7 +1227,7 @@ func getLaunchTemplateInstanceMarketOptionsRequest(i *expinfrav1.AWSLaunchTempla // Persistent option is not available for EC2 autoscaling, EC2 makes a one-time request by default and setting request type should not be allowed. // For one-time requests, only terminate option is available as interruption behavior, and default for spotOptions.SetInstanceInterruptionBehavior() is terminate, so it is not set here explicitly. - if maxPrice := aws.StringValue(i.SpotMarketOptions.MaxPrice); maxPrice != "" { + if maxPrice := aws.ToString(i.SpotMarketOptions.MaxPrice); maxPrice != "" { spotOptions.MaxPrice = aws.String(maxPrice) } @@ -1253,6 +1253,6 @@ func getLaunchTemplatePrivateDNSNameOptionsRequest(privateDNSName *infrav1.Priva return &types.LaunchTemplatePrivateDnsNameOptionsRequest{ EnableResourceNameDnsAAAARecord: privateDNSName.EnableResourceNameDNSAAAARecord, EnableResourceNameDnsARecord: privateDNSName.EnableResourceNameDNSARecord, - HostnameType: types.HostnameType(aws.StringValue(privateDNSName.HostnameType)), + HostnameType: types.HostnameType(aws.ToString(privateDNSName.HostnameType)), } } diff --git a/pkg/cloud/services/ec2/launchtemplate_test.go b/pkg/cloud/services/ec2/launchtemplate_test.go index 438ceaef66..fd4ff8c81a 100644 --- a/pkg/cloud/services/ec2/launchtemplate_test.go +++ b/pkg/cloud/services/ec2/launchtemplate_test.go @@ -21,13 +21,11 @@ import ( "encoding/base64" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" ec2types "github.com/aws/aws-sdk-go-v2/service/ec2/types" "github.com/aws/aws-sdk-go-v2/service/ssm" ssmtypes "github.com/aws/aws-sdk-go-v2/service/ssm/types" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/awserr" - "github.com/aws/aws-sdk-go/aws/request" "github.com/aws/smithy-go" "github.com/golang/mock/gomock" "github.com/google/go-cmp/cmp" @@ -984,11 +982,10 @@ func TestGetLaunchTemplateID(t *testing.T) { m.DescribeLaunchTemplateVersions(context.TODO(), gomock.Eq(&ec2.DescribeLaunchTemplateVersionsInput{ LaunchTemplateName: aws.String("foo"), Versions: []string{"$Latest"}, - })).Return(nil, awserr.New( - awserrors.LaunchTemplateNameNotFound, - "The specified launch template, with template name foo, does not exist.", - nil, - )) + })).Return(nil, &smithy.GenericAPIError{ + Code: awserrors.LaunchTemplateNameNotFound, + Message: "The specified launch template, with template name foo, does not exist.", + }) }, check: func(g *WithT, launchTemplateID string, err error) { g.Expect(err).NotTo(HaveOccurred()) @@ -1221,7 +1218,7 @@ func TestCreateLaunchTemplate(t *testing.T) { LaunchTemplate: &ec2types.LaunchTemplate{ LaunchTemplateId: aws.String("launch-template-id"), }, - }, nil).Do(func(ctx context.Context, arg *ec2.CreateLaunchTemplateInput, requestOptions ...request.Option) { + }, nil).Do(func(ctx context.Context, arg *ec2.CreateLaunchTemplateInput, requestOptions ...ec2.Options) { // formatting added to match arrays during cmp.Equal formatTagsInput(arg) if !cmp.Equal(expectedInput, arg, cmpopts.IgnoreUnexported( @@ -1290,7 +1287,7 @@ func TestCreateLaunchTemplate(t *testing.T) { LaunchTemplate: &ec2types.LaunchTemplate{ LaunchTemplateId: aws.String("launch-template-id"), }, - }, nil).Do(func(ctx context.Context, arg *ec2.CreateLaunchTemplateInput, requestOptions ...request.Option) { + }, nil).Do(func(ctx context.Context, arg *ec2.CreateLaunchTemplateInput, requestOptions ...ec2.Options) { // formatting added to match arrays during reflect.DeepEqual formatTagsInput(arg) if !cmp.Equal(expectedInput, arg, cmpopts.IgnoreUnexported( @@ -1358,7 +1355,7 @@ func TestCreateLaunchTemplate(t *testing.T) { }, } m.CreateLaunchTemplate(context.TODO(), gomock.AssignableToTypeOf(expectedInput)).Return(nil, - awserrors.NewFailedDependency("dependency failure")).Do(func(ctx context.Context, arg *ec2.CreateLaunchTemplateInput, requestOptions ...request.Option) { + awserrors.NewFailedDependency("dependency failure")).Do(func(ctx context.Context, arg *ec2.CreateLaunchTemplateInput, requestOptions ...ec2.Options) { // formatting added to match arrays during cmp.Equal formatTagsInput(arg) if !cmp.Equal(expectedInput, arg, cmpopts.IgnoreUnexported( @@ -1516,7 +1513,7 @@ func TestCreateLaunchTemplateVersion(t *testing.T) { LaunchTemplateId: aws.String("launch-template-id"), }, }, nil).Do( - func(ctx context.Context, arg *ec2.CreateLaunchTemplateVersionInput, requestOptions ...request.Option) { + func(ctx context.Context, arg *ec2.CreateLaunchTemplateVersionInput, requestOptions ...ec2.Options) { // formatting added to match tags slice during cmp.Equal() formatTagsInput(arg) if !cmp.Equal(expectedInput, arg, LaunchTemplateVersionIgnoreUnexported) { @@ -1576,7 +1573,7 @@ func TestCreateLaunchTemplateVersion(t *testing.T) { LaunchTemplateId: aws.String("launch-template-id"), }, }, nil).Do( - func(ctx context.Context, arg *ec2.CreateLaunchTemplateVersionInput, requestOptions ...request.Option) { + func(ctx context.Context, arg *ec2.CreateLaunchTemplateVersionInput, requestOptions ...ec2.Options) { // formatting added to match tags slice during cmp.Equal() formatTagsInput(arg) if !cmp.Equal(expectedInput, arg, LaunchTemplateVersionIgnoreUnexported) { @@ -1634,7 +1631,7 @@ func TestCreateLaunchTemplateVersion(t *testing.T) { LaunchTemplateId: aws.String("launch-template-id"), }, }, nil).Do( - func(ctx context.Context, arg *ec2.CreateLaunchTemplateVersionInput, requestOptions ...request.Option) { + func(ctx context.Context, arg *ec2.CreateLaunchTemplateVersionInput, requestOptions ...ec2.Options) { // formatting added to match tags slice during cmp.Equal() formatTagsInput(arg) if !cmp.Equal(expectedInput, arg, LaunchTemplateVersionIgnoreUnexported) { @@ -1682,7 +1679,7 @@ func TestCreateLaunchTemplateVersion(t *testing.T) { } m.CreateLaunchTemplateVersion(context.TODO(), gomock.AssignableToTypeOf(expectedInput)).Return(nil, awserrors.NewFailedDependency("dependency failure")).Do( - func(ctx context.Context, arg *ec2.CreateLaunchTemplateVersionInput, requestOptions ...request.Option) { + func(ctx context.Context, arg *ec2.CreateLaunchTemplateVersionInput, requestOptions ...ec2.Options) { // formatting added to match tags slice during cmp.Equal() formatTagsInput(arg) if !cmp.Equal(expectedInput, arg, LaunchTemplateVersionIgnoreUnexported) { diff --git a/pkg/cloud/services/gc/cleanup_test.go b/pkg/cloud/services/gc/cleanup_test.go index 1e7c997a9b..363ed94364 100644 --- a/pkg/cloud/services/gc/cleanup_test.go +++ b/pkg/cloud/services/gc/cleanup_test.go @@ -26,7 +26,6 @@ import ( elbv2 "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancingv2" rgapi "github.com/aws/aws-sdk-go-v2/service/resourcegroupstaggingapi" rgapitypes "github.com/aws/aws-sdk-go-v2/service/resourcegroupstaggingapi/types" - "github.com/aws/aws-sdk-go/aws/request" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" corev1 "k8s.io/api/core/v1" @@ -73,7 +72,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{}, }, nil @@ -95,7 +94,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{}, }, nil @@ -117,7 +116,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{}, }, nil @@ -139,7 +138,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -171,7 +170,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -203,7 +202,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -243,7 +242,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -283,7 +282,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -323,7 +322,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -363,7 +362,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -403,7 +402,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -443,7 +442,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -483,7 +482,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -558,7 +557,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -598,7 +597,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -638,7 +637,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -713,7 +712,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { @@ -783,7 +782,7 @@ func TestReconcileDelete(t *testing.T) { Values: []string{"owned"}, }, }, - }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...request.Option) (*rgapi.GetResourcesOutput, error) { + }).DoAndReturn(func(awsCtx context.Context, input *rgapi.GetResourcesInput, opts ...rgapi.Options) (*rgapi.GetResourcesOutput, error) { return &rgapi.GetResourcesOutput{ ResourceTagMappingList: []rgapitypes.ResourceTagMapping{ { diff --git a/pkg/cloud/services/gc/ec2.go b/pkg/cloud/services/gc/ec2.go index 6b60cf07be..377f9539f3 100644 --- a/pkg/cloud/services/gc/ec2.go +++ b/pkg/cloud/services/gc/ec2.go @@ -25,7 +25,7 @@ import ( "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - converters "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/convertersv2" + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/converters" filter "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/filter" ) diff --git a/pkg/cloud/services/gc/loadbalancer.go b/pkg/cloud/services/gc/loadbalancer.go index 31b5aa6f4c..2d9e7d64c6 100644 --- a/pkg/cloud/services/gc/loadbalancer.go +++ b/pkg/cloud/services/gc/loadbalancer.go @@ -26,7 +26,7 @@ import ( elbv2 "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancingv2" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/convertersv2" + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/converters" ) func (s *Service) deleteLoadBalancers(ctx context.Context, resources []*AWSResource) error { @@ -222,7 +222,7 @@ func (s *Service) filterProviderOwnedLB(ctx context.Context, names []string) ([] serviceTag := infrav1.ClusterAWSCloudProviderTagKey(s.scope.KubernetesClusterName()) if *tag.Key == serviceTag && *tag.Value == string(infrav1.ResourceLifecycleOwned) { arn := composeFakeArn(elbService, elbResourcePrefix+*tagDesc.LoadBalancerName) - resource, err := composeAWSResource(arn, convertersv2.ELBTagsToMap(tagDesc.Tags)) + resource, err := composeAWSResource(arn, converters.ELBTagsToMap(tagDesc.Tags)) if err != nil { return nil, fmt.Errorf("error compose aws elb resource %s: %w", arn, err) } @@ -250,7 +250,7 @@ func (s *Service) filterProviderOwnedLBV2(ctx context.Context, arns []string) ([ for _, tag := range tagDesc.Tags { serviceTag := infrav1.ClusterAWSCloudProviderTagKey(s.scope.KubernetesClusterName()) if *tag.Key == serviceTag && *tag.Value == string(infrav1.ResourceLifecycleOwned) { - resource, err := composeAWSResource(*tagDesc.ResourceArn, convertersv2.V2TagsToMap(tagDesc.Tags)) + resource, err := composeAWSResource(*tagDesc.ResourceArn, converters.V2TagsToMap(tagDesc.Tags)) if err != nil { return nil, fmt.Errorf("error compose aws elbv2 resource %s: %w", *tagDesc.ResourceArn, err) } diff --git a/pkg/cloud/services/interfaces.go b/pkg/cloud/services/interfaces.go index f36788d4a5..65b08a2ecd 100644 --- a/pkg/cloud/services/interfaces.go +++ b/pkg/cloud/services/interfaces.go @@ -106,7 +106,7 @@ type MachinePoolReconcileInterface interface { type SecretInterface interface { Delete(m *scope.MachineScope) error Create(m *scope.MachineScope, data []byte) (string, int32, error) - UserData(secretPrefix string, chunks int32, region string, endpoints []scope.ServiceEndpoint) ([]byte, error) + UserData(secretPrefix string, chunks int32, region string) ([]byte, error) } // ELBInterface encapsulates the methods exposed to the cluster and machine diff --git a/pkg/cloud/services/mock_services/secretsmanager_machine_interface_mock.go b/pkg/cloud/services/mock_services/secretsmanager_machine_interface_mock.go index 6f1a515805..4054da1e3e 100644 --- a/pkg/cloud/services/mock_services/secretsmanager_machine_interface_mock.go +++ b/pkg/cloud/services/mock_services/secretsmanager_machine_interface_mock.go @@ -81,16 +81,16 @@ func (mr *MockSecretInterfaceMockRecorder) Delete(arg0 interface{}) *gomock.Call } // UserData mocks base method. -func (m *MockSecretInterface) UserData(arg0 string, arg1 int32, arg2 string, arg3 []scope.ServiceEndpoint) ([]byte, error) { +func (m *MockSecretInterface) UserData(arg0 string, arg1 int32, arg2 string) ([]byte, error) { m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "UserData", arg0, arg1, arg2, arg3) + ret := m.ctrl.Call(m, "UserData", arg0, arg1, arg2) ret0, _ := ret[0].([]byte) ret1, _ := ret[1].(error) return ret0, ret1 } // UserData indicates an expected call of UserData. -func (mr *MockSecretInterfaceMockRecorder) UserData(arg0, arg1, arg2, arg3 interface{}) *gomock.Call { +func (mr *MockSecretInterfaceMockRecorder) UserData(arg0, arg1, arg2 interface{}) *gomock.Call { mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UserData", reflect.TypeOf((*MockSecretInterface)(nil).UserData), arg0, arg1, arg2, arg3) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UserData", reflect.TypeOf((*MockSecretInterface)(nil).UserData), arg0, arg1, arg2) } diff --git a/pkg/cloud/services/network/carriergateways.go b/pkg/cloud/services/network/carriergateways.go index 5a4fa05b6b..af89c43bc4 100644 --- a/pkg/cloud/services/network/carriergateways.go +++ b/pkg/cloud/services/network/carriergateways.go @@ -20,9 +20,9 @@ import ( "context" "fmt" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/pkg/errors" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" diff --git a/pkg/cloud/services/network/carriergateways_test.go b/pkg/cloud/services/network/carriergateways_test.go index 12c86477a1..c23a873c02 100644 --- a/pkg/cloud/services/network/carriergateways_test.go +++ b/pkg/cloud/services/network/carriergateways_test.go @@ -20,9 +20,9 @@ import ( "context" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" diff --git a/pkg/cloud/services/network/egress_only_gateways.go b/pkg/cloud/services/network/egress_only_gateways.go index 8c734d8e46..e710adecf7 100644 --- a/pkg/cloud/services/network/egress_only_gateways.go +++ b/pkg/cloud/services/network/egress_only_gateways.go @@ -20,9 +20,9 @@ import ( "context" "fmt" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/pkg/errors" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" diff --git a/pkg/cloud/services/network/egress_only_gateways_test.go b/pkg/cloud/services/network/egress_only_gateways_test.go index f85714d95b..fbd859ab80 100644 --- a/pkg/cloud/services/network/egress_only_gateways_test.go +++ b/pkg/cloud/services/network/egress_only_gateways_test.go @@ -20,9 +20,9 @@ import ( "context" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" diff --git a/pkg/cloud/services/network/eips.go b/pkg/cloud/services/network/eips.go index 90d4c38daf..6ebd0ec7c4 100644 --- a/pkg/cloud/services/network/eips.go +++ b/pkg/cloud/services/network/eips.go @@ -20,9 +20,9 @@ import ( "context" "fmt" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/pkg/errors" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" @@ -43,7 +43,7 @@ func (s *Service) getOrAllocateAddresses(num int, role string, pool *infrav1.Ela // Reuse existing unallocated addreses with the same role. for _, address := range out.Addresses { if address.AssociationId == nil { - eips = append(eips, aws.StringValue(address.AllocationId)) + eips = append(eips, aws.ToString(address.AllocationId)) } } @@ -82,7 +82,7 @@ func (s *Service) allocateAddress(alloc *ec2.AllocateAddressInput) (string, erro return "", err } - return aws.StringValue(out.AllocationId), nil + return aws.ToString(out.AllocationId), nil } func (s *Service) describeAddresses(role string) (*ec2.DescribeAddressesOutput, error) { @@ -239,7 +239,7 @@ func (s *Service) publicIpv4PoolHasAtLeastNFreeIPs(pool *infrav1.ElasticIPPool, } publicIpv4Pool := pool.PublicIpv4Pool pools, err := s.EC2Client.DescribePublicIpv4Pools(context.TODO(), &ec2.DescribePublicIpv4PoolsInput{ - PoolIds: []string{aws.StringValue(publicIpv4Pool)}, + PoolIds: []string{aws.ToString(publicIpv4Pool)}, }) if err != nil { return false, fmt.Errorf("failed to describe Public IPv4 Pool %q: %w", *publicIpv4Pool, err) @@ -248,7 +248,7 @@ func (s *Service) publicIpv4PoolHasAtLeastNFreeIPs(pool *infrav1.ElasticIPPool, return false, fmt.Errorf("unexpected number of configured Public IPv4 Pools. want 1, got %d", len(pools.PublicIpv4Pools)) } - freeIPs := aws.Int32Value(pools.PublicIpv4Pools[0].TotalAvailableAddressCount) + freeIPs := aws.ToInt32(pools.PublicIpv4Pools[0].TotalAvailableAddressCount) hasFreeIPs := freeIPs >= want // force to fallback to Amazon pool when the custom pool is full. diff --git a/pkg/cloud/services/network/eips_test.go b/pkg/cloud/services/network/eips_test.go index d844663169..53dbc23dd2 100644 --- a/pkg/cloud/services/network/eips_test.go +++ b/pkg/cloud/services/network/eips_test.go @@ -20,9 +20,9 @@ import ( "context" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/aws/smithy-go" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" diff --git a/pkg/cloud/services/network/gateways.go b/pkg/cloud/services/network/gateways.go index 161cc82a74..ee9fa65692 100644 --- a/pkg/cloud/services/network/gateways.go +++ b/pkg/cloud/services/network/gateways.go @@ -20,9 +20,9 @@ import ( "context" "fmt" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/pkg/errors" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" diff --git a/pkg/cloud/services/network/gateways_test.go b/pkg/cloud/services/network/gateways_test.go index 150571c211..62d35e3b69 100644 --- a/pkg/cloud/services/network/gateways_test.go +++ b/pkg/cloud/services/network/gateways_test.go @@ -20,9 +20,9 @@ import ( "context" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" diff --git a/pkg/cloud/services/network/natgateways_test.go b/pkg/cloud/services/network/natgateways_test.go index ae3cb26718..087993de58 100644 --- a/pkg/cloud/services/network/natgateways_test.go +++ b/pkg/cloud/services/network/natgateways_test.go @@ -20,9 +20,9 @@ import ( "context" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" diff --git a/pkg/cloud/services/network/routetables_test.go b/pkg/cloud/services/network/routetables_test.go index c1ab2825c8..eb131b8217 100644 --- a/pkg/cloud/services/network/routetables_test.go +++ b/pkg/cloud/services/network/routetables_test.go @@ -22,9 +22,9 @@ import ( "strings" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/golang/mock/gomock" "github.com/google/go-cmp/cmp" . "github.com/onsi/gomega" diff --git a/pkg/cloud/services/network/secondarycidr_test.go b/pkg/cloud/services/network/secondarycidr_test.go index 856781b2ec..3296072299 100644 --- a/pkg/cloud/services/network/secondarycidr_test.go +++ b/pkg/cloud/services/network/secondarycidr_test.go @@ -20,9 +20,9 @@ import ( "context" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" "k8s.io/apimachinery/pkg/runtime" diff --git a/pkg/cloud/services/network/subnets.go b/pkg/cloud/services/network/subnets.go index 1cf991ec5b..f339a9a8c0 100644 --- a/pkg/cloud/services/network/subnets.go +++ b/pkg/cloud/services/network/subnets.go @@ -25,9 +25,9 @@ import ( "strings" "time" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/pkg/errors" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" @@ -367,7 +367,7 @@ func (s *Service) deleteSubnets() error { } for _, sn := range existing.Subnets { - if err := s.deleteSubnet(aws.StringValue(sn.SubnetId)); err != nil { + if err := s.deleteSubnet(aws.ToString(sn.SubnetId)); err != nil { return err } } @@ -402,10 +402,10 @@ func (s *Service) describeVpcSubnets() (infrav1.Subnets, error) { Tags: converters.TagsToMap(ec2sn.Tags), } // For IPv6 subnets, both, ipv4 and 6 have to be defined so pods can have ipv6 cidr ranges. - spec.CidrBlock = aws.StringValue(ec2sn.CidrBlock) + spec.CidrBlock = aws.ToString(ec2sn.CidrBlock) for _, set := range ec2sn.Ipv6CidrBlockAssociationSet { if set.Ipv6CidrBlockState.State == types.SubnetCidrBlockStateCodeAssociated { - spec.IPv6CidrBlock = aws.StringValue(set.Ipv6CidrBlock) + spec.IPv6CidrBlock = aws.ToString(set.Ipv6CidrBlock) spec.IsIPv6 = true } } @@ -520,7 +520,7 @@ func (s *Service) createSubnet(sn *infrav1.SubnetSpec) (*infrav1.SubnetSpec, err record.Eventf(s.scope.InfraCluster(), "SuccessfulCreateSubnet", "Created new managed Subnet %q", *out.Subnet.SubnetId) s.scope.Info("Created subnet", "id", *out.Subnet.SubnetId, "public", sn.IsPublic, "az", sn.AvailabilityZone, "cidr", sn.CidrBlock, "ipv6", sn.IsIPv6, "ipv6-cidr", sn.IPv6CidrBlock) - wReq := &ec2.DescribeSubnetsInput{SubnetIds: []string{aws.StringValue(out.Subnet.SubnetId)}} + wReq := &ec2.DescribeSubnetsInput{SubnetIds: []string{aws.ToString(out.Subnet.SubnetId)}} if err := ec2.NewSubnetAvailableWaiter(s.EC2Client).Wait(context.TODO(), wReq, time.Minute*5); err != nil { return nil, errors.Wrapf(err, "failed to wait for subnet %q", *out.Subnet.SubnetId) } @@ -574,7 +574,7 @@ func (s *Service) createSubnet(sn *infrav1.SubnetSpec) (*infrav1.SubnetSpec, err if err := wait.WaitForWithRetryable(wait.NewBackoff(), func() (bool, error) { if _, err := s.EC2Client.ModifySubnetAttribute(context.TODO(), &ec2.ModifySubnetAttributeInput{ SubnetId: out.Subnet.SubnetId, - PrivateDnsHostnameTypeOnLaunch: types.HostnameType(aws.StringValue(s.scope.VPC().PrivateDNSHostnameTypeOnLaunch)), + PrivateDnsHostnameTypeOnLaunch: types.HostnameType(aws.ToString(s.scope.VPC().PrivateDNSHostnameTypeOnLaunch)), }); err != nil { return false, err } @@ -597,7 +597,7 @@ func (s *Service) createSubnet(sn *infrav1.SubnetSpec) (*infrav1.SubnetSpec, err } for _, set := range out.Subnet.Ipv6CidrBlockAssociationSet { if set.Ipv6CidrBlockState.State == types.SubnetCidrBlockStateCodeAssociated { - subnet.IPv6CidrBlock = aws.StringValue(set.Ipv6CidrBlock) + subnet.IPv6CidrBlock = aws.ToString(set.Ipv6CidrBlock) subnet.IsIPv6 = true } } diff --git a/pkg/cloud/services/network/subnets_test.go b/pkg/cloud/services/network/subnets_test.go index 11dbde0dd4..f14c9b7deb 100644 --- a/pkg/cloud/services/network/subnets_test.go +++ b/pkg/cloud/services/network/subnets_test.go @@ -24,9 +24,9 @@ import ( "slices" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/golang/mock/gomock" "github.com/google/go-cmp/cmp" . "github.com/onsi/gomega" diff --git a/pkg/cloud/services/network/vpc.go b/pkg/cloud/services/network/vpc.go index 9f4e510a99..078afd1dd7 100644 --- a/pkg/cloud/services/network/vpc.go +++ b/pkg/cloud/services/network/vpc.go @@ -20,9 +20,9 @@ import ( "context" "fmt" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" "github.com/pkg/errors" kerrors "k8s.io/apimachinery/pkg/util/errors" "k8s.io/apimachinery/pkg/util/sets" @@ -229,7 +229,7 @@ func (s *Service) reconcileVPCEndpoints() error { for _, service := range services.UnsortedList() { var existing *types.VpcEndpoint for _, ep := range endpoints { - if aws.StringValue(ep.ServiceName) == service { + if aws.ToString(ep.ServiceName) == service { existing = &ep break } @@ -331,7 +331,7 @@ func (s *Service) ensureManagedVPCAttributes(vpc *infrav1.VPCSpec) error { return err } errs = append(errs, errors.Wrap(err, "failed to describe enableDnsHostnames vpc attribute")) - } else if !aws.BoolValue(vpcAttr.EnableDnsHostnames.Value) { + } else if !aws.ToBool(vpcAttr.EnableDnsHostnames.Value) { attrInput := &ec2.ModifyVpcAttributeInput{ VpcId: aws.String(vpc.ID), EnableDnsHostnames: &types.AttributeBooleanValue{Value: aws.Bool(true)}, @@ -358,7 +358,7 @@ func (s *Service) ensureManagedVPCAttributes(vpc *infrav1.VPCSpec) error { return err } errs = append(errs, errors.Wrap(err, "failed to describe enableDnsSupport vpc attribute")) - } else if !aws.BoolValue(vpcAttr.EnableDnsSupport.Value) { + } else if !aws.ToBool(vpcAttr.EnableDnsSupport.Value) { attrInput := &ec2.ModifyVpcAttributeInput{ VpcId: aws.String(vpc.ID), EnableDnsSupport: &types.AttributeBooleanValue{Value: aws.Bool(true)}, @@ -495,7 +495,7 @@ func (s *Service) createVPC() (*infrav1.VPCSpec, error) { // We have to describe the VPC again because the `create` output will **NOT** contain the associated IPv6 address. vpc, err := s.EC2Client.DescribeVpcs(context.TODO(), &ec2.DescribeVpcsInput{ - VpcIds: []string{aws.StringValue(out.Vpc.VpcId)}, + VpcIds: []string{aws.ToString(out.Vpc.VpcId)}, }) if err != nil { record.Warnf(s.scope.InfraCluster(), "DescribeVpcs", "Failed to describe the new ipv6 vpc: %v", err) @@ -509,8 +509,8 @@ func (s *Service) createVPC() (*infrav1.VPCSpec, error) { if set.Ipv6CidrBlockState.State == types.VpcCidrBlockStateCodeAssociated { return &infrav1.VPCSpec{ IPv6: &infrav1.IPv6{ - CidrBlock: aws.StringValue(set.Ipv6CidrBlock), - PoolID: aws.StringValue(set.Ipv6Pool), + CidrBlock: aws.ToString(set.Ipv6CidrBlock), + PoolID: aws.ToString(set.Ipv6Pool), }, ID: *vpc.Vpcs[0].VpcId, CidrBlock: *out.Vpc.CidrBlock, @@ -598,8 +598,8 @@ func (s *Service) describeVPCByID() (*infrav1.VPCSpec, error) { for _, set := range out.Vpcs[0].Ipv6CidrBlockAssociationSet { if set.Ipv6CidrBlockState.State == types.VpcCidrBlockStateCodeAssociated { vpc.IPv6 = &infrav1.IPv6{ - CidrBlock: aws.StringValue(set.Ipv6CidrBlock), - PoolID: aws.StringValue(set.Ipv6Pool), + CidrBlock: aws.ToString(set.Ipv6CidrBlock), + PoolID: aws.ToString(set.Ipv6Pool), } break } @@ -646,8 +646,8 @@ func (s *Service) describeVPCByName() (*infrav1.VPCSpec, error) { for _, set := range out.Vpcs[0].Ipv6CidrBlockAssociationSet { if set.Ipv6CidrBlockState.State == types.VpcCidrBlockStateCodeAssociated { vpc.IPv6 = &infrav1.IPv6{ - CidrBlock: aws.StringValue(set.Ipv6CidrBlock), - PoolID: aws.StringValue(set.Ipv6Pool), + CidrBlock: aws.ToString(set.Ipv6CidrBlock), + PoolID: aws.ToString(set.Ipv6Pool), } break } diff --git a/pkg/cloud/services/network/vpc_test.go b/pkg/cloud/services/network/vpc_test.go index 059f642ee6..9c2f5f3a22 100644 --- a/pkg/cloud/services/network/vpc_test.go +++ b/pkg/cloud/services/network/vpc_test.go @@ -20,10 +20,9 @@ import ( "context" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/request" "github.com/aws/smithy-go" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" @@ -38,7 +37,7 @@ import ( clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" ) -func describeVpcAttributeTrue(_ context.Context, input *ec2.DescribeVpcAttributeInput, _ ...request.Option) (*ec2.DescribeVpcAttributeOutput, error) { +func describeVpcAttributeTrue(_ context.Context, input *ec2.DescribeVpcAttributeInput, _ ...ec2.Options) (*ec2.DescribeVpcAttributeOutput, error) { result := &ec2.DescribeVpcAttributeOutput{ VpcId: input.VpcId, } @@ -51,7 +50,7 @@ func describeVpcAttributeTrue(_ context.Context, input *ec2.DescribeVpcAttribute return result, nil } -func describeVpcAttributeFalse(_ context.Context, input *ec2.DescribeVpcAttributeInput, _ ...request.Option) (*ec2.DescribeVpcAttributeOutput, error) { +func describeVpcAttributeFalse(_ context.Context, input *ec2.DescribeVpcAttributeInput, _ ...ec2.Options) (*ec2.DescribeVpcAttributeOutput, error) { result := &ec2.DescribeVpcAttributeOutput{ VpcId: input.VpcId, } diff --git a/pkg/cloud/services/s3/s3.go b/pkg/cloud/services/s3/s3.go index 982ba46e92..6da0d7b433 100644 --- a/pkg/cloud/services/s3/s3.go +++ b/pkg/cloud/services/s3/s3.go @@ -26,10 +26,10 @@ import ( "path" "sort" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/s3" - "github.com/aws/aws-sdk-go-v2/service/s3/types" + s3types "github.com/aws/aws-sdk-go-v2/service/s3/types" stsv2 "github.com/aws/aws-sdk-go-v2/service/sts" - "github.com/aws/aws-sdk-go/aws" "github.com/pkg/errors" "k8s.io/utils/ptr" @@ -37,10 +37,10 @@ import ( "sigs.k8s.io/cluster-api-provider-aws/v2/feature" iam "sigs.k8s.io/cluster-api-provider-aws/v2/iam/api/v1beta1" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/awserrors" + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/endpoints" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/scope" stsservice "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/services/sts" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/services/userdata" - "sigs.k8s.io/cluster-api-provider-aws/v2/util/system" ) // AWSDefaultRegion is the default AWS region. @@ -138,7 +138,7 @@ func (s *Service) DeleteBucket(ctx context.Context) error { if err != nil { smithyErr := awserrors.ParseSmithyError(err) switch smithyErr.ErrorCode() { - case (&types.NoSuchBucket{}).ErrorCode(): + case (&s3types.NoSuchBucket{}).ErrorCode(): log.Info("Bucket already removed") return nil default: @@ -170,7 +170,7 @@ func (s *Service) DeleteBucket(ctx context.Context) error { if err != nil { smithyErr := awserrors.ParseSmithyError(err) switch smithyErr.ErrorCode() { - case (&types.NoSuchBucket{}).ErrorCode(): + case (&s3types.NoSuchBucket{}).ErrorCode(): log.Info("Bucket already removed") return nil case "BucketNotEmpty": @@ -203,10 +203,10 @@ func (s *Service) Create(ctx context.Context, m *scope.MachineScope, data []byte s.scope.Info("Creating object", "bucket_name", bucket, "key", key) if _, err := s.S3Client.PutObject(ctx, &s3.PutObjectInput{ - Body: aws.ReadSeekCloser(bytes.NewReader(data)), + Body: bytes.NewReader(data), Bucket: aws.String(bucket), Key: aws.String(key), - ServerSideEncryption: types.ServerSideEncryptionAwsKms, + ServerSideEncryption: s3types.ServerSideEncryptionAwsKms, }); err != nil { return "", errors.Wrap(err, "putting object") } @@ -254,10 +254,10 @@ func (s *Service) CreateForMachinePool(ctx context.Context, scope scope.LaunchTe s.scope.Info("Creating object for machine pool", "bucket_name", bucket, "key", key) if _, err := s.S3Client.PutObject(ctx, &s3.PutObjectInput{ - Body: aws.ReadSeekCloser(bytes.NewReader(data)), + Body: bytes.NewReader(data), Bucket: aws.String(bucket), Key: aws.String(key), - ServerSideEncryption: types.ServerSideEncryptionAwsKms, + ServerSideEncryption: s3types.ServerSideEncryptionAwsKms, }); err != nil { return "", errors.Wrap(err, "putting object for machine pool") } @@ -321,10 +321,10 @@ func (s *Service) Delete(ctx context.Context, m *scope.MachineScope) error { case "NotFound": s.scope.Debug("Either bucket or object does not exist", "bucket", bucket, "key", key) return nil - case (&types.NoSuchKey{}).ErrorCode(): + case (&s3types.NoSuchKey{}).ErrorCode(): s.scope.Debug("Object already deleted", "bucket", bucket, "key", key) return nil - case (&types.NoSuchBucket{}).ErrorCode(): + case (&s3types.NoSuchBucket{}).ErrorCode(): s.scope.Debug("Bucket does not exist", "bucket", bucket) return nil } @@ -380,7 +380,7 @@ func (s *Service) DeleteForMachinePool(ctx context.Context, scope scope.LaunchTe smithyErr := awserrors.ParseSmithyError(err) switch smithyErr.ErrorCode() { - case (&types.NoSuchBucket{}).ErrorCode(): + case (&s3types.NoSuchBucket{}).ErrorCode(): default: return errors.Wrap(err, "deleting S3 object for machine pool") } @@ -393,8 +393,8 @@ func (s *Service) createBucketIfNotExist(ctx context.Context, bucketName string) // See https://docs.aws.amazon.com/AmazonS3/latest/API/API_CreateBucket.html#AmazonS3-CreateBucket-request-LocationConstraint. if s.scope.Region() != AWSDefaultRegion { - input.CreateBucketConfiguration = &types.CreateBucketConfiguration{ - LocationConstraint: types.BucketLocationConstraint(s.scope.Region()), + input.CreateBucketConfiguration = &s3types.CreateBucketConfiguration{ + LocationConstraint: s3types.BucketLocationConstraint(s.scope.Region()), } } @@ -410,7 +410,7 @@ func (s *Service) createBucketIfNotExist(ctx context.Context, bucketName string) // If bucket already exists, all good. // // TODO: This will fail if bucket is shared with other cluster. - case (&types.BucketAlreadyOwnedByYou{}).ErrorCode(): + case (&s3types.BucketAlreadyOwnedByYou{}).ErrorCode(): return nil default: return errors.Wrap(err, "creating S3 bucket") @@ -444,11 +444,11 @@ func (s *Service) ensureBucketLifecycleConfiguration(ctx context.Context, bucket input := &s3.PutBucketLifecycleConfigurationInput{ Bucket: aws.String(bucketName), - LifecycleConfiguration: &types.BucketLifecycleConfiguration{ - Rules: []types.LifecycleRule{ + LifecycleConfiguration: &s3types.BucketLifecycleConfiguration{ + Rules: []s3types.LifecycleRule{ { ID: aws.String("machine-pool"), - Expiration: &types.LifecycleExpiration{ + Expiration: &s3types.LifecycleExpiration{ // The bootstrap token for new nodes to join the cluster is normally rotated regularly, // such as in CAPI's `KubeadmConfig` reconciler. Therefore, the launch template user data // stored in the S3 bucket only needs to live longer than the token TTL. @@ -456,10 +456,10 @@ func (s *Service) ensureBucketLifecycleConfiguration(ctx context.Context, bucket // (see function `DeleteForMachinePool`). Days: aws.Int32(1), }, - Filter: &types.LifecycleRuleFilterMemberPrefix{ - Value: "machine-pool/", + Filter: &s3types.LifecycleRuleFilter{ + Prefix: aws.String("machine-pool/"), }, - Status: types.ExpirationStatusEnabled, + Status: s3types.ExpirationStatusEnabled, }, }, }, @@ -477,7 +477,7 @@ func (s *Service) ensureBucketLifecycleConfiguration(ctx context.Context, bucket func (s *Service) tagBucket(ctx context.Context, bucketName string) error { taggingInput := &s3.PutBucketTaggingInput{ Bucket: aws.String(bucketName), - Tagging: &types.Tagging{ + Tagging: &s3types.Tagging{ TagSet: nil, }, } @@ -491,7 +491,7 @@ func (s *Service) tagBucket(ctx context.Context, bucketName string) error { }) for key, value := range tags { - taggingInput.Tagging.TagSet = append(taggingInput.Tagging.TagSet, types.Tag{ + taggingInput.Tagging.TagSet = append(taggingInput.Tagging.TagSet, s3types.Tag{ Key: aws.String(key), Value: aws.String(value), }) @@ -518,7 +518,7 @@ func (s *Service) bucketPolicy(bucketName string) (string, error) { } bucket := s.scope.Bucket() - partition := system.GetPartitionFromRegion(s.scope.Region()) + partition := endpoints.GetPartitionFromRegion(s.scope.Region()) statements := []iam.StatementEntry{ { diff --git a/pkg/cloud/services/secretsmanager/cloudinit.go b/pkg/cloud/services/secretsmanager/cloudinit.go index 6f444d1822..48745ac2ca 100644 --- a/pkg/cloud/services/secretsmanager/cloudinit.go +++ b/pkg/cloud/services/secretsmanager/cloudinit.go @@ -17,25 +17,14 @@ limitations under the License. package secretsmanager import ( - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/scope" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/internal/mime" ) -const ( - serviceID = "secretsmanager" -) - // UserData creates a multi-part MIME document including a script boothook to // download userdata from AWS Secrets Manager and then restart cloud-init, and an include part // specifying the on disk location of the new userdata. -func (s *Service) UserData(secretPrefix string, chunks int32, region string, endpoints []scope.ServiceEndpoint) ([]byte, error) { - serviceEndpoint := "" - for _, v := range endpoints { - if v.ServiceID == serviceID { - serviceEndpoint = v.URL - } - } - userData, err := mime.GenerateInitDocument(secretPrefix, chunks, region, serviceEndpoint, secretFetchScript) +func (s *Service) UserData(secretPrefix string, chunks int32, region string) ([]byte, error) { + userData, err := mime.GenerateInitDocument(secretPrefix, chunks, region, secretFetchScript) if err != nil { return []byte{}, err } diff --git a/pkg/cloud/services/secretsmanager/mock_secretsmanageriface/secretsmanagerapi_mock.go b/pkg/cloud/services/secretsmanager/mock_secretsmanageriface/secretsmanagerapi_mock.go new file mode 100644 index 0000000000..d2e72e44cf --- /dev/null +++ b/pkg/cloud/services/secretsmanager/mock_secretsmanageriface/secretsmanagerapi_mock.go @@ -0,0 +1,92 @@ +/* +Copyright The Kubernetes Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by MockGen. DO NOT EDIT. +// Source: sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/services/secretsmanager (interfaces: SecretsManagerAPI) + +// Package mock_secretsmanageriface is a generated GoMock package. +package mock_secretsmanageriface + +import ( + context "context" + reflect "reflect" + + secretsmanager "github.com/aws/aws-sdk-go-v2/service/secretsmanager" + gomock "github.com/golang/mock/gomock" +) + +// MockSecretsManagerAPI is a mock of SecretsManagerAPI interface. +type MockSecretsManagerAPI struct { + ctrl *gomock.Controller + recorder *MockSecretsManagerAPIMockRecorder +} + +// MockSecretsManagerAPIMockRecorder is the mock recorder for MockSecretsManagerAPI. +type MockSecretsManagerAPIMockRecorder struct { + mock *MockSecretsManagerAPI +} + +// NewMockSecretsManagerAPI creates a new mock instance. +func NewMockSecretsManagerAPI(ctrl *gomock.Controller) *MockSecretsManagerAPI { + mock := &MockSecretsManagerAPI{ctrl: ctrl} + mock.recorder = &MockSecretsManagerAPIMockRecorder{mock} + return mock +} + +// EXPECT returns an object that allows the caller to indicate expected use. +func (m *MockSecretsManagerAPI) EXPECT() *MockSecretsManagerAPIMockRecorder { + return m.recorder +} + +// CreateSecret mocks base method. +func (m *MockSecretsManagerAPI) CreateSecret(arg0 context.Context, arg1 *secretsmanager.CreateSecretInput, arg2 ...func(*secretsmanager.Options)) (*secretsmanager.CreateSecretOutput, error) { + m.ctrl.T.Helper() + varargs := []interface{}{arg0, arg1} + for _, a := range arg2 { + varargs = append(varargs, a) + } + ret := m.ctrl.Call(m, "CreateSecret", varargs...) + ret0, _ := ret[0].(*secretsmanager.CreateSecretOutput) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// CreateSecret indicates an expected call of CreateSecret. +func (mr *MockSecretsManagerAPIMockRecorder) CreateSecret(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + varargs := append([]interface{}{arg0, arg1}, arg2...) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateSecret", reflect.TypeOf((*MockSecretsManagerAPI)(nil).CreateSecret), varargs...) +} + +// DeleteSecret mocks base method. +func (m *MockSecretsManagerAPI) DeleteSecret(arg0 context.Context, arg1 *secretsmanager.DeleteSecretInput, arg2 ...func(*secretsmanager.Options)) (*secretsmanager.DeleteSecretOutput, error) { + m.ctrl.T.Helper() + varargs := []interface{}{arg0, arg1} + for _, a := range arg2 { + varargs = append(varargs, a) + } + ret := m.ctrl.Call(m, "DeleteSecret", varargs...) + ret0, _ := ret[0].(*secretsmanager.DeleteSecretOutput) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// DeleteSecret indicates an expected call of DeleteSecret. +func (mr *MockSecretsManagerAPIMockRecorder) DeleteSecret(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + varargs := append([]interface{}{arg0, arg1}, arg2...) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "DeleteSecret", reflect.TypeOf((*MockSecretsManagerAPI)(nil).DeleteSecret), varargs...) +} diff --git a/pkg/cloud/services/secretsmanager/secret.go b/pkg/cloud/services/secretsmanager/secret.go index 432a941c26..d0015e0ddd 100644 --- a/pkg/cloud/services/secretsmanager/secret.go +++ b/pkg/cloud/services/secretsmanager/secret.go @@ -29,7 +29,7 @@ import ( "k8s.io/apimachinery/pkg/util/uuid" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/convertersv2" + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/converters" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/scope" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/services/wait" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/internal/bytes" @@ -91,7 +91,7 @@ func (s *Service) retryableCreateSecret(name string, chunk []byte, tags infrav1. _, err := s.SecretsManagerClient.CreateSecret(context.TODO(), &secretsmanager.CreateSecretInput{ Name: aws.String(name), SecretBinary: chunk, - Tags: convertersv2.MapToSecretsManagerTags(tags), + Tags: converters.MapToSecretsManagerTags(tags), }) // If the secret already exists, delete it, return request to retry, as deletes are eventually consistent if err != nil { diff --git a/pkg/cloud/services/secretsmanager/service_test.go b/pkg/cloud/services/secretsmanager/service_test.go index 9e645d8f86..d5bad7cc05 100644 --- a/pkg/cloud/services/secretsmanager/service_test.go +++ b/pkg/cloud/services/secretsmanager/service_test.go @@ -20,14 +20,11 @@ import ( "bytes" "net/mail" "testing" - - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/scope" ) func TestUserData(t *testing.T) { service := Service{} - endpoints := []scope.ServiceEndpoint{} - doc, _ := service.UserData("secretARN", 1, "eu-west-1", endpoints) + doc, _ := service.UserData("secretARN", 1, "eu-west-1") if _, err := mail.ReadMessage(bytes.NewBuffer(doc)); err != nil { t.Fatalf("Cannot parse MIME doc: %+v\n%s", err, string(doc)) @@ -36,14 +33,7 @@ func TestUserData(t *testing.T) { func TestUserDataEndpoints(t *testing.T) { service := Service{} - endpoints := []scope.ServiceEndpoint{ - { - URL: "localhost", - SigningRegion: "localhost", - ServiceID: "secretsmanager", - }, - } - doc, _ := service.UserData("secretARN", 1, "eu-west-1", endpoints) + doc, _ := service.UserData("secretARN", 1, "eu-west-1") if _, err := mail.ReadMessage(bytes.NewBuffer(doc)); err != nil { t.Fatalf("Cannot parse MIME doc: %+v\n%s", err, string(doc)) diff --git a/pkg/cloud/services/securitygroup/securitygroups_test.go b/pkg/cloud/services/securitygroup/securitygroups_test.go index d0c161d33d..2fd1cc64db 100644 --- a/pkg/cloud/services/securitygroup/securitygroups_test.go +++ b/pkg/cloud/services/securitygroup/securitygroups_test.go @@ -22,10 +22,10 @@ import ( "strings" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/awserr" + "github.com/aws/smithy-go" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" "github.com/pkg/errors" @@ -809,11 +809,17 @@ func TestReconcileSecurityGroups(t *testing.T) { m.RevokeSecurityGroupIngress(context.TODO(), gomock.AssignableToTypeOf(&ec2.RevokeSecurityGroupIngressInput{ GroupId: aws.String("sg-default"), - })).Return(&ec2.RevokeSecurityGroupIngressOutput{}, awserr.New("InvalidPermission.NotFound", "rules not found in security group", nil)) + })).Return(&ec2.RevokeSecurityGroupIngressOutput{}, &smithy.GenericAPIError{ + Code: "InvalidPermission.NotFound", + Message: "rules not found in security group", + }) m.RevokeSecurityGroupEgress(context.TODO(), gomock.AssignableToTypeOf(&ec2.RevokeSecurityGroupEgressInput{ GroupId: aws.String("sg-default"), - })).Return(&ec2.RevokeSecurityGroupEgressOutput{}, awserr.New("InvalidPermission.NotFound", "rules not found in security group", nil)) + })).Return(&ec2.RevokeSecurityGroupEgressOutput{}, &smithy.GenericAPIError{ + Code: "InvalidPermission.NotFound", + Message: "rules not found in security group", + }) m.DescribeSecurityGroups(context.TODO(), &ec2.DescribeSecurityGroupsInput{ Filters: []types.Filter{ @@ -1955,7 +1961,10 @@ func TestDeleteSecurityGroups(t *testing.T) { VPC: infrav1.VPCSpec{ID: "vpc-id"}, }, expect: func(m *mocks.MockEC2APIMockRecorder) { - m.DescribeSecurityGroups(context.TODO(), gomock.AssignableToTypeOf(&ec2.DescribeSecurityGroupsInput{}), gomock.Any()).Return(nil, awserr.New("dependency-failure", "dependency-failure", errors.Errorf("dependency-failure"))) + m.DescribeSecurityGroups(context.TODO(), gomock.AssignableToTypeOf(&ec2.DescribeSecurityGroupsInput{}), gomock.Any()).Return(nil, &smithy.GenericAPIError{ + Code: "dependency-failure", + Message: "dependency-failure", + }) }, wantErr: true, }, @@ -1996,7 +2005,10 @@ func TestDeleteSecurityGroups(t *testing.T) { }, }, }, nil).Times(2) - m.RevokeSecurityGroupIngress(context.TODO(), gomock.AssignableToTypeOf(&ec2.RevokeSecurityGroupIngressInput{}), gomock.Any()).Return(nil, awserr.New("failure", "failure", errors.Errorf("failure"))) + m.RevokeSecurityGroupIngress(context.TODO(), gomock.AssignableToTypeOf(&ec2.RevokeSecurityGroupIngressInput{}), gomock.Any()).Return(nil, &smithy.GenericAPIError{ + Code: "failure", + Message: "failure", + }) }, wantErr: true, }, diff --git a/pkg/cloud/services/ssm/cloudinit.go b/pkg/cloud/services/ssm/cloudinit.go index 4159238fba..eed2e96685 100644 --- a/pkg/cloud/services/ssm/cloudinit.go +++ b/pkg/cloud/services/ssm/cloudinit.go @@ -18,25 +18,14 @@ limitations under the License. package ssm import ( - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/scope" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/internal/mime" ) -const ( - serviceID = "ssm" -) - // UserData creates a multi-part MIME document including a script boothook to // download userdata from AWS Systems Manager and then restart cloud-init, and an include part // specifying the on disk location of the new userdata. -func (s *Service) UserData(secretPrefix string, chunks int32, region string, endpoints []scope.ServiceEndpoint) ([]byte, error) { - var serviceEndpoint = "" - for _, v := range endpoints { - if v.ServiceID == serviceID { - serviceEndpoint = v.URL - } - } - var userData, err = mime.GenerateInitDocument(secretPrefix, chunks, region, serviceEndpoint, secretFetchScript) +func (s *Service) UserData(secretPrefix string, chunks int32, region string) ([]byte, error) { + var userData, err = mime.GenerateInitDocument(secretPrefix, chunks, region, secretFetchScript) if err != nil { return []byte{}, err } diff --git a/pkg/cloud/services/ssm/service_test.go b/pkg/cloud/services/ssm/service_test.go index 84ab5fc070..bb83eb847f 100644 --- a/pkg/cloud/services/ssm/service_test.go +++ b/pkg/cloud/services/ssm/service_test.go @@ -20,14 +20,11 @@ import ( "bytes" "net/mail" "testing" - - "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/scope" ) func TestUserData(t *testing.T) { service := Service{} - endpoints := []scope.ServiceEndpoint{} - doc, _ := service.UserData("secretARN", 1, "eu-west-1", endpoints) + doc, _ := service.UserData("secretARN", 1, "eu-west-1") if _, err := mail.ReadMessage(bytes.NewBuffer(doc)); err != nil { t.Fatalf("Cannot parse MIME doc: %+v\n%s", err, string(doc)) @@ -36,14 +33,7 @@ func TestUserData(t *testing.T) { func TestUserDataEndpoints(t *testing.T) { service := Service{} - endpoints := []scope.ServiceEndpoint{ - { - URL: "localhost", - SigningRegion: "localhost", - ServiceID: "ssm", - }, - } - doc, _ := service.UserData("secretARN", 1, "eu-west-1", endpoints) + doc, _ := service.UserData("secretARN", 1, "eu-west-1") if _, err := mail.ReadMessage(bytes.NewBuffer(doc)); err != nil { t.Fatalf("Cannot parse MIME doc: %+v\n%s", err, string(doc)) diff --git a/pkg/cloud/services/sts/mock_stsiface/doc.go b/pkg/cloud/services/sts/mock_stsiface/doc.go index 648e4b4ef8..d02e63394d 100644 --- a/pkg/cloud/services/sts/mock_stsiface/doc.go +++ b/pkg/cloud/services/sts/mock_stsiface/doc.go @@ -17,8 +17,6 @@ limitations under the License. // Package mock_stsiface provides a mock implementation for the STSClient interface. // Run go generate to regenerate this mock. // -//go:generate ../../../../../hack/tools/bin/mockgen -destination stsiface_mock_v2.go -package mock_stsiface sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/services/sts STSClient -//go:generate /usr/bin/env bash -c "cat ../../../../../hack/boilerplate/boilerplate.generatego.txt stsiface_mock_v2.go > _stsiface_mock_v2.go && mv _stsiface_mock_v2.go stsiface_mock_v2.go" -//go:generate ../../../../../hack/tools/bin/mockgen -destination stsiface_mock_v1.go -package mock_stsiface github.com/aws/aws-sdk-go/service/sts/stsiface STSAPI -//go:generate /usr/bin/env bash -c "cat ../../../../../hack/boilerplate/boilerplate.generatego.txt stsiface_mock_v1.go > _stsiface_mock_v1.go && mv _stsiface_mock_v1.go stsiface_mock_v1.go" +//go:generate ../../../../../hack/tools/bin/mockgen -destination stsiface_mock.go -package mock_stsiface sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/services/sts STSClient +//go:generate /usr/bin/env bash -c "cat ../../../../../hack/boilerplate/boilerplate.generatego.txt stsiface_mock.go > _stsiface_mock.go && mv _stsiface_mock.go stsiface_mock.go" package mock_stsiface //nolint:stylecheck diff --git a/pkg/cloud/services/sts/mock_stsiface/stsiface_mock_v2.go b/pkg/cloud/services/sts/mock_stsiface/stsiface_mock.go similarity index 100% rename from pkg/cloud/services/sts/mock_stsiface/stsiface_mock_v2.go rename to pkg/cloud/services/sts/mock_stsiface/stsiface_mock.go diff --git a/pkg/cloud/services/sts/mock_stsiface/stsiface_mock_v1.go b/pkg/cloud/services/sts/mock_stsiface/stsiface_mock_v1.go deleted file mode 100644 index 047c9491fc..0000000000 --- a/pkg/cloud/services/sts/mock_stsiface/stsiface_mock_v1.go +++ /dev/null @@ -1,453 +0,0 @@ -/* -Copyright The Kubernetes Authors. - -Licensed under the Apache License, Version 2.0 (the "License"); -you may not use this file except in compliance with the License. -You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - -Unless required by applicable law or agreed to in writing, software -distributed under the License is distributed on an "AS IS" BASIS, -WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -See the License for the specific language governing permissions and -limitations under the License. -*/ - -// Code generated by MockGen. DO NOT EDIT. -// Source: github.com/aws/aws-sdk-go/service/sts/stsiface (interfaces: STSAPI) - -// Package mock_stsiface is a generated GoMock package. -package mock_stsiface - -import ( - context "context" - reflect "reflect" - - request "github.com/aws/aws-sdk-go/aws/request" - sts "github.com/aws/aws-sdk-go/service/sts" - gomock "github.com/golang/mock/gomock" -) - -// MockSTSAPI is a mock of STSAPI interface. -type MockSTSAPI struct { - ctrl *gomock.Controller - recorder *MockSTSAPIMockRecorder -} - -// MockSTSAPIMockRecorder is the mock recorder for MockSTSAPI. -type MockSTSAPIMockRecorder struct { - mock *MockSTSAPI -} - -// NewMockSTSAPI creates a new mock instance. -func NewMockSTSAPI(ctrl *gomock.Controller) *MockSTSAPI { - mock := &MockSTSAPI{ctrl: ctrl} - mock.recorder = &MockSTSAPIMockRecorder{mock} - return mock -} - -// EXPECT returns an object that allows the caller to indicate expected use. -func (m *MockSTSAPI) EXPECT() *MockSTSAPIMockRecorder { - return m.recorder -} - -// AssumeRole mocks base method. -func (m *MockSTSAPI) AssumeRole(arg0 *sts.AssumeRoleInput) (*sts.AssumeRoleOutput, error) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "AssumeRole", arg0) - ret0, _ := ret[0].(*sts.AssumeRoleOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// AssumeRole indicates an expected call of AssumeRole. -func (mr *MockSTSAPIMockRecorder) AssumeRole(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AssumeRole", reflect.TypeOf((*MockSTSAPI)(nil).AssumeRole), arg0) -} - -// AssumeRoleRequest mocks base method. -func (m *MockSTSAPI) AssumeRoleRequest(arg0 *sts.AssumeRoleInput) (*request.Request, *sts.AssumeRoleOutput) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "AssumeRoleRequest", arg0) - ret0, _ := ret[0].(*request.Request) - ret1, _ := ret[1].(*sts.AssumeRoleOutput) - return ret0, ret1 -} - -// AssumeRoleRequest indicates an expected call of AssumeRoleRequest. -func (mr *MockSTSAPIMockRecorder) AssumeRoleRequest(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AssumeRoleRequest", reflect.TypeOf((*MockSTSAPI)(nil).AssumeRoleRequest), arg0) -} - -// AssumeRoleWithContext mocks base method. -func (m *MockSTSAPI) AssumeRoleWithContext(arg0 context.Context, arg1 *sts.AssumeRoleInput, arg2 ...request.Option) (*sts.AssumeRoleOutput, error) { - m.ctrl.T.Helper() - varargs := []interface{}{arg0, arg1} - for _, a := range arg2 { - varargs = append(varargs, a) - } - ret := m.ctrl.Call(m, "AssumeRoleWithContext", varargs...) - ret0, _ := ret[0].(*sts.AssumeRoleOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// AssumeRoleWithContext indicates an expected call of AssumeRoleWithContext. -func (mr *MockSTSAPIMockRecorder) AssumeRoleWithContext(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - varargs := append([]interface{}{arg0, arg1}, arg2...) - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AssumeRoleWithContext", reflect.TypeOf((*MockSTSAPI)(nil).AssumeRoleWithContext), varargs...) -} - -// AssumeRoleWithSAML mocks base method. -func (m *MockSTSAPI) AssumeRoleWithSAML(arg0 *sts.AssumeRoleWithSAMLInput) (*sts.AssumeRoleWithSAMLOutput, error) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "AssumeRoleWithSAML", arg0) - ret0, _ := ret[0].(*sts.AssumeRoleWithSAMLOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// AssumeRoleWithSAML indicates an expected call of AssumeRoleWithSAML. -func (mr *MockSTSAPIMockRecorder) AssumeRoleWithSAML(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AssumeRoleWithSAML", reflect.TypeOf((*MockSTSAPI)(nil).AssumeRoleWithSAML), arg0) -} - -// AssumeRoleWithSAMLRequest mocks base method. -func (m *MockSTSAPI) AssumeRoleWithSAMLRequest(arg0 *sts.AssumeRoleWithSAMLInput) (*request.Request, *sts.AssumeRoleWithSAMLOutput) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "AssumeRoleWithSAMLRequest", arg0) - ret0, _ := ret[0].(*request.Request) - ret1, _ := ret[1].(*sts.AssumeRoleWithSAMLOutput) - return ret0, ret1 -} - -// AssumeRoleWithSAMLRequest indicates an expected call of AssumeRoleWithSAMLRequest. -func (mr *MockSTSAPIMockRecorder) AssumeRoleWithSAMLRequest(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AssumeRoleWithSAMLRequest", reflect.TypeOf((*MockSTSAPI)(nil).AssumeRoleWithSAMLRequest), arg0) -} - -// AssumeRoleWithSAMLWithContext mocks base method. -func (m *MockSTSAPI) AssumeRoleWithSAMLWithContext(arg0 context.Context, arg1 *sts.AssumeRoleWithSAMLInput, arg2 ...request.Option) (*sts.AssumeRoleWithSAMLOutput, error) { - m.ctrl.T.Helper() - varargs := []interface{}{arg0, arg1} - for _, a := range arg2 { - varargs = append(varargs, a) - } - ret := m.ctrl.Call(m, "AssumeRoleWithSAMLWithContext", varargs...) - ret0, _ := ret[0].(*sts.AssumeRoleWithSAMLOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// AssumeRoleWithSAMLWithContext indicates an expected call of AssumeRoleWithSAMLWithContext. -func (mr *MockSTSAPIMockRecorder) AssumeRoleWithSAMLWithContext(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - varargs := append([]interface{}{arg0, arg1}, arg2...) - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AssumeRoleWithSAMLWithContext", reflect.TypeOf((*MockSTSAPI)(nil).AssumeRoleWithSAMLWithContext), varargs...) -} - -// AssumeRoleWithWebIdentity mocks base method. -func (m *MockSTSAPI) AssumeRoleWithWebIdentity(arg0 *sts.AssumeRoleWithWebIdentityInput) (*sts.AssumeRoleWithWebIdentityOutput, error) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "AssumeRoleWithWebIdentity", arg0) - ret0, _ := ret[0].(*sts.AssumeRoleWithWebIdentityOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// AssumeRoleWithWebIdentity indicates an expected call of AssumeRoleWithWebIdentity. -func (mr *MockSTSAPIMockRecorder) AssumeRoleWithWebIdentity(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AssumeRoleWithWebIdentity", reflect.TypeOf((*MockSTSAPI)(nil).AssumeRoleWithWebIdentity), arg0) -} - -// AssumeRoleWithWebIdentityRequest mocks base method. -func (m *MockSTSAPI) AssumeRoleWithWebIdentityRequest(arg0 *sts.AssumeRoleWithWebIdentityInput) (*request.Request, *sts.AssumeRoleWithWebIdentityOutput) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "AssumeRoleWithWebIdentityRequest", arg0) - ret0, _ := ret[0].(*request.Request) - ret1, _ := ret[1].(*sts.AssumeRoleWithWebIdentityOutput) - return ret0, ret1 -} - -// AssumeRoleWithWebIdentityRequest indicates an expected call of AssumeRoleWithWebIdentityRequest. -func (mr *MockSTSAPIMockRecorder) AssumeRoleWithWebIdentityRequest(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AssumeRoleWithWebIdentityRequest", reflect.TypeOf((*MockSTSAPI)(nil).AssumeRoleWithWebIdentityRequest), arg0) -} - -// AssumeRoleWithWebIdentityWithContext mocks base method. -func (m *MockSTSAPI) AssumeRoleWithWebIdentityWithContext(arg0 context.Context, arg1 *sts.AssumeRoleWithWebIdentityInput, arg2 ...request.Option) (*sts.AssumeRoleWithWebIdentityOutput, error) { - m.ctrl.T.Helper() - varargs := []interface{}{arg0, arg1} - for _, a := range arg2 { - varargs = append(varargs, a) - } - ret := m.ctrl.Call(m, "AssumeRoleWithWebIdentityWithContext", varargs...) - ret0, _ := ret[0].(*sts.AssumeRoleWithWebIdentityOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// AssumeRoleWithWebIdentityWithContext indicates an expected call of AssumeRoleWithWebIdentityWithContext. -func (mr *MockSTSAPIMockRecorder) AssumeRoleWithWebIdentityWithContext(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - varargs := append([]interface{}{arg0, arg1}, arg2...) - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AssumeRoleWithWebIdentityWithContext", reflect.TypeOf((*MockSTSAPI)(nil).AssumeRoleWithWebIdentityWithContext), varargs...) -} - -// DecodeAuthorizationMessage mocks base method. -func (m *MockSTSAPI) DecodeAuthorizationMessage(arg0 *sts.DecodeAuthorizationMessageInput) (*sts.DecodeAuthorizationMessageOutput, error) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "DecodeAuthorizationMessage", arg0) - ret0, _ := ret[0].(*sts.DecodeAuthorizationMessageOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// DecodeAuthorizationMessage indicates an expected call of DecodeAuthorizationMessage. -func (mr *MockSTSAPIMockRecorder) DecodeAuthorizationMessage(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "DecodeAuthorizationMessage", reflect.TypeOf((*MockSTSAPI)(nil).DecodeAuthorizationMessage), arg0) -} - -// DecodeAuthorizationMessageRequest mocks base method. -func (m *MockSTSAPI) DecodeAuthorizationMessageRequest(arg0 *sts.DecodeAuthorizationMessageInput) (*request.Request, *sts.DecodeAuthorizationMessageOutput) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "DecodeAuthorizationMessageRequest", arg0) - ret0, _ := ret[0].(*request.Request) - ret1, _ := ret[1].(*sts.DecodeAuthorizationMessageOutput) - return ret0, ret1 -} - -// DecodeAuthorizationMessageRequest indicates an expected call of DecodeAuthorizationMessageRequest. -func (mr *MockSTSAPIMockRecorder) DecodeAuthorizationMessageRequest(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "DecodeAuthorizationMessageRequest", reflect.TypeOf((*MockSTSAPI)(nil).DecodeAuthorizationMessageRequest), arg0) -} - -// DecodeAuthorizationMessageWithContext mocks base method. -func (m *MockSTSAPI) DecodeAuthorizationMessageWithContext(arg0 context.Context, arg1 *sts.DecodeAuthorizationMessageInput, arg2 ...request.Option) (*sts.DecodeAuthorizationMessageOutput, error) { - m.ctrl.T.Helper() - varargs := []interface{}{arg0, arg1} - for _, a := range arg2 { - varargs = append(varargs, a) - } - ret := m.ctrl.Call(m, "DecodeAuthorizationMessageWithContext", varargs...) - ret0, _ := ret[0].(*sts.DecodeAuthorizationMessageOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// DecodeAuthorizationMessageWithContext indicates an expected call of DecodeAuthorizationMessageWithContext. -func (mr *MockSTSAPIMockRecorder) DecodeAuthorizationMessageWithContext(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - varargs := append([]interface{}{arg0, arg1}, arg2...) - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "DecodeAuthorizationMessageWithContext", reflect.TypeOf((*MockSTSAPI)(nil).DecodeAuthorizationMessageWithContext), varargs...) -} - -// GetAccessKeyInfo mocks base method. -func (m *MockSTSAPI) GetAccessKeyInfo(arg0 *sts.GetAccessKeyInfoInput) (*sts.GetAccessKeyInfoOutput, error) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "GetAccessKeyInfo", arg0) - ret0, _ := ret[0].(*sts.GetAccessKeyInfoOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// GetAccessKeyInfo indicates an expected call of GetAccessKeyInfo. -func (mr *MockSTSAPIMockRecorder) GetAccessKeyInfo(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetAccessKeyInfo", reflect.TypeOf((*MockSTSAPI)(nil).GetAccessKeyInfo), arg0) -} - -// GetAccessKeyInfoRequest mocks base method. -func (m *MockSTSAPI) GetAccessKeyInfoRequest(arg0 *sts.GetAccessKeyInfoInput) (*request.Request, *sts.GetAccessKeyInfoOutput) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "GetAccessKeyInfoRequest", arg0) - ret0, _ := ret[0].(*request.Request) - ret1, _ := ret[1].(*sts.GetAccessKeyInfoOutput) - return ret0, ret1 -} - -// GetAccessKeyInfoRequest indicates an expected call of GetAccessKeyInfoRequest. -func (mr *MockSTSAPIMockRecorder) GetAccessKeyInfoRequest(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetAccessKeyInfoRequest", reflect.TypeOf((*MockSTSAPI)(nil).GetAccessKeyInfoRequest), arg0) -} - -// GetAccessKeyInfoWithContext mocks base method. -func (m *MockSTSAPI) GetAccessKeyInfoWithContext(arg0 context.Context, arg1 *sts.GetAccessKeyInfoInput, arg2 ...request.Option) (*sts.GetAccessKeyInfoOutput, error) { - m.ctrl.T.Helper() - varargs := []interface{}{arg0, arg1} - for _, a := range arg2 { - varargs = append(varargs, a) - } - ret := m.ctrl.Call(m, "GetAccessKeyInfoWithContext", varargs...) - ret0, _ := ret[0].(*sts.GetAccessKeyInfoOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// GetAccessKeyInfoWithContext indicates an expected call of GetAccessKeyInfoWithContext. -func (mr *MockSTSAPIMockRecorder) GetAccessKeyInfoWithContext(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - varargs := append([]interface{}{arg0, arg1}, arg2...) - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetAccessKeyInfoWithContext", reflect.TypeOf((*MockSTSAPI)(nil).GetAccessKeyInfoWithContext), varargs...) -} - -// GetCallerIdentity mocks base method. -func (m *MockSTSAPI) GetCallerIdentity(arg0 *sts.GetCallerIdentityInput) (*sts.GetCallerIdentityOutput, error) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "GetCallerIdentity", arg0) - ret0, _ := ret[0].(*sts.GetCallerIdentityOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// GetCallerIdentity indicates an expected call of GetCallerIdentity. -func (mr *MockSTSAPIMockRecorder) GetCallerIdentity(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetCallerIdentity", reflect.TypeOf((*MockSTSAPI)(nil).GetCallerIdentity), arg0) -} - -// GetCallerIdentityRequest mocks base method. -func (m *MockSTSAPI) GetCallerIdentityRequest(arg0 *sts.GetCallerIdentityInput) (*request.Request, *sts.GetCallerIdentityOutput) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "GetCallerIdentityRequest", arg0) - ret0, _ := ret[0].(*request.Request) - ret1, _ := ret[1].(*sts.GetCallerIdentityOutput) - return ret0, ret1 -} - -// GetCallerIdentityRequest indicates an expected call of GetCallerIdentityRequest. -func (mr *MockSTSAPIMockRecorder) GetCallerIdentityRequest(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetCallerIdentityRequest", reflect.TypeOf((*MockSTSAPI)(nil).GetCallerIdentityRequest), arg0) -} - -// GetCallerIdentityWithContext mocks base method. -func (m *MockSTSAPI) GetCallerIdentityWithContext(arg0 context.Context, arg1 *sts.GetCallerIdentityInput, arg2 ...request.Option) (*sts.GetCallerIdentityOutput, error) { - m.ctrl.T.Helper() - varargs := []interface{}{arg0, arg1} - for _, a := range arg2 { - varargs = append(varargs, a) - } - ret := m.ctrl.Call(m, "GetCallerIdentityWithContext", varargs...) - ret0, _ := ret[0].(*sts.GetCallerIdentityOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// GetCallerIdentityWithContext indicates an expected call of GetCallerIdentityWithContext. -func (mr *MockSTSAPIMockRecorder) GetCallerIdentityWithContext(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - varargs := append([]interface{}{arg0, arg1}, arg2...) - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetCallerIdentityWithContext", reflect.TypeOf((*MockSTSAPI)(nil).GetCallerIdentityWithContext), varargs...) -} - -// GetFederationToken mocks base method. -func (m *MockSTSAPI) GetFederationToken(arg0 *sts.GetFederationTokenInput) (*sts.GetFederationTokenOutput, error) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "GetFederationToken", arg0) - ret0, _ := ret[0].(*sts.GetFederationTokenOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// GetFederationToken indicates an expected call of GetFederationToken. -func (mr *MockSTSAPIMockRecorder) GetFederationToken(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetFederationToken", reflect.TypeOf((*MockSTSAPI)(nil).GetFederationToken), arg0) -} - -// GetFederationTokenRequest mocks base method. -func (m *MockSTSAPI) GetFederationTokenRequest(arg0 *sts.GetFederationTokenInput) (*request.Request, *sts.GetFederationTokenOutput) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "GetFederationTokenRequest", arg0) - ret0, _ := ret[0].(*request.Request) - ret1, _ := ret[1].(*sts.GetFederationTokenOutput) - return ret0, ret1 -} - -// GetFederationTokenRequest indicates an expected call of GetFederationTokenRequest. -func (mr *MockSTSAPIMockRecorder) GetFederationTokenRequest(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetFederationTokenRequest", reflect.TypeOf((*MockSTSAPI)(nil).GetFederationTokenRequest), arg0) -} - -// GetFederationTokenWithContext mocks base method. -func (m *MockSTSAPI) GetFederationTokenWithContext(arg0 context.Context, arg1 *sts.GetFederationTokenInput, arg2 ...request.Option) (*sts.GetFederationTokenOutput, error) { - m.ctrl.T.Helper() - varargs := []interface{}{arg0, arg1} - for _, a := range arg2 { - varargs = append(varargs, a) - } - ret := m.ctrl.Call(m, "GetFederationTokenWithContext", varargs...) - ret0, _ := ret[0].(*sts.GetFederationTokenOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// GetFederationTokenWithContext indicates an expected call of GetFederationTokenWithContext. -func (mr *MockSTSAPIMockRecorder) GetFederationTokenWithContext(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - varargs := append([]interface{}{arg0, arg1}, arg2...) - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetFederationTokenWithContext", reflect.TypeOf((*MockSTSAPI)(nil).GetFederationTokenWithContext), varargs...) -} - -// GetSessionToken mocks base method. -func (m *MockSTSAPI) GetSessionToken(arg0 *sts.GetSessionTokenInput) (*sts.GetSessionTokenOutput, error) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "GetSessionToken", arg0) - ret0, _ := ret[0].(*sts.GetSessionTokenOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// GetSessionToken indicates an expected call of GetSessionToken. -func (mr *MockSTSAPIMockRecorder) GetSessionToken(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetSessionToken", reflect.TypeOf((*MockSTSAPI)(nil).GetSessionToken), arg0) -} - -// GetSessionTokenRequest mocks base method. -func (m *MockSTSAPI) GetSessionTokenRequest(arg0 *sts.GetSessionTokenInput) (*request.Request, *sts.GetSessionTokenOutput) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "GetSessionTokenRequest", arg0) - ret0, _ := ret[0].(*request.Request) - ret1, _ := ret[1].(*sts.GetSessionTokenOutput) - return ret0, ret1 -} - -// GetSessionTokenRequest indicates an expected call of GetSessionTokenRequest. -func (mr *MockSTSAPIMockRecorder) GetSessionTokenRequest(arg0 interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetSessionTokenRequest", reflect.TypeOf((*MockSTSAPI)(nil).GetSessionTokenRequest), arg0) -} - -// GetSessionTokenWithContext mocks base method. -func (m *MockSTSAPI) GetSessionTokenWithContext(arg0 context.Context, arg1 *sts.GetSessionTokenInput, arg2 ...request.Option) (*sts.GetSessionTokenOutput, error) { - m.ctrl.T.Helper() - varargs := []interface{}{arg0, arg1} - for _, a := range arg2 { - varargs = append(varargs, a) - } - ret := m.ctrl.Call(m, "GetSessionTokenWithContext", varargs...) - ret0, _ := ret[0].(*sts.GetSessionTokenOutput) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// GetSessionTokenWithContext indicates an expected call of GetSessionTokenWithContext. -func (mr *MockSTSAPIMockRecorder) GetSessionTokenWithContext(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { - mr.mock.ctrl.T.Helper() - varargs := append([]interface{}{arg0, arg1}, arg2...) - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetSessionTokenWithContext", reflect.TypeOf((*MockSTSAPI)(nil).GetSessionTokenWithContext), varargs...) -} diff --git a/pkg/cloud/throttle/throttle.go b/pkg/cloud/throttle/throttle.go index 5e35323177..1ee1e773ea 100644 --- a/pkg/cloud/throttle/throttle.go +++ b/pkg/cloud/throttle/throttle.go @@ -23,7 +23,6 @@ import ( "strings" awsmiddleware "github.com/aws/aws-sdk-go-v2/aws/middleware" - "github.com/aws/aws-sdk-go/aws/request" "github.com/aws/smithy-go/middleware" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/awserrors" @@ -50,30 +49,13 @@ type OperationLimiter struct { limiter *rate.Limiter } -// Wait will wait on a request. -func (o *OperationLimiter) Wait(r *request.Request) error { - return o.getLimiter().Wait(r.Context()) -} - -// WaitV2 will wait on a request for AWS SDK V2. -func (o *OperationLimiter) WaitV2(ctx context.Context) error { +// Wait will wait on a request for AWS SDK V2. +func (o *OperationLimiter) Wait(ctx context.Context) error { return o.getLimiter().Wait(ctx) } -// Match will match a request. -func (o *OperationLimiter) Match(r *request.Request) (bool, error) { - if o.regexp == nil { - var err error - o.regexp, err = regexp.Compile("^" + o.Operation) - if err != nil { - return false, err - } - } - return o.regexp.MatchString(r.Operation.Name), nil -} - -// MatchV2 will match a request for AWS SDK V2. -func (o *OperationLimiter) MatchV2(ctx context.Context) (bool, error) { +// Match will match a request for AWS SDK V2. +func (o *OperationLimiter) Match(ctx context.Context) (bool, error) { if o.regexp == nil { var err error o.regexp, err = regexp.Compile("^" + o.Operation) @@ -85,17 +67,10 @@ func (o *OperationLimiter) MatchV2(ctx context.Context) (bool, error) { return o.regexp.MatchString(opName), nil } -// LimitRequest will limit a request. -func (s ServiceLimiter) LimitRequest(r *request.Request) { - if ol, ok := s.matchRequest(r); ok { - _ = ol.Wait(r) - } -} - -// LimitRequestV2 will limit a request for AWS SDK V2. -func (s ServiceLimiter) LimitRequestV2(ctx context.Context) { - if ol, ok := s.matchRequestV2(ctx); ok { - _ = ol.WaitV2(ctx) +// LimitRequest will limit a request for AWS SDK V2. +func (s ServiceLimiter) LimitRequest(ctx context.Context) { + if ol, ok := s.matchRequest(ctx); ok { + _ = ol.Wait(ctx) } } @@ -106,47 +81,20 @@ func (o *OperationLimiter) getLimiter() *rate.Limiter { return o.limiter } -// ReviewResponse will review the limits of a Request's response. -func (s ServiceLimiter) ReviewResponse(r *request.Request) { - if r.Error != nil { - if errorCode, ok := awserrors.Code(r.Error); ok { - switch errorCode { - case "Throttling", "RequestLimitExceeded": - if ol, ok := s.matchRequest(r); ok { - ol.limiter.ResetTokens() - } - } - } - } -} - -// ReviewResponseV2 will review the limits of a Request's response for AWS SDK V2. -func (s ServiceLimiter) ReviewResponseV2(ctx context.Context, errorCode string) { +// ReviewResponse will review the limits of a Request's response for AWS SDK V2. +func (s ServiceLimiter) ReviewResponse(ctx context.Context, errorCode string) { switch errorCode { case "Throttling", "RequestLimitExceeded": - if ol, ok := s.matchRequestV2(ctx); ok { + if ol, ok := s.matchRequest(ctx); ok { ol.limiter.ResetTokens() } } } -func (s ServiceLimiter) matchRequest(r *request.Request) (*OperationLimiter, bool) { - for _, ol := range s { - match, err := ol.Match(r) - if err != nil { - return nil, false - } - if match { - return ol, true - } - } - return nil, false -} - -// matchRequestV2 is used for matching request for AWS SDK V2. -func (s ServiceLimiter) matchRequestV2(ctx context.Context) (*OperationLimiter, bool) { +// matchRequest is used for matching request for AWS SDK V2. +func (s ServiceLimiter) matchRequest(ctx context.Context) (*OperationLimiter, bool) { for _, ol := range s { - match, err := ol.MatchV2(ctx) + match, err := ol.Match(ctx) if err != nil { return nil, false } @@ -168,13 +116,13 @@ func WithServiceLimiterMiddleware(limiter *ServiceLimiter) func(stack *middlewar // getServiceLimiterMiddleware implements serviceLimiter middleware. func getServiceLimiterMiddleware(limiter *ServiceLimiter) middleware.FinalizeMiddleware { return middleware.FinalizeMiddlewareFunc("capa/ServiceLimiterMiddleware", func(ctx context.Context, input middleware.FinalizeInput, handler middleware.FinalizeHandler) (middleware.FinalizeOutput, middleware.Metadata, error) { - limiter.LimitRequestV2(ctx) + limiter.LimitRequest(ctx) out, metadata, err := handler.HandleFinalize(ctx, input) smithyErr := awserrors.ParseSmithyError(err) if smithyErr != nil { - limiter.ReviewResponseV2(ctx, smithyErr.ErrorCode()) + limiter.ReviewResponse(ctx, smithyErr.ErrorCode()) return out, metadata, err } diff --git a/pkg/eks/identityprovider/plan_test.go b/pkg/eks/identityprovider/plan_test.go index ff5c1f0956..913d46f687 100644 --- a/pkg/eks/identityprovider/plan_test.go +++ b/pkg/eks/identityprovider/plan_test.go @@ -20,9 +20,9 @@ import ( "context" "testing" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/eks" ekstypes "github.com/aws/aws-sdk-go-v2/service/eks/types" - "github.com/aws/aws-sdk-go/aws" "github.com/golang/mock/gomock" . "github.com/onsi/gomega" "k8s.io/klog/v2" diff --git a/pkg/internal/mime/mime.go b/pkg/internal/mime/mime.go index 7f7b23aa8b..6f15b29e16 100644 --- a/pkg/internal/mime/mime.go +++ b/pkg/internal/mime/mime.go @@ -56,7 +56,7 @@ type scriptVariables struct { // GenerateInitDocument renders a given template, applies MIME properties // and returns a series of byte chunks which put together represent a UserData // script. -func GenerateInitDocument(secretPrefix string, chunks int32, region string, endpoint string, secretFetchScript string) ([]byte, error) { +func GenerateInitDocument(secretPrefix string, chunks int32, region string, secretFetchScript string) ([]byte, error) { var secretFetchTemplate = template.Must(template.New("secret-fetch-script").Parse(secretFetchScript)) var buf bytes.Buffer @@ -71,7 +71,6 @@ func GenerateInitDocument(secretPrefix string, chunks int32, region string, endp SecretPrefix: secretPrefix, Chunks: chunks, Region: region, - Endpoint: endpoint, } var scriptBuf bytes.Buffer diff --git a/pkg/internal/mime/mime_test.go b/pkg/internal/mime/mime_test.go index ad6bdbcbd1..9083ab71b5 100644 --- a/pkg/internal/mime/mime_test.go +++ b/pkg/internal/mime/mime_test.go @@ -24,7 +24,7 @@ import ( func TestGenerateInitDocument(t *testing.T) { secretARN := "secretARN" - doc, _ := GenerateInitDocument(secretARN, 1, "eu-west-1", "localhost", "abc123") + doc, _ := GenerateInitDocument(secretARN, 1, "eu-west-1", "abc123") if _, err := mail.ReadMessage(bytes.NewBuffer(doc)); err != nil { t.Fatalf("Cannot parse MIME doc: %+v\n%s", err, string(doc)) diff --git a/test/e2e/shared/aws.go b/test/e2e/shared/aws.go index 6da52bdea8..8288646156 100644 --- a/test/e2e/shared/aws.go +++ b/test/e2e/shared/aws.go @@ -32,28 +32,29 @@ import ( "strings" "time" - awsv2 "github.com/aws/aws-sdk-go-v2/aws" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/config" awscredsv2 "github.com/aws/aws-sdk-go-v2/credentials" + cfn "github.com/aws/aws-sdk-go-v2/service/cloudformation" + cfntypes "github.com/aws/aws-sdk-go-v2/service/cloudformation/types" + "github.com/aws/aws-sdk-go-v2/service/cloudtrail" + cloudtrailtypes "github.com/aws/aws-sdk-go-v2/service/cloudtrail/types" + configservicetypes "github.com/aws/aws-sdk-go-v2/service/configservice/types" "github.com/aws/aws-sdk-go-v2/service/ec2" ec2types "github.com/aws/aws-sdk-go-v2/service/ec2/types" + "github.com/aws/aws-sdk-go-v2/service/ecrpublic" + ecrpublictypes "github.com/aws/aws-sdk-go-v2/service/ecrpublic/types" + "github.com/aws/aws-sdk-go-v2/service/efs" + efstypes "github.com/aws/aws-sdk-go-v2/service/efs/types" "github.com/aws/aws-sdk-go-v2/service/eks" ekstypes "github.com/aws/aws-sdk-go-v2/service/eks/types" elb "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancing" elbtypes "github.com/aws/aws-sdk-go-v2/service/elasticloadbalancing/types" "github.com/aws/aws-sdk-go-v2/service/iam" iamtypes "github.com/aws/aws-sdk-go-v2/service/iam/types" + "github.com/aws/aws-sdk-go-v2/service/servicequotas" + servicequotastypes "github.com/aws/aws-sdk-go-v2/service/servicequotas/types" "github.com/aws/aws-sdk-go-v2/service/sts" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/client" - awscreds "github.com/aws/aws-sdk-go/aws/credentials" - "github.com/aws/aws-sdk-go/aws/session" - cfn "github.com/aws/aws-sdk-go/service/cloudformation" - "github.com/aws/aws-sdk-go/service/cloudtrail" - "github.com/aws/aws-sdk-go/service/configservice" - "github.com/aws/aws-sdk-go/service/ecrpublic" - "github.com/aws/aws-sdk-go/service/efs" - "github.com/aws/aws-sdk-go/service/servicequotas" "github.com/aws/smithy-go" cfn_iam "github.com/awslabs/goformation/v4/cloudformation/iam" . "github.com/onsi/ginkgo/v2" @@ -371,56 +372,7 @@ func (i *AWSInfrastructure) DeleteInfrastructure(ctx context.Context) { } } -func NewAWSSession() client.ConfigProvider { - By("Getting an AWS IAM session - from environment") - region, err := credentials.ResolveRegion("") - Expect(err).NotTo(HaveOccurred()) - config := aws.NewConfig().WithCredentialsChainVerboseErrors(true).WithRegion(region) - sess, err := session.NewSessionWithOptions(session.Options{ - SharedConfigState: session.SharedConfigEnable, - Config: *config, - }) - Expect(err).NotTo(HaveOccurred()) - _, err = sess.Config.Credentials.Get() - Expect(err).NotTo(HaveOccurred()) - return sess -} - -func NewAWSSessionRepoWithKey(accessKey *iamtypes.AccessKey) client.ConfigProvider { - By("Getting an AWS IAM session - from access key") - Expect(accessKey.AccessKeyId).NotTo(BeNil()) - Expect(accessKey.SecretAccessKey).NotTo(BeNil()) - config := aws.NewConfig().WithCredentialsChainVerboseErrors(true).WithRegion("us-east-1") - config.Credentials = awscreds.NewStaticCredentials(*accessKey.AccessKeyId, *accessKey.SecretAccessKey, "") - - sess, err := session.NewSessionWithOptions(session.Options{ - Config: *config, - }) - Expect(err).NotTo(HaveOccurred()) - _, err = sess.Config.Credentials.Get() - Expect(err).NotTo(HaveOccurred()) - return sess -} - -func NewAWSSessionWithKey(accessKey *iamtypes.AccessKey) client.ConfigProvider { - By("Getting an AWS IAM session - from access key") - Expect(accessKey.AccessKeyId).NotTo(BeNil()) - Expect(accessKey.SecretAccessKey).NotTo(BeNil()) - region, err := credentials.ResolveRegion("") - Expect(err).NotTo(HaveOccurred()) - config := aws.NewConfig().WithCredentialsChainVerboseErrors(true).WithRegion(region) - config.Credentials = awscreds.NewStaticCredentials(*accessKey.AccessKeyId, *accessKey.SecretAccessKey, "") - - sess, err := session.NewSessionWithOptions(session.Options{ - Config: *config, - }) - Expect(err).NotTo(HaveOccurred()) - _, err = sess.Config.Credentials.Get() - Expect(err).NotTo(HaveOccurred()) - return sess -} - -func NewAWSSessionV2() *awsv2.Config { +func NewAWSSession() *aws.Config { By("Getting an AWS IAM session - from environment") region, err := credentials.ResolveRegion("") Expect(err).NotTo(HaveOccurred()) @@ -434,11 +386,11 @@ func NewAWSSessionV2() *awsv2.Config { return &cfg } -func NewAWSSessionRepoWithKeyV2(accessKey *iamtypes.AccessKey) *awsv2.Config { +func NewAWSSessionRepoWithKey(accessKey *iamtypes.AccessKey) *aws.Config { By("Getting an AWS IAM session - from access key") region, err := credentials.ResolveRegion("us-east-1") Expect(err).NotTo(HaveOccurred()) - staticCredProvider := awscredsv2.NewStaticCredentialsProvider(awsv2.ToString(accessKey.AccessKeyId), awsv2.ToString(accessKey.SecretAccessKey), "") + staticCredProvider := awscredsv2.NewStaticCredentialsProvider(aws.ToString(accessKey.AccessKeyId), aws.ToString(accessKey.SecretAccessKey), "") optFns := []func(*config.LoadOptions) error{ config.WithRegion(region), config.WithCredentialsProvider(staticCredProvider), @@ -450,11 +402,11 @@ func NewAWSSessionRepoWithKeyV2(accessKey *iamtypes.AccessKey) *awsv2.Config { return &cfg } -func NewAWSSessionWithKeyV2(accessKey *iamtypes.AccessKey) *awsv2.Config { +func NewAWSSessionWithKey(accessKey *iamtypes.AccessKey) *aws.Config { By("Getting an AWS IAM session - from access key") region, err := credentials.ResolveRegion("") Expect(err).NotTo(HaveOccurred()) - staticCredProvider := awscredsv2.NewStaticCredentialsProvider(awsv2.ToString(accessKey.AccessKeyId), awsv2.ToString(accessKey.SecretAccessKey), "") + staticCredProvider := awscredsv2.NewStaticCredentialsProvider(aws.ToString(accessKey.AccessKeyId), aws.ToString(accessKey.SecretAccessKey), "") optFns := []func(*config.LoadOptions) error{ config.WithRegion(region), config.WithCredentialsProvider(staticCredProvider), @@ -467,15 +419,19 @@ func NewAWSSessionWithKeyV2(accessKey *iamtypes.AccessKey) *awsv2.Config { } // createCloudFormationStack ensures the cloudformation stack is up to date. -func createCloudFormationStack(ctx context.Context, cfg *awsv2.Config, prov client.ConfigProvider, t *cfn_bootstrap.Template, tags map[string]string) error { +func createCloudFormationStack(ctx context.Context, cfg *aws.Config, t *cfn_bootstrap.Template, tags map[string]string) error { By(fmt.Sprintf("Creating AWS CloudFormation stack for AWS IAM resources: stack-name=%s", t.Spec.StackName)) - cfnClient := cfn.New(prov) + cfnClient := cfn.NewFromConfig(*cfg) // CloudFormation stack will clean up on a failure, we don't need an Eventually here. // The `create` already does a WaitUntilStackCreateComplete. - cfnSvc := cloudformation.NewService(cfnClient) - if err := cfnSvc.ReconcileBootstrapNoUpdate(t.Spec.StackName, *renderCustomCloudFormation(t), tags); err != nil { + cfnSvc := cloudformation.NewService( + &cloudformation.CFNClient{ + Client: cfnClient, + }) + + if err := cfnSvc.ReconcileBootstrapNoUpdate(ctx, t.Spec.StackName, *renderCustomCloudFormation(t), tags); err != nil { By(fmt.Sprintf("Error reconciling Cloud formation stack %v", err)) - spewCloudFormationResources(cfnClient, t) + spewCloudFormationResources(ctx, cfnClient, t) // always clean up on a failure because we could leak these resources and the next cloud formation create would // fail with the same problem. @@ -484,22 +440,22 @@ func createCloudFormationStack(ctx context.Context, cfg *awsv2.Config, prov clie return err } - spewCloudFormationResources(cfnClient, t) + spewCloudFormationResources(ctx, cfnClient, t) return nil } -func spewCloudFormationResources(cfnClient *cfn.CloudFormation, t *cfn_bootstrap.Template) { - output, err := cfnClient.DescribeStackEvents(&cfn.DescribeStackEventsInput{StackName: aws.String(t.Spec.StackName), NextToken: aws.String("1")}) +func spewCloudFormationResources(ctx context.Context, cfnClient *cfn.Client, t *cfn_bootstrap.Template) { + output, err := cfnClient.DescribeStackEvents(ctx, &cfn.DescribeStackEventsInput{StackName: aws.String(t.Spec.StackName), NextToken: aws.String("1")}) if err != nil { By(fmt.Sprintf("Error describin Cloud formation stack events %v, skipping", err)) } else { By("========= Stack Event Output Begin =========") for _, event := range output.StackEvents { - By(fmt.Sprintf("Event details for %s : Resource: %s, Status: %s, Reason: %s", aws.StringValue(event.LogicalResourceId), aws.StringValue(event.ResourceType), aws.StringValue(event.ResourceStatus), aws.StringValue(event.ResourceStatusReason))) + By(fmt.Sprintf("Event details for %s : Resource: %s, Status: %s, Reason: %s", aws.ToString(event.LogicalResourceId), aws.ToString(event.ResourceType), event.ResourceStatus, aws.ToString(event.ResourceStatusReason))) } By("========= Stack Event Output End =========") } - out, err := cfnClient.DescribeStackResources(&cfn.DescribeStackResourcesInput{ + out, err := cfnClient.DescribeStackResources(ctx, &cfn.DescribeStackResourcesInput{ StackName: aws.String(t.Spec.StackName), }) if err != nil { @@ -510,16 +466,16 @@ func spewCloudFormationResources(cfnClient *cfn.CloudFormation, t *cfn_bootstrap for _, r := range out.StackResources { By(fmt.Sprintf("%s\t%s\t%s\t%s", - aws.StringValue(r.ResourceType), - aws.StringValue(r.PhysicalResourceId), - aws.StringValue(r.ResourceStatus), - aws.StringValue(r.ResourceStatusReason))) + aws.ToString(r.ResourceType), + aws.ToString(r.PhysicalResourceId), + r.ResourceStatus, + aws.ToString(r.ResourceStatusReason))) } By("========= Stack Resources Output End =========") } } -func SetMultitenancyEnvVars(ctx context.Context, cfg *awsv2.Config) error { +func SetMultitenancyEnvVars(ctx context.Context, cfg *aws.Config) error { for _, roles := range MultiTenancyRoles { if err := roles.SetEnvVars(ctx, cfg); err != nil { return err @@ -529,7 +485,7 @@ func SetMultitenancyEnvVars(ctx context.Context, cfg *awsv2.Config) error { } // Delete resources that already exists. -func deleteResourcesInCloudFormation(ctx context.Context, cfg *awsv2.Config, t *cfn_bootstrap.Template) { +func deleteResourcesInCloudFormation(ctx context.Context, cfg *aws.Config, t *cfn_bootstrap.Template) { iamSvc := iam.NewFromConfig(*cfg) temp := *renderCustomCloudFormation(t) var ( @@ -543,20 +499,20 @@ func deleteResourcesInCloudFormation(ctx context.Context, cfg *awsv2.Config, t * // so they don't have any attached resources which prevents their deletion. // temp.Resources is a map. Traversing that directly results in undetermined order. for _, val := range temp.Resources { - switch val.AWSCloudFormationType() { - case configservice.ResourceTypeAwsIamUser: + switch configservicetypes.ResourceType(val.AWSCloudFormationType()) { + case configservicetypes.ResourceTypeUser: user := val.(*cfn_iam.User) iamUsers = append(iamUsers, user) - case configservice.ResourceTypeAwsIamRole: + case configservicetypes.ResourceTypeRole: role := val.(*cfn_iam.Role) iamRoles = append(iamRoles, role) - case "AWS::IAM::InstanceProfile": + case configservicetypes.ResourceTypeIAMInstanceProfile: profile := val.(*cfn_iam.InstanceProfile) instanceProfiles = append(instanceProfiles, profile) - case "AWS::IAM::ManagedPolicy": + case configservicetypes.ResourceType("AWS::IAM::ManagedPolicy"): policy := val.(*cfn_iam.ManagedPolicy) policies = append(policies, policy) - case configservice.ResourceTypeAwsIamGroup: + case configservicetypes.ResourceTypeGroup: group := val.(*cfn_iam.Group) groups = append(groups, group) } @@ -621,8 +577,8 @@ func deleteResourcesInCloudFormation(ctx context.Context, cfg *awsv2.Config, t * Expect(err).NotTo(HaveOccurred()) if len(listPoliciesOutput.Policies) > 0 { for _, p := range listPoliciesOutput.Policies { - if awsv2.ToString(p.PolicyName) == policy.ManagedPolicyName { - By(fmt.Sprintf("cleanup for policy '%s'", awsv2.ToString(p.PolicyName))) + if aws.ToString(p.PolicyName) == policy.ManagedPolicyName { + By(fmt.Sprintf("cleanup for policy '%s'", aws.ToString(p.PolicyName))) repeat := false Eventually(func(gomega Gomega) bool { _, err := iamSvc.DeletePolicy(ctx, &iam.DeletePolicyInput{ @@ -634,7 +590,7 @@ func deleteResourcesInCloudFormation(ctx context.Context, cfg *awsv2.Config, t * } var noSuchEntityErr *iamtypes.NoSuchEntityException return err == nil || errors.As(err, &noSuchEntityErr) - }, 5*time.Minute, 5*time.Second).Should(BeTrue(), fmt.Sprintf("Eventually failed to delete policy %q", awsv2.ToString(p.PolicyName))) + }, 5*time.Minute, 5*time.Second).Should(BeTrue(), fmt.Sprintf("Eventually failed to delete policy %q", aws.ToString(p.PolicyName))) // TODO: why is there a break here? Don't we want to clean up everything? break } @@ -644,7 +600,7 @@ func deleteResourcesInCloudFormation(ctx context.Context, cfg *awsv2.Config, t * } // TODO: remove once test infra accounts are fixed. -func deleteMultitenancyRoles(ctx context.Context, cfg *awsv2.Config) { +func deleteMultitenancyRoles(ctx context.Context, cfg *aws.Config) { if err := DeleteRole(ctx, cfg, "multi-tenancy-role"); err != nil { By(fmt.Sprintf("failed to delete role multi-tenancy-role %s", err)) } @@ -654,7 +610,7 @@ func deleteMultitenancyRoles(ctx context.Context, cfg *awsv2.Config) { } // detachAllPoliciesForRole detaches all policies for role. -func detachAllPoliciesForRole(ctx context.Context, cfg *awsv2.Config, name string) error { +func detachAllPoliciesForRole(ctx context.Context, cfg *aws.Config, name string) error { iamSvc := iam.NewFromConfig(*cfg) input := &iam.ListAttachedRolePoliciesInput{ @@ -681,7 +637,7 @@ func detachAllPoliciesForRole(ctx context.Context, cfg *awsv2.Config, name strin } // DeleteUser deletes an IAM user in a best effort manner. -func DeleteUser(ctx context.Context, cfg *awsv2.Config, name string) error { +func DeleteUser(ctx context.Context, cfg *aws.Config, name string) error { iamSvc := iam.NewFromConfig(*cfg) // if user does not exist, return. @@ -699,7 +655,7 @@ func DeleteUser(ctx context.Context, cfg *awsv2.Config, name string) error { } // DeleteRole deletes roles in a best effort manner. -func DeleteRole(ctx context.Context, cfg *awsv2.Config, name string) error { +func DeleteRole(ctx context.Context, cfg *aws.Config, name string) error { iamSvc := iam.NewFromConfig(*cfg) // if role does not exist, return. @@ -720,7 +676,7 @@ func DeleteRole(ctx context.Context, cfg *awsv2.Config, name string) error { return nil } -func GetPolicyArn(ctx context.Context, cfg awsv2.Config, name string) string { +func GetPolicyArn(ctx context.Context, cfg aws.Config, name string) string { iamSvc := iam.NewFromConfig(cfg) policyList, err := iamSvc.ListPolicies(ctx, &iam.ListPoliciesInput{ @@ -729,14 +685,14 @@ func GetPolicyArn(ctx context.Context, cfg awsv2.Config, name string) string { Expect(err).NotTo(HaveOccurred()) for _, policy := range policyList.Policies { - if awsv2.ToString(policy.PolicyName) == name { - return awsv2.ToString(policy.Arn) + if aws.ToString(policy.PolicyName) == name { + return aws.ToString(policy.Arn) } } return "" } -func logAccountDetails(cfg *awsv2.Config) { +func logAccountDetails(cfg *aws.Config) { By("Getting AWS account details") stsSvc := sts.NewFromConfig(*cfg) @@ -750,38 +706,42 @@ func logAccountDetails(cfg *awsv2.Config) { } // deleteCloudFormationStack removes the provisioned clusterawsadm stack. -func deleteCloudFormationStack(prov client.ConfigProvider, t *cfn_bootstrap.Template) { +func deleteCloudFormationStack(cfg *aws.Config, t *cfn_bootstrap.Template) { By(fmt.Sprintf("Deleting %s CloudFormation stack", t.Spec.StackName)) - CFN := cfn.New(prov) - cfnSvc := cloudformation.NewService(CFN) - err := cfnSvc.DeleteStack(t.Spec.StackName, nil) + ctx := context.TODO() + CFN := cfn.NewFromConfig(*cfg) + cfnSvc := cloudformation.NewService( + &cloudformation.CFNClient{ + Client: CFN, + }) + err := cfnSvc.DeleteStack(context.TODO(), t.Spec.StackName, nil) if err != nil { - var retainResources []*string - out, err := CFN.DescribeStackResources(&cfn.DescribeStackResourcesInput{StackName: aws.String(t.Spec.StackName)}) + var retainResources []string + out, err := CFN.DescribeStackResources(ctx, &cfn.DescribeStackResourcesInput{StackName: aws.String(t.Spec.StackName)}) Expect(err).NotTo(HaveOccurred()) for _, v := range out.StackResources { - if aws.StringValue(v.ResourceStatus) == cfn.ResourceStatusDeleteFailed { - retainResources = append(retainResources, v.LogicalResourceId) + if v.ResourceStatus == cfntypes.ResourceStatusDeleteFailed { + retainResources = append(retainResources, aws.ToString(v.LogicalResourceId)) } } - err = cfnSvc.DeleteStack(t.Spec.StackName, retainResources) + err = cfnSvc.DeleteStack(ctx, t.Spec.StackName, retainResources) Expect(err).NotTo(HaveOccurred()) } - err = CFN.WaitUntilStackDeleteComplete(&cfn.DescribeStacksInput{ + err = cfnSvc.CFN.WaitUntilStackDeleteComplete(ctx, &cfn.DescribeStacksInput{ StackName: aws.String(t.Spec.StackName), - }) + }, cloudformation.MaxWaitCreateUpdateDelete) Expect(err).NotTo(HaveOccurred()) } -func ensureTestImageUploaded(e2eCtx *E2EContext) error { +func ensureTestImageUploaded(ctx context.Context, e2eCtx *E2EContext) error { sessionForRepo := NewAWSSessionRepoWithKey(e2eCtx.Environment.BootstrapAccessKey) - ecrSvc := ecrpublic.New(sessionForRepo) + ecrSvc := ecrpublic.NewFromConfig(*sessionForRepo) repoName := "" if err := wait.WaitForWithRetryable(wait.NewBackoff(), func() (bool, error) { - output, err := ecrSvc.CreateRepository(&ecrpublic.CreateRepositoryInput{ + output, err := ecrSvc.CreateRepository(ctx, &ecrpublic.CreateRepositoryInput{ RepositoryName: aws.String("capa/update"), - CatalogData: &ecrpublic.RepositoryCatalogDataInput{ + CatalogData: &ecrpublictypes.RepositoryCatalogDataInput{ AboutText: aws.String("Created by cluster-api-provider-aws/test/e2e/shared/aws.go for E2E tests"), }, }) @@ -790,13 +750,13 @@ func ensureTestImageUploaded(e2eCtx *E2EContext) error { if !awserrors.IsRepositoryExists(err) { return false, err } - out, err := ecrSvc.DescribeRepositories(&ecrpublic.DescribeRepositoriesInput{RepositoryNames: []*string{aws.String("capa/update")}}) + out, err := ecrSvc.DescribeRepositories(ctx, &ecrpublic.DescribeRepositoriesInput{RepositoryNames: []string{"capa/update"}}) if err != nil || len(out.Repositories) == 0 { return false, err } - repoName = aws.StringValue(out.Repositories[0].RepositoryUri) + repoName = aws.ToString(out.Repositories[0].RepositoryUri) } else { - repoName = aws.StringValue(output.Repository.RepositoryUri) + repoName = aws.ToString(output.Repository.RepositoryUri) } return true, nil @@ -821,13 +781,13 @@ func ensureTestImageUploaded(e2eCtx *E2EContext) error { return err } - outToken, err := ecrSvc.GetAuthorizationToken(&ecrpublic.GetAuthorizationTokenInput{}) + outToken, err := ecrSvc.GetAuthorizationToken(ctx, &ecrpublic.GetAuthorizationTokenInput{}) if err != nil { return err } // Auth token is in username:password format. To login using it, we need to decode first and separate password and username - decodedUsernamePassword, _ := b64.StdEncoding.DecodeString(aws.StringValue(outToken.AuthorizationData.AuthorizationToken)) + decodedUsernamePassword, _ := b64.StdEncoding.DecodeString(aws.ToString(outToken.AuthorizationData.AuthorizationToken)) strList := strings.Split(string(decodedUsernamePassword), ":") if len(strList) != 2 { @@ -852,7 +812,7 @@ func ensureTestImageUploaded(e2eCtx *E2EContext) error { // ensureNoServiceLinkedRoles removes an auto-created IAM role, and tests // the controller's IAM permissions to use ELB and Spot instances successfully. -func ensureNoServiceLinkedRoles(ctx context.Context, cfg *awsv2.Config) { +func ensureNoServiceLinkedRoles(ctx context.Context, cfg *aws.Config) { iamSvc := iam.NewFromConfig(*cfg) By("Deleting AWS IAM Service Linked Role: role-name=AWSServiceRoleForElasticLoadBalancing") @@ -876,7 +836,7 @@ func ensureNoServiceLinkedRoles(ctx context.Context, cfg *awsv2.Config) { } // ensureSSHKeyPair ensures A SSH key is present under the name. -func ensureSSHKeyPair(config awsv2.Config, keyPairName string) { +func ensureSSHKeyPair(config aws.Config, keyPairName string) { By(fmt.Sprintf("Ensuring presence of SSH key in EC2: key-name=%s", keyPairName)) ec2c := ec2.NewFromConfig(config) _, err := ec2c.CreateKeyPair(context.TODO(), &ec2.CreateKeyPairInput{KeyName: aws.String(keyPairName)}) @@ -886,10 +846,10 @@ func ensureSSHKeyPair(config awsv2.Config, keyPairName string) { } } -func ensureStackTags(prov client.ConfigProvider, stackName string, expectedTags map[string]string) { +func ensureStackTags(cfg *aws.Config, stackName string, expectedTags map[string]string) { By(fmt.Sprintf("Ensuring AWS CloudFormation stack is created or updated with the specified tags: stack-name=%s", stackName)) - CFN := cfn.New(prov) - r, err := CFN.DescribeStacks(&cfn.DescribeStacksInput{StackName: &stackName}) + CFN := cfn.NewFromConfig(*cfg) + r, err := CFN.DescribeStacks(context.TODO(), &cfn.DescribeStacksInput{StackName: &stackName}) Expect(err).NotTo(HaveOccurred()) stacks := r.Stacks Expect(len(stacks)).To(BeNumerically("==", 1)) @@ -914,7 +874,7 @@ func encodeCredentials(accessKey *iamtypes.AccessKey, region string) string { // newUserAccessKey generates a new AWS Access Key pair based off of the // bootstrap user. This tests that the CloudFormation policy is correct. -func newUserAccessKey(ctx context.Context, cfg *awsv2.Config, userName string) *iamtypes.AccessKey { +func newUserAccessKey(ctx context.Context, cfg *aws.Config, userName string) *iamtypes.AccessKey { iamSvc := iam.NewFromConfig(*cfg) keyOuts, _ := iamSvc.ListAccessKeys(ctx, &iam.ListAccessKeysInput{ @@ -947,21 +907,22 @@ func DumpCloudTrailEvents(e2eCtx *E2EContext) { return } - client := cloudtrail.New(e2eCtx.BootstrapUserAWSSession) - events := []*cloudtrail.Event{} - err := client.LookupEventsPages( - &cloudtrail.LookupEventsInput{ - StartTime: aws.Time(e2eCtx.StartOfSuite), - EndTime: aws.Time(time.Now()), - }, - func(page *cloudtrail.LookupEventsOutput, lastPage bool) bool { - events = append(events, page.Events...) - return !lastPage - }, - ) - if err != nil { - fmt.Fprintf(GinkgoWriter, "Couldn't get AWS CloudTrail events: err=%v\n", err) + client := cloudtrail.NewFromConfig(*e2eCtx.BootstrapUserAWSSession) + events := []cloudtrailtypes.Event{} + + paginator := cloudtrail.NewLookupEventsPaginator(client, &cloudtrail.LookupEventsInput{ + StartTime: aws.Time(e2eCtx.StartOfSuite), + EndTime: aws.Time(time.Now()), + }) + + for paginator.HasMorePages() { + page, err := paginator.NextPage(context.TODO()) + if err != nil { + fmt.Fprintf(GinkgoWriter, "Couldn't get AWS CloudTrail events: err=%v\n", err) + } + events = append(events, page.Events...) } + logPath := filepath.Join(e2eCtx.Settings.ArtifactFolder, "cloudtrail-events.yaml") dat, err := yaml.Marshal(events) if err != nil { @@ -980,7 +941,7 @@ func conformanceImageID(e2eCtx *E2EContext) string { amiName := AMIPrefix + ver + "*" By(fmt.Sprintf("Searching for AMI: name=%s", amiName)) - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filters := []ec2types.Filter{ { Name: aws.String("name"), @@ -996,12 +957,12 @@ func conformanceImageID(e2eCtx *E2EContext) string { }) Expect(err).NotTo(HaveOccurred()) Expect(len(resp.Images)).To(Not(BeZero())) - imageID := aws.StringValue(resp.Images[0].ImageId) + imageID := aws.ToString(resp.Images[0].ImageId) By(fmt.Sprintf("Using AMI: image-id=%s", imageID)) return imageID } -func GetAvailabilityZones(config awsv2.Config) []ec2types.AvailabilityZone { +func GetAvailabilityZones(config aws.Config) []ec2types.AvailabilityZone { ec2Client := ec2.NewFromConfig(config) azs, err := ec2Client.DescribeAvailabilityZones(context.TODO(), nil) Expect(err).NotTo(HaveOccurred()) @@ -1017,39 +978,41 @@ type ServiceQuota struct { RequestStatus string } -func EnsureServiceQuotas(sess client.ConfigProvider) (map[string]*ServiceQuota, map[string]*servicequotas.ServiceQuota) { +func EnsureServiceQuotas(sess *aws.Config) (map[string]*ServiceQuota, map[string]*servicequotastypes.ServiceQuota) { + ctx := context.TODO() limitedResources := getLimitedResources() - serviceQuotasClient := servicequotas.New(sess) + serviceQuotasClient := servicequotas.NewFromConfig(*sess) - originalQuotas := map[string]*servicequotas.ServiceQuota{} + originalQuotas := map[string]*servicequotastypes.ServiceQuota{} for k, v := range limitedResources { - out, err := serviceQuotasClient.GetServiceQuota(&servicequotas.GetServiceQuotaInput{ + out, err := serviceQuotasClient.GetServiceQuota(ctx, &servicequotas.GetServiceQuotaInput{ QuotaCode: aws.String(v.QuotaCode), ServiceCode: aws.String(v.ServiceCode), }) Expect(err).NotTo(HaveOccurred()) originalQuotas[k] = out.Quota - v.Value = int(aws.Float64Value(out.Quota.Value)) + v.Value = int(aws.ToFloat64(out.Quota.Value)) limitedResources[k] = v if v.Value < v.DesiredMinimumValue { - v.attemptRaiseServiceQuotaRequest(serviceQuotasClient) + v.attemptRaiseServiceQuotaRequest(ctx, serviceQuotasClient) } } return limitedResources, originalQuotas } -func (s *ServiceQuota) attemptRaiseServiceQuotaRequest(serviceQuotasClient *servicequotas.ServiceQuotas) { - s.updateServiceQuotaRequestStatus(serviceQuotasClient) +func (s *ServiceQuota) attemptRaiseServiceQuotaRequest(ctx context.Context, serviceQuotasClient *servicequotas.Client) { + s.updateServiceQuotaRequestStatus(ctx, serviceQuotasClient) if s.RequestStatus == "" { - s.raiseServiceRequest(serviceQuotasClient) + s.raiseServiceRequest(ctx, serviceQuotasClient) } } -func (s *ServiceQuota) raiseServiceRequest(serviceQuotasClient *servicequotas.ServiceQuotas) { +func (s *ServiceQuota) raiseServiceRequest(ctx context.Context, serviceQuotasClient *servicequotas.Client) { fmt.Printf("Requesting service quota increase for %s/%s to %d\n", s.ServiceCode, s.QuotaName, s.DesiredMinimumValue) out, err := serviceQuotasClient.RequestServiceQuotaIncrease( + ctx, &servicequotas.RequestServiceQuotaIncreaseInput{ DesiredValue: aws.Float64(float64(s.DesiredMinimumValue)), ServiceCode: aws.String(s.ServiceCode), @@ -1059,27 +1022,28 @@ func (s *ServiceQuota) raiseServiceRequest(serviceQuotasClient *servicequotas.Se if err != nil { fmt.Printf("Unable to raise quota for %s/%s: %s\n", s.ServiceCode, s.QuotaName, err) } else { - s.RequestStatus = aws.StringValue(out.RequestedQuota.Status) + s.RequestStatus = string(out.RequestedQuota.Status) } } -func (s *ServiceQuota) updateServiceQuotaRequestStatus(serviceQuotasClient *servicequotas.ServiceQuotas) { +func (s *ServiceQuota) updateServiceQuotaRequestStatus(ctx context.Context, serviceQuotasClient *servicequotas.Client) { params := &servicequotas.ListRequestedServiceQuotaChangeHistoryInput{ ServiceCode: aws.String(s.ServiceCode), } - latestRequest := &servicequotas.RequestedServiceQuotaChange{} - _ = serviceQuotasClient.ListRequestedServiceQuotaChangeHistoryPages(params, - func(page *servicequotas.ListRequestedServiceQuotaChangeHistoryOutput, lastPage bool) bool { - for _, v := range page.RequestedQuotas { - if int(aws.Float64Value(v.DesiredValue)) >= s.DesiredMinimumValue && aws.StringValue(v.QuotaCode) == s.QuotaCode && aws.TimeValue(v.Created).After(aws.TimeValue(latestRequest.Created)) { - latestRequest = v - } + latestRequest := &servicequotastypes.RequestedServiceQuotaChange{} + + paginator := servicequotas.NewListRequestedServiceQuotaChangeHistoryPaginator(serviceQuotasClient, params) + for paginator.HasMorePages() { + page, _ := paginator.NextPage(ctx) + for _, v := range page.RequestedQuotas { + if int(aws.ToFloat64(v.DesiredValue)) >= s.DesiredMinimumValue && aws.ToString(v.QuotaCode) == s.QuotaCode && aws.ToTime(v.Created).After(aws.ToTime(latestRequest.Created)) { + latestRequest = &v } - return !lastPage - }, - ) - if latestRequest.Status != nil { - s.RequestStatus = aws.StringValue(latestRequest.Status) + } + } + + if latestRequest.Status != "" { + s.RequestStatus = string(latestRequest.Status) } } @@ -1097,10 +1061,10 @@ func DumpEKSClusters(ctx context.Context, e2eCtx *E2EContext) { input := &eks.ListClustersInput{} var eksClient *eks.Client - if e2eCtx.BootstrapUserAWSSessionV2 == nil && e2eCtx.AWSSessionV2 != nil { - eksClient = eks.NewFromConfig(*e2eCtx.AWSSessionV2) - } else if e2eCtx.BootstrapUserAWSSessionV2 != nil { - eksClient = eks.NewFromConfig(*e2eCtx.BootstrapUserAWSSessionV2) + if e2eCtx.BootstrapUserAWSSession == nil && e2eCtx.AWSSession != nil { + eksClient = eks.NewFromConfig(*e2eCtx.AWSSession) + } else if e2eCtx.BootstrapUserAWSSession != nil { + eksClient = eks.NewFromConfig(*e2eCtx.BootstrapUserAWSSession) } else { Fail("Couldn't list EKS clusters: no AWS client was set up (please look at previous errors)") return @@ -1151,7 +1115,7 @@ func dumpEKSCluster(cluster *ekstypes.Cluster, logPath string) { // ListVpcInternetGateways, ListNATGateways, ListRunningEC2, ListVPC. func ListVpcInternetGateways(e2eCtx *E2EContext) ([]ec2types.InternetGateway, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) out, err := ec2Svc.DescribeInternetGateways(context.TODO(), &ec2.DescribeInternetGatewaysInput{}) if err != nil { @@ -1162,7 +1126,7 @@ func ListVpcInternetGateways(e2eCtx *E2EContext) ([]ec2types.InternetGateway, er } func ListNATGateways(e2eCtx *E2EContext) (map[string]ec2types.NatGateway, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) describeNatGatewayInput := &ec2.DescribeNatGatewaysInput{ Filter: []ec2types.Filter{ @@ -1179,7 +1143,7 @@ func ListNATGateways(e2eCtx *E2EContext) (map[string]ec2types.NatGateway, error) return nil, fmt.Errorf("failed to describe NAT gateways: %w", err) } for _, r := range page.NatGateways { - gateways[aws.StringValue(r.SubnetId)] = r + gateways[aws.ToString(r.SubnetId)] = r } } @@ -1188,7 +1152,7 @@ func ListNATGateways(e2eCtx *E2EContext) (map[string]ec2types.NatGateway, error) // listRunningEC2 returns a list of running EC2 instances. func listRunningEC2(e2eCtx *E2EContext) ([]instance, error) { //nolint:unused - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) resp, err := ec2Svc.DescribeInstances(context.TODO(), &ec2.DescribeInstancesInput{ Filters: []ec2types.Filter{filter.EC2.InstanceStates(ec2types.InstanceStateNameRunning)}, @@ -1205,8 +1169,8 @@ func listRunningEC2(e2eCtx *E2EContext) ([]instance, error) { //nolint:unused tags := i.Tags name := "" for _, t := range tags { - if aws.StringValue(t.Key) == "Name" { - name = aws.StringValue(t.Value) + if aws.ToString(t.Key) == "Name" { + name = aws.ToString(t.Value) } } if name == "" { @@ -1215,7 +1179,7 @@ func listRunningEC2(e2eCtx *E2EContext) ([]instance, error) { //nolint:unused instances = append(instances, instance{ name: name, - instanceID: aws.StringValue(i.InstanceId), + instanceID: aws.ToString(i.InstanceId), }, ) } @@ -1224,7 +1188,7 @@ func listRunningEC2(e2eCtx *E2EContext) ([]instance, error) { //nolint:unused } func ListClusterEC2Instances(e2eCtx *E2EContext, clusterName string) ([]ec2types.Instance, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("tag-key"), Values: []string{"sigs.k8s.io/cluster-api-provider-aws/cluster/" + clusterName}, @@ -1269,7 +1233,7 @@ func WaitForInstanceState(e2eCtx *E2EContext, clusterName string, state string) } func TerminateInstance(e2eCtx *E2EContext, instanceID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.TerminateInstancesInput{ InstanceIds: []string{instanceID}, @@ -1282,7 +1246,7 @@ func TerminateInstance(e2eCtx *E2EContext, instanceID string) bool { } func ListVPC(e2eCtx *E2EContext) int { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DescribeVpcsInput{ Filters: []ec2types.Filter{ @@ -1299,7 +1263,7 @@ func ListVPC(e2eCtx *E2EContext) int { } func GetVPC(e2eCtx *E2EContext, vpcID string) (*ec2types.Vpc, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("vpc-id"), @@ -1323,7 +1287,7 @@ func GetVPC(e2eCtx *E2EContext, vpcID string) (*ec2types.Vpc, error) { } func GetVPCByName(e2eCtx *E2EContext, vpcName string) (*ec2types.Vpc, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("tag:Name"), @@ -1347,7 +1311,7 @@ func GetVPCByName(e2eCtx *E2EContext, vpcName string) (*ec2types.Vpc, error) { } func GetVPCEndpointsByID(e2eCtx *E2EContext, vpcID string) ([]ec2types.VpcEndpoint, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DescribeVpcEndpointsInput{ Filters: []ec2types.Filter{ @@ -1372,7 +1336,7 @@ func GetVPCEndpointsByID(e2eCtx *E2EContext, vpcID string) ([]ec2types.VpcEndpoi } func CreateVPC(e2eCtx *E2EContext, vpcName string, cidrBlock string) (*ec2types.Vpc, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.CreateVpcInput{ CidrBlock: aws.String(cidrBlock), @@ -1396,7 +1360,7 @@ func CreateVPC(e2eCtx *E2EContext, vpcName string, cidrBlock string) (*ec2types. } func DisassociateVpcCidrBlock(e2eCtx *E2EContext, assocID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DisassociateVpcCidrBlockInput{ AssociationId: aws.String(assocID), @@ -1409,7 +1373,7 @@ func DisassociateVpcCidrBlock(e2eCtx *E2EContext, assocID string) bool { } func DeleteVPC(e2eCtx *E2EContext, vpcID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DeleteVpcInput{ VpcId: aws.String(vpcID), @@ -1421,7 +1385,7 @@ func DeleteVPC(e2eCtx *E2EContext, vpcID string) bool { } func ListVpcSubnets(e2eCtx *E2EContext, vpcID string) ([]ec2types.Subnet, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("vpc-id"), @@ -1442,7 +1406,7 @@ func ListVpcSubnets(e2eCtx *E2EContext, vpcID string) ([]ec2types.Subnet, error) } func GetSubnet(e2eCtx *E2EContext, subnetID string) (*ec2types.Subnet, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("subnet-id"), @@ -1466,7 +1430,7 @@ func GetSubnet(e2eCtx *E2EContext, subnetID string) (*ec2types.Subnet, error) { } func GetSubnetByName(e2eCtx *E2EContext, name string) (*ec2types.Subnet, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("tag:Name"), @@ -1490,7 +1454,7 @@ func GetSubnetByName(e2eCtx *E2EContext, name string) (*ec2types.Subnet, error) } func CreateSubnet(e2eCtx *E2EContext, clusterName string, cidrBlock string, az string, vpcID string, st string) (*ec2types.Subnet, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.CreateSubnetInput{ CidrBlock: aws.String(cidrBlock), @@ -1520,7 +1484,7 @@ func CreateSubnet(e2eCtx *E2EContext, clusterName string, cidrBlock string, az s } func DeleteSubnet(e2eCtx *E2EContext, subnetID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DeleteSubnetInput{ SubnetId: aws.String(subnetID), @@ -1533,7 +1497,7 @@ func DeleteSubnet(e2eCtx *E2EContext, subnetID string) bool { } func GetAddress(e2eCtx *E2EContext, allocationID string) (*ec2types.Address, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("allocation-id"), @@ -1557,7 +1521,7 @@ func GetAddress(e2eCtx *E2EContext, allocationID string) (*ec2types.Address, err } func AllocateAddress(e2eCtx *E2EContext, eipName string) (*ec2.AllocateAddressOutput, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.AllocateAddressInput{ Domain: ec2types.DomainTypeVpc, @@ -1582,7 +1546,7 @@ func AllocateAddress(e2eCtx *E2EContext, eipName string) (*ec2.AllocateAddressOu } func DisassociateAddress(e2eCtx *E2EContext, assocID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DisassociateAddressInput{ AssociationId: aws.String(assocID), @@ -1595,7 +1559,7 @@ func DisassociateAddress(e2eCtx *E2EContext, assocID string) bool { } func ReleaseAddress(e2eCtx *E2EContext, allocationID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.ReleaseAddressInput{ AllocationId: aws.String(allocationID), @@ -1608,7 +1572,7 @@ func ReleaseAddress(e2eCtx *E2EContext, allocationID string) bool { } func CreateNatGateway(e2eCtx *E2EContext, gatewayName string, connectType string, allocationID string, subnetID string) (*ec2types.NatGateway, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.CreateNatGatewayInput{ SubnetId: aws.String(subnetID), @@ -1641,7 +1605,7 @@ func CreateNatGateway(e2eCtx *E2EContext, gatewayName string, connectType string } func GetNatGateway(e2eCtx *E2EContext, gatewayID string) (*ec2types.NatGateway, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("nat-gateway-id"), @@ -1665,7 +1629,7 @@ func GetNatGateway(e2eCtx *E2EContext, gatewayID string) (*ec2types.NatGateway, } func DeleteNatGateway(e2eCtx *E2EContext, gatewayID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DeleteNatGatewayInput{ NatGatewayId: aws.String(gatewayID), @@ -1687,7 +1651,7 @@ func WaitForNatGatewayState(e2eCtx *E2EContext, gatewayID string, state string) } func CreateInternetGateway(e2eCtx *E2EContext, gatewayName string) (*ec2types.InternetGateway, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.CreateInternetGatewayInput{ TagSpecifications: []ec2types.TagSpecification{ @@ -1711,7 +1675,7 @@ func CreateInternetGateway(e2eCtx *E2EContext, gatewayName string) (*ec2types.In } func GetInternetGateway(e2eCtx *E2EContext, gatewayID string) (*ec2types.InternetGateway, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("internet-gateway-id"), @@ -1735,7 +1699,7 @@ func GetInternetGateway(e2eCtx *E2EContext, gatewayID string) (*ec2types.Interne } func DeleteInternetGateway(e2eCtx *E2EContext, gatewayID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DeleteInternetGatewayInput{ InternetGatewayId: aws.String(gatewayID), @@ -1748,7 +1712,7 @@ func DeleteInternetGateway(e2eCtx *E2EContext, gatewayID string) bool { } func AttachInternetGateway(e2eCtx *E2EContext, gatewayID string, vpcID string) (bool, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.AttachInternetGatewayInput{ InternetGatewayId: aws.String(gatewayID), @@ -1762,7 +1726,7 @@ func AttachInternetGateway(e2eCtx *E2EContext, gatewayID string, vpcID string) ( } func DetachInternetGateway(e2eCtx *E2EContext, gatewayID string, vpcID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DetachInternetGatewayInput{ InternetGatewayId: aws.String(gatewayID), @@ -1776,7 +1740,7 @@ func DetachInternetGateway(e2eCtx *E2EContext, gatewayID string, vpcID string) b } func CreatePeering(e2eCtx *E2EContext, peerName string, vpcID string, peerVpcID string) (*ec2types.VpcPeeringConnection, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.CreateVpcPeeringConnectionInput{ VpcId: aws.String(vpcID), @@ -1802,7 +1766,7 @@ func CreatePeering(e2eCtx *E2EContext, peerName string, vpcID string, peerVpcID } func GetPeering(e2eCtx *E2EContext, peeringID string) (*ec2types.VpcPeeringConnection, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("vpc-peering-connection-id"), @@ -1826,7 +1790,7 @@ func GetPeering(e2eCtx *E2EContext, peeringID string) (*ec2types.VpcPeeringConne } func DeletePeering(e2eCtx *E2EContext, peeringID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DeleteVpcPeeringConnectionInput{ VpcPeeringConnectionId: aws.String(peeringID), @@ -1839,7 +1803,7 @@ func DeletePeering(e2eCtx *E2EContext, peeringID string) bool { } func AcceptPeering(e2eCtx *E2EContext, peeringID string) (*ec2types.VpcPeeringConnection, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.AcceptVpcPeeringConnectionInput{ VpcPeeringConnectionId: aws.String(peeringID), @@ -1853,7 +1817,7 @@ func AcceptPeering(e2eCtx *E2EContext, peeringID string) (*ec2types.VpcPeeringCo } func CreateRouteTable(e2eCtx *E2EContext, rtName string, vpcID string) (*ec2types.RouteTable, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.CreateRouteTableInput{ VpcId: aws.String(vpcID), @@ -1878,7 +1842,7 @@ func CreateRouteTable(e2eCtx *E2EContext, rtName string, vpcID string) (*ec2type } func ListVpcRouteTables(e2eCtx *E2EContext, vpcID string) ([]ec2types.RouteTable, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("vpc-id"), @@ -1899,7 +1863,7 @@ func ListVpcRouteTables(e2eCtx *E2EContext, vpcID string) ([]ec2types.RouteTable } func ListSubnetRouteTables(e2eCtx *E2EContext, subnetID string) ([]ec2types.RouteTable, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("association.subnet-id"), @@ -1920,7 +1884,7 @@ func ListSubnetRouteTables(e2eCtx *E2EContext, subnetID string) ([]ec2types.Rout } func GetRouteTable(e2eCtx *E2EContext, rtID string) (*ec2types.RouteTable, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("route-table-id"), @@ -1944,7 +1908,7 @@ func GetRouteTable(e2eCtx *E2EContext, rtID string) (*ec2types.RouteTable, error } func DeleteRouteTable(e2eCtx *E2EContext, rtID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DeleteRouteTableInput{ RouteTableId: aws.String(rtID), @@ -1957,7 +1921,7 @@ func DeleteRouteTable(e2eCtx *E2EContext, rtID string) bool { } func CreateRoute(e2eCtx *E2EContext, rtID string, destinationCidr string, natID *string, igwID *string, pcxID *string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.CreateRouteInput{ RouteTableId: &rtID, @@ -1981,7 +1945,7 @@ func CreateRoute(e2eCtx *E2EContext, rtID string, destinationCidr string, natID } func DeleteRoute(e2eCtx *E2EContext, rtID string, destinationCidr string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DeleteRouteInput{ RouteTableId: aws.String(rtID), @@ -1995,7 +1959,7 @@ func DeleteRoute(e2eCtx *E2EContext, rtID string, destinationCidr string) bool { } func AssociateRouteTable(e2eCtx *E2EContext, rtID string, subnetID string) (*ec2.AssociateRouteTableOutput, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.AssociateRouteTableInput{ RouteTableId: aws.String(rtID), @@ -2010,7 +1974,7 @@ func AssociateRouteTable(e2eCtx *E2EContext, rtID string, subnetID string) (*ec2 } func DisassociateRouteTable(e2eCtx *E2EContext, assocID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DisassociateRouteTableInput{ AssociationId: aws.String(assocID), @@ -2023,7 +1987,7 @@ func DisassociateRouteTable(e2eCtx *E2EContext, assocID string) bool { } func CreateSecurityGroup(e2eCtx *E2EContext, sgName string, sgDescription string, vpcID string) (*ec2.CreateSecurityGroupOutput, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.CreateSecurityGroupInput{ VpcId: aws.String(vpcID), @@ -2050,7 +2014,7 @@ func CreateSecurityGroup(e2eCtx *E2EContext, sgName string, sgDescription string } func GetSecurityGroupByFilters(e2eCtx *E2EContext, filters []ec2types.Filter) ([]ec2types.SecurityGroup, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DescribeSecurityGroupsInput{ Filters: filters, } @@ -2062,7 +2026,7 @@ func GetSecurityGroupByFilters(e2eCtx *E2EContext, filters []ec2types.Filter) ([ } func GetSecurityGroup(e2eCtx *E2EContext, sgID string) (*ec2types.SecurityGroup, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("group-id"), @@ -2086,7 +2050,7 @@ func GetSecurityGroup(e2eCtx *E2EContext, sgID string) (*ec2types.SecurityGroup, } func GetSecurityGroupsByVPC(e2eCtx *E2EContext, vpcID string) ([]ec2types.SecurityGroup, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("vpc-id"), @@ -2112,7 +2076,7 @@ func GetSecurityGroupsByVPC(e2eCtx *E2EContext, vpcID string) ([]ec2types.Securi } func DeleteSecurityGroup(e2eCtx *E2EContext, sgID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DeleteSecurityGroupInput{ GroupId: aws.String(sgID), @@ -2125,7 +2089,7 @@ func DeleteSecurityGroup(e2eCtx *E2EContext, sgID string) bool { } func ListSecurityGroupRules(e2eCtx *E2EContext, sgID string) ([]ec2types.SecurityGroupRule, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("group-id"), @@ -2146,7 +2110,7 @@ func ListSecurityGroupRules(e2eCtx *E2EContext, sgID string) ([]ec2types.Securit } func GetSecurityGroupRule(e2eCtx *E2EContext, sgrID string) (*ec2types.SecurityGroupRule, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) filter := ec2types.Filter{ Name: aws.String("security-group-rule-id"), @@ -2170,7 +2134,7 @@ func GetSecurityGroupRule(e2eCtx *E2EContext, sgrID string) (*ec2types.SecurityG } func CreateSecurityGroupIngressRule(e2eCtx *E2EContext, sgID string, sgrDescription string, cidr string, protocol string, fromPort int32, toPort int32) (bool, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) ipPerm := ec2types.IpPermission{ FromPort: aws.Int32(fromPort), @@ -2199,7 +2163,7 @@ func CreateSecurityGroupIngressRule(e2eCtx *E2EContext, sgID string, sgrDescript } func CreateSecurityGroupEgressRule(e2eCtx *E2EContext, sgID string, sgrDescription string, cidr string, protocol string, fromPort int32, toPort int32) (bool, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) ipPerm := ec2types.IpPermission{ FromPort: aws.Int32(fromPort), @@ -2237,7 +2201,7 @@ func CreateSecurityGroupRule(e2eCtx *E2EContext, sgID string, sgrDescription str } func CreateSecurityGroupIngressRuleWithSourceSG(e2eCtx *E2EContext, sgID string, protocol string, toPort int32, sourceSecurityGroupID string) (bool, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) ipPerm := ec2types.IpPermission{ FromPort: aws.Int32(toPort), @@ -2264,7 +2228,7 @@ func CreateSecurityGroupIngressRuleWithSourceSG(e2eCtx *E2EContext, sgID string, } func DeleteSecurityGroupIngressRule(e2eCtx *E2EContext, sgID, sgrID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.RevokeSecurityGroupIngressInput{ SecurityGroupRuleIds: []string{sgrID}, @@ -2278,7 +2242,7 @@ func DeleteSecurityGroupIngressRule(e2eCtx *E2EContext, sgID, sgrID string) bool } func DeleteSecurityGroupEgressRule(e2eCtx *E2EContext, sgID, sgrID string) bool { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.RevokeSecurityGroupEgressInput{ SecurityGroupRuleIds: []string{sgrID}, @@ -2302,7 +2266,7 @@ func DeleteSecurityGroupRule(e2eCtx *E2EContext, sgID, sgrID, rt string) bool { } func ListLoadBalancers(ctx context.Context, e2eCtx *E2EContext, clusterName string) ([]elbtypes.LoadBalancerDescription, error) { - elbSvc := elb.NewFromConfig(*e2eCtx.BootstrapUserAWSSessionV2) + elbSvc := elb.NewFromConfig(*e2eCtx.BootstrapUserAWSSession) input := &elb.DescribeLoadBalancersInput{ LoadBalancerNames: []string{clusterName + "-apiserver"}, @@ -2319,7 +2283,7 @@ func ListLoadBalancers(ctx context.Context, e2eCtx *E2EContext, clusterName stri } func DeleteLoadBalancer(ctx context.Context, e2eCtx *E2EContext, loadbalancerName string) bool { - elbSvc := elb.NewFromConfig(*e2eCtx.BootstrapUserAWSSessionV2) + elbSvc := elb.NewFromConfig(*e2eCtx.BootstrapUserAWSSession) input := &elb.DeleteLoadBalancerInput{ LoadBalancerName: aws.String(loadbalancerName), @@ -2331,61 +2295,60 @@ func DeleteLoadBalancer(ctx context.Context, e2eCtx *E2EContext, loadbalancerNam return true } -func CreateEFS(e2eCtx *E2EContext, creationToken string) (*efs.FileSystemDescription, error) { - efsSvc := efs.New(e2eCtx.BootstrapUserAWSSession) +func CreateEFS(e2eCtx *E2EContext, creationToken string) (*efs.CreateFileSystemOutput, error) { + efsSvc := efs.NewFromConfig(*e2eCtx.BootstrapUserAWSSession) input := &efs.CreateFileSystemInput{ CreationToken: aws.String(creationToken), Encrypted: aws.Bool(true), } - efsOutput, err := efsSvc.CreateFileSystem(input) + efsOutput, err := efsSvc.CreateFileSystem(context.TODO(), input) if err != nil { return nil, err } return efsOutput, nil } -func DescribeEFS(e2eCtx *E2EContext, efsID string) (*efs.FileSystemDescription, error) { - efsSvc := efs.New(e2eCtx.BootstrapUserAWSSession) +func DescribeEFS(ctx context.Context, e2eCtx *E2EContext, efsID string) (*efstypes.FileSystemDescription, error) { + efsSvc := efs.NewFromConfig(*e2eCtx.BootstrapUserAWSSession) input := &efs.DescribeFileSystemsInput{ FileSystemId: aws.String(efsID), } - efsOutput, err := efsSvc.DescribeFileSystems(input) + efsOutput, err := efsSvc.DescribeFileSystems(ctx, input) if err != nil { return nil, err } if efsOutput == nil || len(efsOutput.FileSystems) == 0 { - return nil, &efs.FileSystemNotFound{ - ErrorCode: aws.String(efs.ErrCodeFileSystemNotFound), - } + return nil, &efstypes.FileSystemNotFound{} } - return efsOutput.FileSystems[0], nil + return &efsOutput.FileSystems[0], nil } -func DeleteEFS(e2eCtx *E2EContext, efsID string) (*efs.DeleteFileSystemOutput, error) { - efsSvc := efs.New(e2eCtx.BootstrapUserAWSSession) +func DeleteEFS(ctx context.Context, e2eCtx *E2EContext, efsID string) (*efs.DeleteFileSystemOutput, error) { + efsSvc := efs.NewFromConfig(*e2eCtx.BootstrapUserAWSSession) input := &efs.DeleteFileSystemInput{ FileSystemId: aws.String(efsID), } - result, err := efsSvc.DeleteFileSystem(input) + result, err := efsSvc.DeleteFileSystem(ctx, input) if err != nil { return nil, err } return result, nil } -func GetEFSState(e2eCtx *E2EContext, efsID string) (*string, error) { - efs, err := DescribeEFS(e2eCtx, efsID) +func GetEFSState(ctx context.Context, e2eCtx *E2EContext, efsID string) (*string, error) { + efs, err := DescribeEFS(ctx, e2eCtx, efsID) if err != nil { return nil, err } - return efs.LifeCycleState, nil + state := string(efs.LifeCycleState) + return &state, nil } -func CreateMountTargetOnEFS(e2eCtx *E2EContext, efsID string, vpcID string, sg string) (*efs.MountTargetDescription, error) { - efsSvc := efs.New(e2eCtx.BootstrapUserAWSSession) +func CreateMountTargetOnEFS(ctx context.Context, e2eCtx *E2EContext, efsID string, vpcID string, sg string) (*efs.CreateMountTargetOutput, error) { + efsSvc := efs.NewFromConfig(*e2eCtx.BootstrapUserAWSSession) subnets, err := ListVpcSubnets(e2eCtx, vpcID) if err != nil { @@ -2393,53 +2356,53 @@ func CreateMountTargetOnEFS(e2eCtx *E2EContext, efsID string, vpcID string, sg s } input := &efs.CreateMountTargetInput{ FileSystemId: aws.String(efsID), - SecurityGroups: aws.StringSlice([]string{sg}), + SecurityGroups: []string{sg}, SubnetId: subnets[0].SubnetId, } - result, err := efsSvc.CreateMountTarget(input) + result, err := efsSvc.CreateMountTarget(ctx, input) if err != nil { return nil, err } return result, nil } -func DeleteMountTarget(e2eCtx *E2EContext, mountTargetID string) (*efs.DeleteMountTargetOutput, error) { - efsSvc := efs.New(e2eCtx.BootstrapUserAWSSession) +func DeleteMountTarget(ctx context.Context, e2eCtx *E2EContext, mountTargetID string) (*efs.DeleteMountTargetOutput, error) { + efsSvc := efs.NewFromConfig(*e2eCtx.BootstrapUserAWSSession) input := &efs.DeleteMountTargetInput{ MountTargetId: aws.String(mountTargetID), } - result, err := efsSvc.DeleteMountTarget(input) + result, err := efsSvc.DeleteMountTarget(ctx, input) if err != nil { return nil, err } return result, nil } -func GetMountTarget(e2eCtx *E2EContext, mountTargetID string) (*efs.MountTargetDescription, error) { - efsSvc := efs.New(e2eCtx.BootstrapUserAWSSession) +func GetMountTarget(ctx context.Context, e2eCtx *E2EContext, mountTargetID string) (*efstypes.MountTargetDescription, error) { + efsSvc := efs.NewFromConfig(*e2eCtx.BootstrapUserAWSSession) input := &efs.DescribeMountTargetsInput{ MountTargetId: aws.String(mountTargetID), } - result, err := efsSvc.DescribeMountTargets(input) + result, err := efsSvc.DescribeMountTargets(ctx, input) if err != nil { return nil, err } if len(result.MountTargets) == 0 { - return nil, &efs.MountTargetNotFound{ - ErrorCode: aws.String(efs.ErrCodeMountTargetNotFound), - } + return nil, &efstypes.MountTargetNotFound{} } - return result.MountTargets[0], nil + return &result.MountTargets[0], nil } -func GetMountTargetState(e2eCtx *E2EContext, mountTargetID string) (*string, error) { - result, err := GetMountTarget(e2eCtx, mountTargetID) +func GetMountTargetState(ctx context.Context, e2eCtx *E2EContext, mountTargetID string) (*string, error) { + result, err := GetMountTarget(ctx, e2eCtx, mountTargetID) if err != nil { return nil, err } - return result.LifeCycleState, nil + + state := string(result.LifeCycleState) + return &state, nil } func getAvailabilityZone(e2eCtx *E2EContext) string { @@ -2459,7 +2422,7 @@ func getInstanceFamily(e2eCtx *E2EContext) string { } func AllocateHost(ctx context.Context, e2eCtx *E2EContext) (string, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.AllocateHostsInput{ AvailabilityZone: aws.String(getAvailabilityZone(e2eCtx)), InstanceFamily: aws.String(getInstanceFamily(e2eCtx)), @@ -2474,7 +2437,7 @@ func AllocateHost(ctx context.Context, e2eCtx *E2EContext) (string, error) { } func ReleaseHost(ctx context.Context, e2eCtx *E2EContext, hostID string) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.ReleaseHostsInput{ HostIds: []string{hostID}, @@ -2486,7 +2449,7 @@ func ReleaseHost(ctx context.Context, e2eCtx *E2EContext, hostID string) { } func GetHostID(ctx context.Context, e2eCtx *E2EContext, instanceID string) string { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DescribeInstancesInput{ InstanceIds: []string{instanceID}, diff --git a/test/e2e/shared/context.go b/test/e2e/shared/context.go index 4889964e1a..5f96f093a1 100644 --- a/test/e2e/shared/context.go +++ b/test/e2e/shared/context.go @@ -25,7 +25,6 @@ import ( awsv2 "github.com/aws/aws-sdk-go-v2/aws" iamtypes "github.com/aws/aws-sdk-go-v2/service/iam/types" - "github.com/aws/aws-sdk-go/aws/client" "github.com/awslabs/goformation/v4/cloudformation" "github.com/gofrs/flock" corev1 "k8s.io/api/core/v1" @@ -64,13 +63,9 @@ type E2EContext struct { // Environment represents the runtime environment. Environment RuntimeEnvironment // AWSSession is the AWS session for the tests. - AWSSession client.ConfigProvider - // AWSSessionV2 is the AWS SDK V2 client for the tests. - AWSSessionV2 *awsv2.Config + AWSSession *awsv2.Config // BootstrapUserAWSSession is the AWS session for the bootstrap user. - BootstrapUserAWSSession client.ConfigProvider - // BootstrapUserAWSSessionV2 is the AWS SDK V2 session for the bootstrap user. This is until the V2 migration is done. - BootstrapUserAWSSessionV2 *awsv2.Config + BootstrapUserAWSSession *awsv2.Config // IsManaged indicates that this is for the managed part of the provider. IsManaged bool // CloudFormationTemplate is the rendered template created for the test. diff --git a/test/e2e/shared/defaults.go b/test/e2e/shared/defaults.go index deac101fa5..4b7adf22c6 100644 --- a/test/e2e/shared/defaults.go +++ b/test/e2e/shared/defaults.go @@ -24,9 +24,8 @@ import ( "flag" "strings" - awsv2 "github.com/aws/aws-sdk-go-v2/aws" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/iam" - "github.com/aws/aws-sdk-go/aws" "k8s.io/apimachinery/pkg/runtime" cgscheme "k8s.io/client-go/kubernetes/scheme" @@ -122,7 +121,7 @@ func (m MultitenancyRole) RoleName() string { } // SetEnvVars sets the environment variables for the role. -func (m MultitenancyRole) SetEnvVars(ctx context.Context, cfg *awsv2.Config) error { +func (m MultitenancyRole) SetEnvVars(ctx context.Context, cfg *aws.Config) error { arn, err := m.RoleARN(ctx, cfg) if err != nil { return err @@ -134,7 +133,7 @@ func (m MultitenancyRole) SetEnvVars(ctx context.Context, cfg *awsv2.Config) err } // RoleARN returns the role ARN. -func (m MultitenancyRole) RoleARN(ctx context.Context, cfg *awsv2.Config) (string, error) { +func (m MultitenancyRole) RoleARN(ctx context.Context, cfg *aws.Config) (string, error) { if roleARN, ok := roleLookupCache[m.RoleName()]; ok { return roleARN, nil } diff --git a/test/e2e/shared/exec.go b/test/e2e/shared/exec.go index e02bea706c..300abf61a8 100644 --- a/test/e2e/shared/exec.go +++ b/test/e2e/shared/exec.go @@ -29,9 +29,9 @@ import ( "regexp" "time" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/service/ssm" + "github.com/aws/aws-sdk-go-v2/service/ssm" expect "github.com/google/goexpect" ) @@ -42,7 +42,7 @@ type instance struct { // allMachines gets all EC2 instances at once, to save on DescribeInstances calls. func allMachines(ctx context.Context, e2eCtx *E2EContext) ([]instance, error) { - ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Svc := ec2.NewFromConfig(*e2eCtx.AWSSession) resp, err := ec2Svc.DescribeInstances(ctx, &ec2.DescribeInstancesInput{}) if err != nil { return nil, err @@ -56,8 +56,8 @@ func allMachines(ctx context.Context, e2eCtx *E2EContext) ([]instance, error) { tags := i.Tags name := "" for _, t := range tags { - if aws.StringValue(t.Key) == "Name" { - name = aws.StringValue(t.Value) + if aws.ToString(t.Key) == "Name" { + name = aws.ToString(t.Value) } } if name == "" { @@ -66,7 +66,7 @@ func allMachines(ctx context.Context, e2eCtx *E2EContext) ([]instance, error) { instances = append(instances, instance{ name: name, - instanceID: aws.StringValue(i.InstanceId), + instanceID: aws.ToString(i.InstanceId), }, ) } @@ -82,8 +82,8 @@ type command struct { // commandsForMachine opens a terminal connection using AWS SSM Session Manager // and executes the given commands, outputting the results to a file for each. func commandsForMachine(ctx context.Context, e2eCtx *E2EContext, f *os.File, instanceID string, commands []command) { - ssmSvc := ssm.New(e2eCtx.BootstrapUserAWSSession) - sess, err := ssmSvc.StartSessionWithContext(ctx, &ssm.StartSessionInput{ + ssmSvc := ssm.NewFromConfig(*e2eCtx.BootstrapUserAWSSession) + sess, err := ssmSvc.StartSession(ctx, &ssm.StartSessionInput{ Target: aws.String(instanceID), }) if err != nil { @@ -91,7 +91,7 @@ func commandsForMachine(ctx context.Context, e2eCtx *E2EContext, f *os.File, ins return } defer func() { - if _, err := ssmSvc.TerminateSession(&ssm.TerminateSessionInput{SessionId: sess.SessionId}); err != nil { + if _, err := ssmSvc.TerminateSession(ctx, &ssm.TerminateSessionInput{SessionId: sess.SessionId}); err != nil { fmt.Fprintf(f, "unable to terminate session: err=%s", err) } }() @@ -100,7 +100,7 @@ func commandsForMachine(ctx context.Context, e2eCtx *E2EContext, f *os.File, ins fmt.Fprintf(f, "unable to marshal session: err=%s", err) return } - cmdLine := fmt.Sprintf("session-manager-plugin %s %s StartSession %s", string(sessionToken), *ssmSvc.Client.Config.Region, ssmSvc.Client.Endpoint) + cmdLine := fmt.Sprintf("session-manager-plugin %s %s StartSession", string(sessionToken), ssmSvc.Options().Region) e, _, err := expect.Spawn(cmdLine, -1) if err != nil { fmt.Fprintf(f, "unable to spawn AWS SSM Session Manager plugin: %s", err) diff --git a/test/e2e/shared/resource.go b/test/e2e/shared/resource.go index d53a34d51c..c22bb337f8 100644 --- a/test/e2e/shared/resource.go +++ b/test/e2e/shared/resource.go @@ -27,7 +27,7 @@ import ( "path/filepath" "time" - "github.com/aws/aws-sdk-go/service/servicequotas" + servicequotastypes "github.com/aws/aws-sdk-go-v2/service/servicequotas/types" "github.com/gofrs/flock" . "github.com/onsi/ginkgo/v2" . "github.com/onsi/gomega" @@ -70,7 +70,7 @@ func WriteResourceQuotesToFile(logPath string, serviceQuotas map[string]*Service Expect(err).NotTo(HaveOccurred()) } -func WriteAWSResourceQuotesToFile(logPath string, serviceQuotas map[string]*servicequotas.ServiceQuota) { +func WriteAWSResourceQuotesToFile(logPath string, serviceQuotas map[string]*servicequotastypes.ServiceQuota) { if _, err := os.Stat(logPath); err == nil { // If resource-quotas file exists, remove it. Should not fail on error, another ginkgo node might have already deleted it. os.Remove(logPath) diff --git a/test/e2e/shared/suite.go b/test/e2e/shared/suite.go index f53f7039e5..a5baf7ef48 100644 --- a/test/e2e/shared/suite.go +++ b/test/e2e/shared/suite.go @@ -129,9 +129,8 @@ func Node1BeforeSuite(e2eCtx *E2EContext) []byte { Expect(err).NotTo(HaveOccurred()) e2eCtx.AWSSession = NewAWSSession() - e2eCtx.AWSSessionV2 = NewAWSSessionV2() - logAccountDetails(e2eCtx.AWSSessionV2) + logAccountDetails(e2eCtx.AWSSession) bootstrapTemplate := getBootstrapTemplate(e2eCtx) bootstrapTags := map[string]string{"capa-e2e-test": "true"} @@ -143,7 +142,7 @@ func Node1BeforeSuite(e2eCtx *E2EContext) []byte { count++ By(fmt.Sprintf("Trying to create CloudFormation stack... attempt %d", count)) success := true - if err := createCloudFormationStack(context.TODO(), e2eCtx.AWSSessionV2, e2eCtx.AWSSession, bootstrapTemplate, bootstrapTags); err != nil { + if err := createCloudFormationStack(context.TODO(), e2eCtx.AWSSession, bootstrapTemplate, bootstrapTags); err != nil { By(fmt.Sprintf("Failed to create CloudFormation stack in attempt %d: %s", count, err.Error())) deleteCloudFormationStack(e2eCtx.AWSSession, bootstrapTemplate) success = false @@ -153,16 +152,15 @@ func Node1BeforeSuite(e2eCtx *E2EContext) []byte { } ensureStackTags(e2eCtx.AWSSession, bootstrapTemplate.Spec.StackName, bootstrapTags) - ensureNoServiceLinkedRoles(context.TODO(), e2eCtx.AWSSessionV2) - ensureSSHKeyPair(*e2eCtx.AWSSessionV2, DefaultSSHKeyPairName) - e2eCtx.Environment.BootstrapAccessKey = newUserAccessKey(context.TODO(), e2eCtx.AWSSessionV2, bootstrapTemplate.Spec.BootstrapUser.UserName) + ensureNoServiceLinkedRoles(context.TODO(), e2eCtx.AWSSession) + ensureSSHKeyPair(*e2eCtx.AWSSession, DefaultSSHKeyPairName) + e2eCtx.Environment.BootstrapAccessKey = newUserAccessKey(context.TODO(), e2eCtx.AWSSession, bootstrapTemplate.Spec.BootstrapUser.UserName) e2eCtx.BootstrapUserAWSSession = NewAWSSessionWithKey(e2eCtx.Environment.BootstrapAccessKey) - e2eCtx.BootstrapUserAWSSessionV2 = NewAWSSessionWithKeyV2(e2eCtx.Environment.BootstrapAccessKey) By("Waiting for access key to propagate...") time.Sleep(10 * time.Second) - Expect(ensureTestImageUploaded(e2eCtx)).NotTo(HaveOccurred()) + Expect(ensureTestImageUploaded(context.TODO(), e2eCtx)).NotTo(HaveOccurred()) // Image ID is needed when using a CI Kubernetes version. This is used in conformance test and upgrade to main test. if !e2eCtx.IsManaged { @@ -230,15 +228,13 @@ func AllNodesBeforeSuite(e2eCtx *E2EContext, data []byte) { e2eCtx.Environment.BootstrapClusterProxy = framework.NewClusterProxy("bootstrap", conf.KubeconfigPath, e2eCtx.Environment.Scheme) e2eCtx.E2EConfig = &conf.E2EConfig e2eCtx.BootstrapUserAWSSession = NewAWSSessionWithKey(conf.BootstrapAccessKey) - e2eCtx.BootstrapUserAWSSessionV2 = NewAWSSessionWithKeyV2(conf.BootstrapAccessKey) e2eCtx.Settings.FileLock = flock.New(ResourceQuotaFilePath) e2eCtx.Settings.KubetestConfigFilePath = conf.KubetestConfigFilePath e2eCtx.Settings.UseCIArtifacts = conf.UseCIArtifacts e2eCtx.Settings.GinkgoNodes = conf.GinkgoNodes e2eCtx.Settings.GinkgoSlowSpecThreshold = conf.GinkgoSlowSpecThreshold e2eCtx.AWSSession = NewAWSSession() - e2eCtx.AWSSessionV2 = NewAWSSessionV2() - azs := GetAvailabilityZones(*e2eCtx.AWSSessionV2) + azs := GetAvailabilityZones(*e2eCtx.AWSSession) SetEnvVar(AwsAvailabilityZone1, *azs[0].ZoneName, false) SetEnvVar(AwsAvailabilityZone2, *azs[1].ZoneName, false) SetEnvVar("AWS_REGION", conf.Region, false) diff --git a/test/e2e/suites/managed/eks_clusterclass_test.go b/test/e2e/suites/managed/eks_clusterclass_test.go index 3c492aaee9..31d8d58f0d 100644 --- a/test/e2e/suites/managed/eks_clusterclass_test.go +++ b/test/e2e/suites/managed/eks_clusterclass_test.go @@ -57,7 +57,7 @@ var _ = ginkgo.Describe("[managed] [general] EKS clusterclass tests", func() { clusterName = fmt.Sprintf("%s-%s", specName, util.RandomString(6)) ginkgo.By("default iam role should exist") - VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, "", false, e2eCtx.AWSSessionV2) + VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, "", false, e2eCtx.AWSSession) }) capi_e2e.QuickStartSpec(context.TODO(), func() capi_e2e.QuickStartSpecInput { diff --git a/test/e2e/suites/managed/eks_ipv6_test.go b/test/e2e/suites/managed/eks_ipv6_test.go index a9f691d142..d8e7d46c50 100644 --- a/test/e2e/suites/managed/eks_ipv6_test.go +++ b/test/e2e/suites/managed/eks_ipv6_test.go @@ -58,7 +58,7 @@ var _ = ginkgo.Describe("[managed] [general] [ipv6] EKS cluster tests", func() { clusterName = fmt.Sprintf("%s-%s", specName, util.RandomString(6)) ginkgo.By("default iam role should exist") - VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, clusterName, false, e2eCtx.AWSSessionV2) + VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, clusterName, false, e2eCtx.AWSSession) ginkgo.By("should create an EKS control plane") ManagedClusterSpec(ctx, func() ManagedClusterSpecInput { @@ -66,7 +66,7 @@ var _ = ginkgo.Describe("[managed] [general] [ipv6] EKS cluster tests", func() { E2EConfig: e2eCtx.E2EConfig, ConfigClusterFn: defaultConfigCluster, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, Flavour: EKSIPv6ClusterFlavor, @@ -81,7 +81,7 @@ var _ = ginkgo.Describe("[managed] [general] [ipv6] EKS cluster tests", func() { E2EConfig: e2eCtx.E2EConfig, ConfigClusterFn: defaultConfigCluster, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, IncludeScaling: false, diff --git a/test/e2e/suites/managed/eks_legacy_test.go b/test/e2e/suites/managed/eks_legacy_test.go index 900760f3b2..24fdd6bcd6 100644 --- a/test/e2e/suites/managed/eks_legacy_test.go +++ b/test/e2e/suites/managed/eks_legacy_test.go @@ -58,7 +58,7 @@ var _ = ginkgo.Describe("[managed] [legacy] EKS cluster tests - single kind", fu eksClusterName := getEKSClusterName(namespace.Name, clusterName) ginkgo.By("default iam role should exist") - VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, eksClusterName, false, e2eCtx.AWSSessionV2) + VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, eksClusterName, false, e2eCtx.AWSSession) ginkgo.By("should create an EKS control plane") ManagedClusterSpec(ctx, func() ManagedClusterSpecInput { @@ -66,7 +66,7 @@ var _ = ginkgo.Describe("[managed] [legacy] EKS cluster tests - single kind", fu E2EConfig: e2eCtx.E2EConfig, ConfigClusterFn: defaultConfigCluster, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, Flavour: EKSControlPlaneOnlyLegacyFlavor, @@ -81,7 +81,7 @@ var _ = ginkgo.Describe("[managed] [legacy] EKS cluster tests - single kind", fu E2EConfig: e2eCtx.E2EConfig, ConfigClusterFn: defaultConfigCluster, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, IncludeScaling: false, diff --git a/test/e2e/suites/managed/eks_test.go b/test/e2e/suites/managed/eks_test.go index cddc0a83ed..c84e3c96e1 100644 --- a/test/e2e/suites/managed/eks_test.go +++ b/test/e2e/suites/managed/eks_test.go @@ -56,7 +56,7 @@ var _ = ginkgo.Describe("[managed] [general] EKS cluster tests", func() { eksClusterName := getEKSClusterName(namespace.Name, clusterName) ginkgo.By("default iam role should exist") - VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, eksClusterName, false, e2eCtx.AWSSessionV2) + VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, eksClusterName, false, e2eCtx.AWSSession) ginkgo.By("should create an EKS control plane") ManagedClusterSpec(ctx, func() ManagedClusterSpecInput { @@ -64,7 +64,7 @@ var _ = ginkgo.Describe("[managed] [general] EKS cluster tests", func() { E2EConfig: e2eCtx.E2EConfig, ConfigClusterFn: defaultConfigCluster, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, Flavour: EKSControlPlaneOnlyWithAddonFlavor, @@ -78,7 +78,7 @@ var _ = ginkgo.Describe("[managed] [general] EKS cluster tests", func() { return UpdateAwsNodeVersionSpecInput{ E2EConfig: e2eCtx.E2EConfig, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, } @@ -89,7 +89,7 @@ var _ = ginkgo.Describe("[managed] [general] EKS cluster tests", func() { return CheckAddonExistsSpecInput{ E2EConfig: e2eCtx.E2EConfig, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, AddonName: cniAddonName, @@ -103,7 +103,7 @@ var _ = ginkgo.Describe("[managed] [general] EKS cluster tests", func() { E2EConfig: e2eCtx.E2EConfig, ConfigClusterFn: defaultConfigCluster, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, Replicas: 1, @@ -117,7 +117,7 @@ var _ = ginkgo.Describe("[managed] [general] EKS cluster tests", func() { E2EConfig: e2eCtx.E2EConfig, ConfigClusterFn: defaultConfigCluster, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, IncludeScaling: true, @@ -133,7 +133,7 @@ var _ = ginkgo.Describe("[managed] [general] EKS cluster tests", func() { E2EConfig: e2eCtx.E2EConfig, ConfigClusterFn: defaultConfigCluster, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, IncludeScaling: true, @@ -150,7 +150,7 @@ var _ = ginkgo.Describe("[managed] [general] EKS cluster tests", func() { E2EConfig: e2eCtx.E2EConfig, ConfigClusterFn: defaultConfigCluster, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, IncludeScaling: true, diff --git a/test/e2e/suites/managed/gc_test.go b/test/e2e/suites/managed/gc_test.go index d8a0f7d00d..f531caa3c0 100644 --- a/test/e2e/suites/managed/gc_test.go +++ b/test/e2e/suites/managed/gc_test.go @@ -55,7 +55,7 @@ var _ = ginkgo.Describe("[managed] [gc] EKS Cluster external resource GC tests", clusterName = fmt.Sprintf("%s-%s", specName, util.RandomString(6)) ginkgo.By("default iam role should exist") - VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, clusterName, false, e2eCtx.AWSSessionV2) + VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, clusterName, false, e2eCtx.AWSSession) ginkgo.By("should create an EKS control plane") ManagedClusterSpec(ctx, func() ManagedClusterSpecInput { @@ -63,7 +63,7 @@ var _ = ginkgo.Describe("[managed] [gc] EKS Cluster external resource GC tests", E2EConfig: e2eCtx.E2EConfig, ConfigClusterFn: defaultConfigCluster, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, Flavour: EKSManagedPoolFlavor, @@ -111,14 +111,14 @@ var _ = ginkgo.Describe("[managed] [gc] EKS Cluster external resource GC tests", ginkgo.By("Checking we have the load balancers in AWS") shared.WaitForLoadBalancerToExistForService(ctx, shared.WaitForLoadBalancerToExistForServiceInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-nlb", ServiceNamespace: "default", ClusterName: cp.Spec.EKSClusterName, Type: infrav1.LoadBalancerTypeNLB, }, e2eCtx.E2EConfig.GetIntervals("", "wait-loadbalancer-ready")...) shared.WaitForLoadBalancerToExistForService(ctx, shared.WaitForLoadBalancerToExistForServiceInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-elb", ServiceNamespace: "default", ClusterName: cp.Spec.EKSClusterName, @@ -139,7 +139,7 @@ var _ = ginkgo.Describe("[managed] [gc] EKS Cluster external resource GC tests", ginkgo.By("Getting counts of service load balancers") arns, err := shared.GetLoadBalancerARNs(ctx, shared.GetLoadBalancerARNsInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-nlb", ServiceNamespace: "default", ClusterName: cp.Spec.EKSClusterName, @@ -148,7 +148,7 @@ var _ = ginkgo.Describe("[managed] [gc] EKS Cluster external resource GC tests", Expect(err).NotTo(HaveOccurred()) Expect(arns).To(BeEmpty(), "there are %d service load balancers (nlb) still", len(arns)) arns, err = shared.GetLoadBalancerARNs(ctx, shared.GetLoadBalancerARNsInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-elb", ServiceNamespace: "default", ClusterName: cp.Spec.EKSClusterName, @@ -178,7 +178,7 @@ var _ = ginkgo.Describe("[managed] [gc] EKS Cluster external resource GC tests", clusterName = fmt.Sprintf("%s-%s", specName, util.RandomString(6)) ginkgo.By("default iam role should exist") - VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, clusterName, false, e2eCtx.AWSSessionV2) + VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, clusterName, false, e2eCtx.AWSSession) ginkgo.By("should create an EKS control plane") ManagedClusterSpec(ctx, func() ManagedClusterSpecInput { @@ -186,7 +186,7 @@ var _ = ginkgo.Describe("[managed] [gc] EKS Cluster external resource GC tests", E2EConfig: e2eCtx.E2EConfig, ConfigClusterFn: defaultConfigCluster, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, Flavour: EKSManagedPoolFlavor, @@ -234,14 +234,14 @@ var _ = ginkgo.Describe("[managed] [gc] EKS Cluster external resource GC tests", ginkgo.By("Checking we have the load balancers in AWS") shared.WaitForLoadBalancerToExistForService(ctx, shared.WaitForLoadBalancerToExistForServiceInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-nlb", ServiceNamespace: "default", ClusterName: cp.Spec.EKSClusterName, Type: infrav1.LoadBalancerTypeNLB, }, e2eCtx.E2EConfig.GetIntervals("", "wait-loadbalancer-ready")...) shared.WaitForLoadBalancerToExistForService(ctx, shared.WaitForLoadBalancerToExistForServiceInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-elb", ServiceNamespace: "default", ClusterName: cp.Spec.EKSClusterName, @@ -262,7 +262,7 @@ var _ = ginkgo.Describe("[managed] [gc] EKS Cluster external resource GC tests", ginkgo.By("Getting counts of service load balancers") arns, err := shared.GetLoadBalancerARNs(ctx, shared.GetLoadBalancerARNsInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-nlb", ServiceNamespace: "default", ClusterName: cp.Spec.EKSClusterName, @@ -271,7 +271,7 @@ var _ = ginkgo.Describe("[managed] [gc] EKS Cluster external resource GC tests", Expect(err).NotTo(HaveOccurred()) Expect(arns).To(BeEmpty(), "there are %d service load balancers (nlb) still", len(arns)) arns, err = shared.GetLoadBalancerARNs(ctx, shared.GetLoadBalancerARNsInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-elb", ServiceNamespace: "default", ClusterName: cp.Spec.EKSClusterName, diff --git a/test/e2e/suites/managed/upgrade_test.go b/test/e2e/suites/managed/upgrade_test.go index dd7e1f3b32..1fce74bed7 100644 --- a/test/e2e/suites/managed/upgrade_test.go +++ b/test/e2e/suites/managed/upgrade_test.go @@ -59,7 +59,7 @@ var _ = ginkgo.Describe("EKS Cluster upgrade test", func() { upgradeToVersion = e2eCtx.E2EConfig.MustGetVariable(shared.EksUpgradeToVersion) ginkgo.By("default iam role should exist") - VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, clusterName, false, e2eCtx.AWSSessionV2) + VerifyRoleExistsAndOwned(ctx, ekscontrolplanev1.DefaultEKSControlPlaneRole, clusterName, false, e2eCtx.AWSSession) ginkgo.By("should create an EKS control plane") ManagedClusterSpec(ctx, func() ManagedClusterSpecInput { @@ -67,7 +67,7 @@ var _ = ginkgo.Describe("EKS Cluster upgrade test", func() { E2EConfig: e2eCtx.E2EConfig, ConfigClusterFn: defaultConfigCluster, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, Namespace: namespace, ClusterName: clusterName, Flavour: EKSControlPlaneOnlyFlavor, // TODO (richardcase) - change in the future when upgrades to machinepools work @@ -99,7 +99,7 @@ var _ = ginkgo.Describe("EKS Cluster upgrade test", func() { UpgradeControlPlaneVersionSpec(ctx, func() UpgradeControlPlaneVersionSpecInput { return UpgradeControlPlaneVersionSpecInput{ E2EConfig: e2eCtx.E2EConfig, - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, BootstrapClusterProxy: e2eCtx.Environment.BootstrapClusterProxy, ClusterName: clusterName, Namespace: namespace, diff --git a/test/e2e/suites/unmanaged/gc_test.go b/test/e2e/suites/unmanaged/gc_test.go index 01d6807e9b..4e0f9664e8 100644 --- a/test/e2e/suites/unmanaged/gc_test.go +++ b/test/e2e/suites/unmanaged/gc_test.go @@ -91,14 +91,14 @@ var _ = ginkgo.Context("[unmanaged] [gc]", func() { ginkgo.By("Checking we have the load balancers in AWS") shared.WaitForLoadBalancerToExistForService(ctx, shared.WaitForLoadBalancerToExistForServiceInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-nlb", ServiceNamespace: "default", ClusterName: clusterName, Type: infrav1.LoadBalancerTypeNLB, }, e2eCtx.E2EConfig.GetIntervals("", "wait-loadbalancer-ready")...) shared.WaitForLoadBalancerToExistForService(ctx, shared.WaitForLoadBalancerToExistForServiceInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-elb", ServiceNamespace: "default", ClusterName: clusterName, @@ -119,7 +119,7 @@ var _ = ginkgo.Context("[unmanaged] [gc]", func() { ginkgo.By("Getting counts of service load balancers") arns, err := shared.GetLoadBalancerARNs(ctx, shared.GetLoadBalancerARNsInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-nlb", ServiceNamespace: "default", ClusterName: clusterName, @@ -128,7 +128,7 @@ var _ = ginkgo.Context("[unmanaged] [gc]", func() { Expect(err).NotTo(HaveOccurred()) Expect(arns).To(BeEmpty(), "there are %d service load balancers (nlb) still", len(arns)) arns, err = shared.GetLoadBalancerARNs(ctx, shared.GetLoadBalancerARNsInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-elb", ServiceNamespace: "default", ClusterName: clusterName, @@ -197,14 +197,14 @@ var _ = ginkgo.Context("[unmanaged] [gc]", func() { ginkgo.By("Checking we have the load balancers in AWS") shared.WaitForLoadBalancerToExistForService(ctx, shared.WaitForLoadBalancerToExistForServiceInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-nlb", ServiceNamespace: "default", ClusterName: clusterName, Type: infrav1.LoadBalancerTypeNLB, }, e2eCtx.E2EConfig.GetIntervals("", "wait-loadbalancer-ready")...) shared.WaitForLoadBalancerToExistForService(ctx, shared.WaitForLoadBalancerToExistForServiceInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-elb", ServiceNamespace: "default", ClusterName: clusterName, @@ -225,7 +225,7 @@ var _ = ginkgo.Context("[unmanaged] [gc]", func() { ginkgo.By("Getting counts of service load balancers") arns, err := shared.GetLoadBalancerARNs(ctx, shared.GetLoadBalancerARNsInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-nlb", ServiceNamespace: "default", ClusterName: clusterName, @@ -234,7 +234,7 @@ var _ = ginkgo.Context("[unmanaged] [gc]", func() { Expect(err).NotTo(HaveOccurred()) Expect(arns).To(BeEmpty(), "there are %d service load balancers (nlb) still", len(arns)) arns, err = shared.GetLoadBalancerARNs(ctx, shared.GetLoadBalancerARNsInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, ServiceName: "podinfo-elb", ServiceNamespace: "default", ClusterName: clusterName, diff --git a/test/e2e/suites/unmanaged/helpers_test.go b/test/e2e/suites/unmanaged/helpers_test.go index e5a8224295..d8c626f079 100644 --- a/test/e2e/suites/unmanaged/helpers_test.go +++ b/test/e2e/suites/unmanaged/helpers_test.go @@ -30,11 +30,11 @@ import ( "strings" "time" + "github.com/aws/aws-sdk-go-v2/aws" "github.com/aws/aws-sdk-go-v2/service/ec2" "github.com/aws/aws-sdk-go-v2/service/ec2/types" - "github.com/aws/aws-sdk-go/aws" - "github.com/aws/aws-sdk-go/aws/awserr" - "github.com/aws/aws-sdk-go/service/efs" + "github.com/aws/aws-sdk-go-v2/service/efs" + efstypes "github.com/aws/aws-sdk-go-v2/service/efs/types" "github.com/blang/semver" "github.com/onsi/ginkgo/v2" . "github.com/onsi/gomega" @@ -48,6 +48,7 @@ import ( crclient "sigs.k8s.io/controller-runtime/pkg/client" infrav1 "sigs.k8s.io/cluster-api-provider-aws/v2/api/v1beta2" + "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/cloud/awserrors" "sigs.k8s.io/cluster-api-provider-aws/v2/pkg/utils" "sigs.k8s.io/cluster-api-provider-aws/v2/test/e2e/shared" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" @@ -151,7 +152,7 @@ func getSubnetID(filterKey, filterValue, clusterName string) *string { var subnetOutput *ec2.DescribeSubnetsOutput var err error - ec2Client := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Client := ec2.NewFromConfig(*e2eCtx.AWSSession) subnetInput := &ec2.DescribeSubnetsInput{ Filters: []types.Filter{ { @@ -320,7 +321,7 @@ func makeMachineDeployment(namespace, mdName, clusterName string, az *string, re func assertSpotInstanceType(instanceID string) { ginkgo.By(fmt.Sprintf("Finding EC2 spot instance with ID: %s", instanceID)) - ec2Client := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Client := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DescribeInstancesInput{ InstanceIds: []string{ instanceID[strings.LastIndex(instanceID, "/")+1:], @@ -336,7 +337,7 @@ func assertSpotInstanceType(instanceID string) { func assertInstanceMetadataOptions(instanceID string, expected infrav1.InstanceMetadataOptions) { ginkgo.By(fmt.Sprintf("Finding EC2 instance with ID: %s", instanceID)) - ec2Client := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Client := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DescribeInstancesInput{ InstanceIds: []string{ instanceID[strings.LastIndex(instanceID, "/")+1:], @@ -359,7 +360,7 @@ func assertInstanceMetadataOptions(instanceID string, expected infrav1.InstanceM func assertUnencryptedUserDataIgnition(instanceID string, expected string) { ginkgo.By(fmt.Sprintf("Finding EC2 instance with ID: %s", instanceID)) - ec2Client := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Client := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.DescribeInstanceAttributeInput{ Attribute: types.InstanceAttributeNameUserData, InstanceId: aws.String(instanceID[strings.LastIndex(instanceID, "/")+1:]), @@ -375,7 +376,7 @@ func assertUnencryptedUserDataIgnition(instanceID string, expected string) { func terminateInstance(instanceID string) { ginkgo.By(fmt.Sprintf("Terminating EC2 instance with ID: %s", instanceID)) - ec2Client := ec2.NewFromConfig(*e2eCtx.AWSSessionV2) + ec2Client := ec2.NewFromConfig(*e2eCtx.AWSSession) input := &ec2.TerminateInstancesInput{ InstanceIds: []string{ instanceID[strings.LastIndex(instanceID, "/")+1:], @@ -445,12 +446,12 @@ func hasAWSClusterConditions(m *infrav1.AWSCluster, expected []conditionAssertio return true } -func createEFS() *efs.FileSystemDescription { +func createEFS(ctx context.Context) *efs.CreateFileSystemOutput { efs, err := shared.CreateEFS(e2eCtx, string(uuid.NewUUID())) Expect(err).NotTo(HaveOccurred()) Eventually(func() (string, error) { - state, err := shared.GetEFSState(e2eCtx, aws.StringValue(efs.FileSystemId)) - return aws.StringValue(state), err + state, err := shared.GetEFSState(ctx, e2eCtx, aws.ToString(efs.FileSystemId)) + return aws.ToString(state), err }, 2*time.Minute, 5*time.Second).Should(Equal("available")) return efs } @@ -467,35 +468,35 @@ func createSecurityGroupForEFS(clusterName string, vpc *types.Vpc) *ec2.CreateSe }) Expect(err).NotTo(HaveOccurred()) Expect(len(nodeSecurityGroups)).To(Equal(1)) - _, err = shared.CreateSecurityGroupIngressRuleWithSourceSG(e2eCtx, aws.StringValue(securityGroup.GroupId), "tcp", 2049, aws.StringValue(nodeSecurityGroups[0].GroupId)) + _, err = shared.CreateSecurityGroupIngressRuleWithSourceSG(e2eCtx, aws.ToString(securityGroup.GroupId), "tcp", 2049, aws.ToString(nodeSecurityGroups[0].GroupId)) Expect(err).NotTo(HaveOccurred()) return securityGroup } -func createMountTarget(efs *efs.FileSystemDescription, securityGroup *ec2.CreateSecurityGroupOutput, vpc *types.Vpc) *efs.MountTargetDescription { - mt, err := shared.CreateMountTargetOnEFS(e2eCtx, aws.StringValue(efs.FileSystemId), aws.StringValue(vpc.VpcId), aws.StringValue(securityGroup.GroupId)) +func createMountTarget(ctx context.Context, efs *efs.CreateFileSystemOutput, securityGroup *ec2.CreateSecurityGroupOutput, vpc *types.Vpc) *efs.CreateMountTargetOutput { + mt, err := shared.CreateMountTargetOnEFS(ctx, e2eCtx, aws.ToString(efs.FileSystemId), aws.ToString(vpc.VpcId), aws.ToString(securityGroup.GroupId)) Expect(err).NotTo(HaveOccurred()) Eventually(func() (string, error) { - state, err := shared.GetMountTargetState(e2eCtx, *mt.MountTargetId) - return aws.StringValue(state), err + state, err := shared.GetMountTargetState(ctx, e2eCtx, *mt.MountTargetId) + return aws.ToString(state), err }, 5*time.Minute, 10*time.Second).Should(Equal("available")) return mt } -func deleteMountTarget(mountTarget *efs.MountTargetDescription) { - _, err := shared.DeleteMountTarget(e2eCtx, *mountTarget.MountTargetId) +func deleteMountTarget(ctx context.Context, mountTarget *efs.CreateMountTargetOutput) { + _, err := shared.DeleteMountTarget(ctx, e2eCtx, *mountTarget.MountTargetId) Expect(err).NotTo(HaveOccurred()) Eventually(func(g Gomega) { - _, err = shared.GetMountTarget(e2eCtx, *mountTarget.MountTargetId) + _, err = shared.GetMountTarget(ctx, e2eCtx, *mountTarget.MountTargetId) g.Expect(err).ShouldNot(BeNil()) - aerr, ok := err.(awserr.Error) + code, ok := awserrors.Code(err) g.Expect(ok).To(BeTrue()) - g.Expect(aerr.Code()).To(Equal(efs.ErrCodeMountTargetNotFound)) + g.Expect(code).To(Equal((&efstypes.MountTargetNotFound{}).ErrorCode())) }, 5*time.Minute, 10*time.Second).Should(Succeed()) } // example taken from aws-efs-csi-driver (https://github.com/kubernetes-sigs/aws-efs-csi-driver/blob/master/examples/kubernetes/dynamic_provisioning/specs/storageclass.yaml) -func createEFSStorageClass(storageClassName string, clusterClient crclient.Client, efs *efs.FileSystemDescription) { +func createEFSStorageClass(storageClassName string, clusterClient crclient.Client, efs *efs.CreateFileSystemOutput) { storageClass := &storagev1.StorageClass{ TypeMeta: metav1.TypeMeta{ APIVersion: "storage.k8s.io/v1", @@ -507,7 +508,7 @@ func createEFSStorageClass(storageClassName string, clusterClient crclient.Clien MountOptions: []string{"tls"}, Parameters: map[string]string{ "provisioningMode": "efs-ap", - "fileSystemId": aws.StringValue(efs.FileSystemId), + "fileSystemId": aws.ToString(efs.FileSystemId), "directoryPerms": "700", "gidRangeStart": "1000", "gidRangeEnd": "2000", diff --git a/test/e2e/suites/unmanaged/unmanaged_classic_elb_upgrade_test.go b/test/e2e/suites/unmanaged/unmanaged_classic_elb_upgrade_test.go index 4fba43f453..1ef8cf8950 100644 --- a/test/e2e/suites/unmanaged/unmanaged_classic_elb_upgrade_test.go +++ b/test/e2e/suites/unmanaged/unmanaged_classic_elb_upgrade_test.go @@ -191,7 +191,7 @@ var _ = ginkgo.Context("[unmanaged] [upgrade]", func() { Expect(err).NotTo(HaveOccurred(), "failed to get the AWS cluster") shared.CheckClassicElbHealthCheck(ctx, shared.CheckClassicElbHealthCheckInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, LoadBalancerName: awsCluster.Status.Network.APIServerELB.Name, ExpectedTarget: "SSL:6443", }, e2eCtx.E2EConfig.GetIntervals(specName, "wait-classic-elb-health-check-short")...) @@ -210,7 +210,7 @@ var _ = ginkgo.Context("[unmanaged] [upgrade]", func() { ginkgo.By("Management cluster is upgraded to main version") shared.CheckClassicElbHealthCheck(ctx, shared.CheckClassicElbHealthCheckInput{ - AWSSession: e2eCtx.BootstrapUserAWSSessionV2, + AWSSession: e2eCtx.BootstrapUserAWSSession, LoadBalancerName: awsCluster.Status.Network.APIServerELB.Name, ExpectedTarget: "TCP:6443", }, e2eCtx.E2EConfig.GetIntervals(specName, "wait-classic-elb-health-check-long")...) diff --git a/test/e2e/suites/unmanaged/unmanaged_functional_clusterclass_test.go b/test/e2e/suites/unmanaged/unmanaged_functional_clusterclass_test.go index 36dc53021f..5fa396d3db 100644 --- a/test/e2e/suites/unmanaged/unmanaged_functional_clusterclass_test.go +++ b/test/e2e/suites/unmanaged/unmanaged_functional_clusterclass_test.go @@ -60,7 +60,7 @@ var _ = ginkgo.Context("[unmanaged] [functional] [ClusterClass]", func() { defer shared.ReleaseResources(requiredResources, ginkgo.GinkgoParallelProcess(), flock.New(shared.ResourceQuotaFilePath)) namespace := shared.SetupSpecNamespace(ctx, specName, e2eCtx) defer shared.DumpSpecResourcesAndCleanup(ctx, "", namespace, e2eCtx) - Expect(shared.SetMultitenancyEnvVars(ctx, e2eCtx.AWSSessionV2)).To(Succeed()) + Expect(shared.SetMultitenancyEnvVars(ctx, e2eCtx.AWSSession)).To(Succeed()) ginkgo.By("Creating cluster") clusterName := fmt.Sprintf("cluster-%s", util.RandomString(6)) diff --git a/test/e2e/suites/unmanaged/unmanaged_functional_test.go b/test/e2e/suites/unmanaged/unmanaged_functional_test.go index 9ac1d76b55..f4d6d42e94 100644 --- a/test/e2e/suites/unmanaged/unmanaged_functional_test.go +++ b/test/e2e/suites/unmanaged/unmanaged_functional_test.go @@ -88,14 +88,14 @@ var _ = ginkgo.Context("[unmanaged] [functional]", func() { clusterClient := e2eCtx.Environment.BootstrapClusterProxy.GetWorkloadCluster(ctx, namespace.Name, clusterName).GetClient() ginkgo.By("Setting up EFS in AWS") - efs := createEFS() - defer shared.DeleteEFS(e2eCtx, *efs.FileSystemId) + efs := createEFS(ctx) + defer shared.DeleteEFS(ctx, e2eCtx, *efs.FileSystemId) vpc, err := shared.GetVPCByName(e2eCtx, clusterName+"-vpc") Expect(err).NotTo(HaveOccurred()) securityGroup := createSecurityGroupForEFS(clusterName, vpc) defer shared.DeleteSecurityGroup(e2eCtx, *securityGroup.GroupId) - mountTarget := createMountTarget(efs, securityGroup, vpc) - defer deleteMountTarget(mountTarget) + mountTarget := createMountTarget(ctx, efs, securityGroup, vpc) + defer deleteMountTarget(ctx, mountTarget) // running efs dynamic provisioning example (https://github.com/kubernetes-sigs/aws-efs-gpu-op-driver/tree/master/examples/kubernetes/dynamic_provisioning) ginkgo.By("Deploying efs dynamic provisioning resources") @@ -182,7 +182,7 @@ var _ = ginkgo.Context("[unmanaged] [functional]", func() { } namespace := shared.SetupSpecNamespace(ctx, specName, e2eCtx) defer shared.DumpSpecResourcesAndCleanup(ctx, "", namespace, e2eCtx) - Expect(shared.SetMultitenancyEnvVars(ctx, e2eCtx.AWSSessionV2)).To(Succeed()) + Expect(shared.SetMultitenancyEnvVars(ctx, e2eCtx.AWSSession)).To(Succeed()) ginkgo.By("Creating cluster") clusterName := fmt.Sprintf("%s-%s", specName, util.RandomString(6)) clusterctl.ApplyClusterTemplateAndWait(ctx, clusterctl.ApplyClusterTemplateAndWaitInput{ @@ -391,7 +391,7 @@ var _ = ginkgo.Context("[unmanaged] [functional]", func() { ginkgo.By("Creating Machine Deployment in non-configured Availability Zone") md2Name := clusterName + "-md-2" // By default, first availability zone will be used for cluster resources. This step attempts to create a machine deployment in the second availability zone - invalidAz := shared.GetAvailabilityZones(*e2eCtx.AWSSessionV2)[1].ZoneName + invalidAz := shared.GetAvailabilityZones(*e2eCtx.AWSSession)[1].ZoneName framework.CreateMachineDeployment(ctx, framework.CreateMachineDeploymentInput{ Creator: e2eCtx.Environment.BootstrapClusterProxy.GetClient(), MachineDeployment: makeMachineDeployment(namespace.Name, md2Name, clusterName, invalidAz, 1), diff --git a/util/system/util.go b/util/system/util.go index 0b6eb9507c..2ddaa2d1a5 100644 --- a/util/system/util.go +++ b/util/system/util.go @@ -22,7 +22,6 @@ import ( "os" "path/filepath" - "github.com/aws/aws-sdk-go/aws/endpoints" "github.com/pkg/errors" ) @@ -70,19 +69,3 @@ func GetNamespaceFromFile(nsFilePath string) (string, error) { } return string(namespace), nil } - -// GetPartitionFromRegion returns the cluster partition. -func GetPartitionFromRegion(region string) string { - switch region { - case endpoints.UsGovEast1RegionID, endpoints.UsGovWest1RegionID: - return endpoints.AwsUsGovPartitionID - case endpoints.CnNorth1RegionID, endpoints.CnNorthwest1RegionID: - return endpoints.AwsCnPartitionID - case endpoints.UsIsoEast1RegionID, endpoints.UsIsoWest1RegionID: - return endpoints.AwsIsoPartitionID - case endpoints.UsIsobEast1RegionID: - return endpoints.AwsIsoBPartitionID - default: - return endpoints.AwsPartitionID - } -} diff --git a/version/version.go b/version/version.go index b895ae2daf..0d50180f87 100644 --- a/version/version.go +++ b/version/version.go @@ -21,7 +21,7 @@ import ( "fmt" "runtime" - "github.com/aws/aws-sdk-go/aws" + "github.com/aws/aws-sdk-go-v2/aws" ) var (