diff --git a/internal/cloud/awscloud/secure-instance.go b/internal/cloud/awscloud/secure-instance.go index c1ca69105..36cdcf307 100644 --- a/internal/cloud/awscloud/secure-instance.go +++ b/internal/cloud/awscloud/secure-instance.go @@ -73,6 +73,37 @@ func (a *AWS) RunSecureInstance(iamProfile string) (*SecureInstance, error) { return nil, err } + descrSubnetsOutput, err := a.ec2.DescribeSubnets(&ec2.DescribeSubnetsInput{ + Filters: []*ec2.Filter{ + &ec2.Filter{ + Name: aws.String("vpc-id"), + Values: []*string{ + aws.String(vpcID), + }, + }, + }, + }) + if err != nil { + return nil, err + } + if len(descrSubnetsOutput.Subnets) == 0 { + return nil, fmt.Errorf("Expected at least 1 subnet in the VPC, got 0") + } + + // For creating a fleet in a non-default VPC, AWS needs the subnets, and at most 1 subnet per AZ. + // If a VPC has multiple subnets for a single AZ, only pick the first one. + overrides := []*ec2.FleetLaunchTemplateOverridesRequest{} + availZones := map[string]struct{}{} + for _, subnet := range descrSubnetsOutput.Subnets { + az := *subnet.AvailabilityZone + if _, ok := availZones[az]; !ok { + overrides = append(overrides, &ec2.FleetLaunchTemplateOverridesRequest{ + SubnetId: subnet.SubnetId, + }) + availZones[az] = struct{}{} + } + } + createFleetOutput, err := a.ec2.CreateFleet(&ec2.CreateFleetInput{ LaunchTemplateConfigs: []*ec2.FleetLaunchTemplateConfigRequest{ &ec2.FleetLaunchTemplateConfigRequest{ @@ -80,6 +111,7 @@ func (a *AWS) RunSecureInstance(iamProfile string) (*SecureInstance, error) { LaunchTemplateId: aws.String(secureInstance.LTID), Version: aws.String("1"), }, + Overrides: overrides, }, }, TagSpecifications: []*ec2.TagSpecification{