Skip to content

Commit 7cf59ac

Browse files
authored
Update AWS region validations (#899)
1 parent 0a2cc64 commit 7cf59ac

File tree

8 files changed

+115
-16
lines changed

8 files changed

+115
-16
lines changed

cli/cmd/deploy.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -166,5 +166,5 @@ func deploy(configPath string, force bool) {
166166
exit.Error(err, "/deploy", string(response))
167167
}
168168

169-
print.ForUser(deployResponse.Message)
169+
print.ForUserSplitDoubleNewLine(deployResponse.Message)
170170
}

cli/cmd/lib_aws_creds.go

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ import (
2424
cr "github.com/cortexlabs/cortex/pkg/lib/configreader"
2525
"github.com/cortexlabs/cortex/pkg/lib/errors"
2626
"github.com/cortexlabs/cortex/pkg/lib/prompt"
27+
"github.com/cortexlabs/cortex/pkg/types/clusterconfig"
2728
)
2829

2930
type AWSCredentials struct {
@@ -34,6 +35,10 @@ type AWSCredentials struct {
3435
}
3536

3637
func newAWSClient(region string, awsCreds AWSCredentials) (*aws.Client, error) {
38+
if err := clusterconfig.ValidateRegion(region); err != nil {
39+
return nil, err
40+
}
41+
3742
awsClient, err := aws.NewFromCreds(region, awsCreds.AWSAccessKeyID, awsCreds.AWSSecretAccessKey)
3843
if err != nil {
3944
return nil, err

pkg/lib/aws/ec2.go

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,68 @@ func (c *Client) SpotInstancePrice(region string, instanceType string) (float64,
6666
return min, nil
6767
}
6868

69+
func (c *Client) ListAllRegions() (strset.Set, error) {
70+
result, err := c.EC2().DescribeRegions(&ec2.DescribeRegionsInput{
71+
AllRegions: aws.Bool(true),
72+
})
73+
if err != nil {
74+
return nil, errors.WithStack(err)
75+
}
76+
77+
regions := strset.New()
78+
for _, region := range result.Regions {
79+
if region.RegionName != nil {
80+
regions.Add(*region.RegionName)
81+
}
82+
}
83+
84+
return regions, nil
85+
}
86+
87+
// Returns only regions that are enabled for your account
88+
func (c *Client) ListEnabledRegions() (strset.Set, error) {
89+
result, err := c.EC2().DescribeRegions(&ec2.DescribeRegionsInput{
90+
AllRegions: aws.Bool(false),
91+
})
92+
if err != nil {
93+
return nil, errors.WithStack(err)
94+
}
95+
96+
regions := strset.New()
97+
for _, region := range result.Regions {
98+
if region.RegionName != nil {
99+
regions.Add(*region.RegionName)
100+
}
101+
}
102+
103+
return regions, nil
104+
}
105+
106+
// Returns all regions and enabled regions
107+
func (c *Client) ListRegions() (strset.Set, strset.Set, error) {
108+
var allRegions strset.Set
109+
var enabledRegions strset.Set
110+
111+
err := parallel.RunFirstErr(
112+
func() error {
113+
var err error
114+
allRegions, err = c.ListAllRegions()
115+
return err
116+
},
117+
func() error {
118+
var err error
119+
enabledRegions, err = c.ListEnabledRegions()
120+
return err
121+
},
122+
)
123+
124+
if err != nil {
125+
return nil, nil, err
126+
}
127+
128+
return allRegions, enabledRegions, nil
129+
}
130+
69131
func (c *Client) ListAvailabilityZones() (strset.Set, error) {
70132
input := &ec2.DescribeAvailabilityZonesInput{
71133
Filters: []*ec2.Filter{

pkg/lib/aws/eks.go

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -17,19 +17,14 @@ limitations under the License.
1717
package aws
1818

1919
import (
20-
"sort"
21-
2220
"github.com/cortexlabs/cortex/pkg/lib/sets/strset"
2321
)
2422

2523
var EKSSupportedRegions strset.Set
26-
var EKSSupportedRegionsSlice []string
2724

2825
func init() {
2926
EKSSupportedRegions = strset.New()
3027
for region := range InstanceMetadatas {
3128
EKSSupportedRegions.Add(region)
3229
}
33-
EKSSupportedRegionsSlice = EKSSupportedRegions.Slice()
34-
sort.Strings(EKSSupportedRegionsSlice)
3530
}

pkg/lib/aws/sts.go

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -46,12 +46,12 @@ func (c *Client) AreCredentialsValid() (string, string, bool, error) {
4646
// Ignores cache, so will re-run on every call to this method
4747
func (c *Client) CheckCredentials() (string, string, error) {
4848
_, _, isValid, err := c.AreCredentialsValid()
49-
if !isValid {
50-
return "", "", ErrorInvalidAWSCredentials()
51-
}
5249
if err != nil {
5350
return "", "", err
5451
}
52+
if !isValid {
53+
return "", "", ErrorInvalidAWSCredentials()
54+
}
5555
return *c.accountID, *c.hashedAccountID, nil
5656
}
5757

pkg/lib/print/print.go

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,21 @@ import (
2424
)
2525

2626
func ForUser(msg string) {
27+
msgParts := strings.Split(msg, "\n")
28+
29+
if len(msgParts[0]) > 200 {
30+
fmt.Println(msg)
31+
return
32+
}
33+
34+
fmt.Println(console.Bold(msgParts[0]))
35+
36+
if len(msgParts) > 1 {
37+
fmt.Println(strings.Join(msgParts[1:], "\n"))
38+
}
39+
}
40+
41+
func ForUserSplitDoubleNewLine(msg string) {
2742
msgParts := strings.Split(msg, "\n\n")
2843

2944
if len(msgParts[0]) > 200 {

pkg/types/clusterconfig/clusterconfig.go

Lines changed: 20 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -203,7 +203,7 @@ var UserValidation = &cr.StructValidation{
203203
{
204204
StructField: "Region",
205205
StringPtrValidation: &cr.StringPtrValidation{
206-
AllowedValues: aws.EKSSupportedRegionsSlice,
206+
Validator: validateRegion,
207207
},
208208
},
209209
{
@@ -389,6 +389,20 @@ var UserValidation = &cr.StructValidation{
389389
},
390390
}
391391

392+
func ValidateRegion(region string) error {
393+
if !aws.EKSSupportedRegions.Has(region) {
394+
return ErrorInvalidRegion(region)
395+
}
396+
return nil
397+
}
398+
399+
func validateRegion(region string) (string, error) {
400+
if err := ValidateRegion(region); err != nil {
401+
return "", err
402+
}
403+
return region, nil
404+
}
405+
392406
func validateImageVersion(image string) (string, error) {
393407
if !strings.HasPrefix(image, "cortexlabs/") && !strings.HasPrefix(image, "cortexlabsdev/") {
394408
return image, nil
@@ -437,7 +451,7 @@ var AccessValidation = &cr.StructValidation{
437451
{
438452
StructField: "Region",
439453
StringPtrValidation: &cr.StringPtrValidation{
440-
AllowedValues: aws.EKSSupportedRegionsSlice,
454+
Validator: validateRegion,
441455
},
442456
},
443457
{
@@ -728,8 +742,8 @@ func RegionPrompt(clusterConfig *Config) error {
728742
Prompt: RegionUserKey,
729743
},
730744
StringPtrValidation: &cr.StringPtrValidation{
731-
AllowedValues: aws.EKSSupportedRegionsSlice,
732-
Default: defaults.Region,
745+
Validator: validateRegion,
746+
Default: defaults.Region,
733747
},
734748
},
735749
},
@@ -870,8 +884,8 @@ var AccessPromptValidation = &cr.PromptValidation{
870884
Prompt: RegionUserKey,
871885
},
872886
StringPtrValidation: &cr.StringPtrValidation{
873-
AllowedValues: aws.EKSSupportedRegionsSlice,
874-
Default: pointer.String("us-west-2"),
887+
Validator: validateRegion,
888+
Default: pointer.String("us-west-2"),
875889
},
876890
},
877891
},

pkg/types/clusterconfig/errors.go

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@ import (
2828
)
2929

3030
const (
31+
ErrInvalidRegion = "clusterconfig.invalid_region"
3132
ErrInstanceTypeTooSmall = "clusterconfig.instance_type_too_small"
3233
ErrMinInstancesGreaterThanMax = "clusterconfig.min_instances_greater_than_max"
3334
ErrInstanceTypeNotSupportedInRegion = "clusterconfig.instance_type_not_supported_in_region"
@@ -51,10 +52,17 @@ const (
5152
ErrInvalidInstanceType = "clusterconfig.invalid_instance_type"
5253
)
5354

55+
func ErrorInvalidRegion(region string) error {
56+
return errors.WithStack(&errors.Error{
57+
Kind: ErrInvalidRegion,
58+
Message: fmt.Sprintf("%s is not a valid AWS region, or is an AWS region which is not supported by AWS EKS; please choose one of the following regions: %s", s.UserStr(region), strings.Join(aws.EKSSupportedRegions.SliceSorted(), ", ")),
59+
})
60+
}
61+
5462
func ErrorInstanceTypeTooSmall() error {
5563
return errors.WithStack(&errors.Error{
5664
Kind: ErrInstanceTypeTooSmall,
57-
Message: "Cortex does not support nano or micro instances - please specify a larger instance type",
65+
Message: "cortex does not support nano or micro instances - please specify a larger instance type",
5866
})
5967
}
6068

0 commit comments

Comments
 (0)