Skip to content

Commit

Permalink
Add config support for EKS and exclude ghost cluster in our account (#…
Browse files Browse the repository at this point in the history
…295)

* Add config support for EKS and exclude ghost cluster in our account

* Exclude ap-southeast-1 from EKS testing
  • Loading branch information
yorinasub17 authored Apr 25, 2022
1 parent 1c5eb51 commit 33c7045
Show file tree
Hide file tree
Showing 7 changed files with 66 additions and 37 deletions.
6 changes: 6 additions & 0 deletions .circleci/nuke_config.yml
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,12 @@ OIDCProvider:
# We have an active OIDC Provider used by github actions
- ".*token.actions.githubusercontent.com.*"

EKSCluster:
exclude:
names_regex:
# This EKS cluster is a ghost cluster in our account in the ap-southeast-1 region that can not be deleted.
- "^cloud-nuke-TestListEksClusters-o8DrEi$"

CloudWatchLogGroup:
# Use an allow list instead of block list because we haven't done the due diligence yet to figure out what log groups
# we need to keep. This is hard to do in the current scenario as we have thousands of log groups in the accounts.
Expand Down
52 changes: 28 additions & 24 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -216,6 +216,9 @@ The following resources support the Config file:
- EC2 Instances
- Resource type: `ec2`
- Config key: `EC2`
- EKS Clusters
- Resource type: `ekscluster`
- Config key: `EKSCluster`

#### Example

Expand Down Expand Up @@ -302,30 +305,31 @@ To find out what we options are supported in the config file today, consult this

| resource type | names | names_regex | tags | tags_regex |
|--------------------|-------|-------------|------|------------|
| s3 | none | ✅ | none | none |
| iam | none | ✅ | none | none |
| ecsserv | none | ✅ | none | none |
| ecscluster | none | ✅ | none | none |
| secretsmanager | none | ✅ | none | none |
| nat-gateway | none | ✅ | none | none |
| accessanalyzer | none | ✅ | none | none |
| dynamodb | none | ✅ | none | none |
| ebs | none | ✅ | none | none |
| lambda | none | ✅ | none | none |
| elbv2 | none | ✅ | none | none |
| ecs | none | ✅ | none | none |
| elasticache | none | ✅ | none | none |
| vpc | none | ✅ | none | none |
| oidcprovider | none | ✅ | none | none |
| cloudwatch-loggroup | none | ✅ | none | none |
| kmscustomerkeys | none | ✅ | none | none |
| asg | none | ✅ | none | none |
| lc | none | ✅ | none | none |
| eip | none | ✅ | none | none |
| ec2 | none | ✅ | none | none |
| acmpca | none | none | none | none |
| iam role | none | none | none | none |
| ... (more to come) | none | none | none | none |
| s3 | none | ✅ | none | none |
| iam | none | ✅ | none | none |
| ecsserv | none | ✅ | none | none |
| ecscluster | none | ✅ | none | none |
| secretsmanager | none | ✅ | none | none |
| nat-gateway | none | ✅ | none | none |
| accessanalyzer | none | ✅ | none | none |
| dynamodb | none | ✅ | none | none |
| ebs | none | ✅ | none | none |
| lambda | none | ✅ | none | none |
| elbv2 | none | ✅ | none | none |
| ecs | none | ✅ | none | none |
| elasticache | none | ✅ | none | none |
| vpc | none | ✅ | none | none |
| oidcprovider | none | ✅ | none | none |
| cloudwatch-loggroup | none | ✅ | none | none |
| kmscustomerkeys | none | ✅ | none | none |
| asg | none | ✅ | none | none |
| lc | none | ✅ | none | none |
| eip | none | ✅ | none | none |
| ec2 | none | ✅ | none | none |
| eks | none | ✅ | none | none |
| acmpca | none | none | none | none |
| iam role | none | none | none | none |
| ... (more to come) | none | none | none | none |



Expand Down
2 changes: 1 addition & 1 deletion aws/aws.go
Original file line number Diff line number Diff line change
Expand Up @@ -502,7 +502,7 @@ func GetAllResources(targetRegions []string, excludeAfter time.Time, resourceTyp
// EKS resources
eksClusters := EKSClusters{}
if IsNukeable(eksClusters.ResourceName(), resourceTypes) {
eksClusterNames, err := getAllEksClusters(session, excludeAfter)
eksClusterNames, err := getAllEksClusters(session, excludeAfter, configObj)
if err != nil {
return nil, errors.WithStackTrace(err)
}
Expand Down
21 changes: 16 additions & 5 deletions aws/eks.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,30 +7,41 @@ import (
"github.com/aws/aws-sdk-go/aws"
"github.com/aws/aws-sdk-go/aws/session"
"github.com/aws/aws-sdk-go/service/eks"
"github.com/gruntwork-io/cloud-nuke/config"
"github.com/gruntwork-io/cloud-nuke/logging"
"github.com/gruntwork-io/go-commons/errors"
"github.com/hashicorp/go-multierror"
)

// getAllEksClusters returns a list of strings of EKS Cluster Names that uniquely identify each cluster.
func getAllEksClusters(awsSession *session.Session, excludeAfter time.Time) ([]*string, error) {
func getAllEksClusters(awsSession *session.Session, excludeAfter time.Time, configObj config.Config) ([]*string, error) {
svc := eks.New(awsSession)
result, err := svc.ListClusters(&eks.ListClustersInput{})
if err != nil {
return nil, errors.WithStackTrace(err)
}
filteredClusters, err := filterOutRecentEksClusters(svc, result.Clusters, excludeAfter)
filteredClusters, err := filterOutEksClusters(svc, result.Clusters, excludeAfter, configObj)
if err != nil {
return nil, errors.WithStackTrace(err)
}
return filteredClusters, nil
}

// filterOutRecentEksClusters will take in the list of clusters and filter out any clusters that were created after
// `excludeAfter`.
func filterOutRecentEksClusters(svc *eks.EKS, clusterNames []*string, excludeAfter time.Time) ([]*string, error) {
// filterOutEksClusters will take in the list of clusters and filter out any clusters that were created after
// `excludeAfter`, and those that are excluded by the config file.
func filterOutEksClusters(svc *eks.EKS, clusterNames []*string, excludeAfter time.Time, configObj config.Config) ([]*string, error) {
var filteredEksClusterNames []*string
for _, clusterName := range clusterNames {
// Since we already have the name here, avoid an extra API call by applying the name based config filter first.
shouldInclude := config.ShouldInclude(
aws.StringValue(clusterName),
configObj.EKSCluster.IncludeRule.NamesRegExp,
configObj.EKSCluster.ExcludeRule.NamesRegExp,
)
if !shouldInclude {
continue
}

describeResult, err := svc.DescribeCluster(&eks.DescribeClusterInput{
Name: clusterName,
})
Expand Down
20 changes: 13 additions & 7 deletions aws/eks_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,18 +7,24 @@ import (

awsgo "github.com/aws/aws-sdk-go/aws"
"github.com/aws/aws-sdk-go/aws/session"
"github.com/gruntwork-io/cloud-nuke/config"
"github.com/gruntwork-io/cloud-nuke/util"
"github.com/gruntwork-io/terratest/modules/logger"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
)

var (
// Exclude ap-southeast-1, which currently has a ghost EKS cluster that messes cloud-nuke up.
excludeRegionsForEKSTest = []string{"ap-southeast-1"}
)

// Test that we can successfully list clusters by manually creating a cluster, and then using the list function to find
// it.
func TestListEksClusters(t *testing.T) {
t.Parallel()

region, err := getRandomRegion()
region, err := getRandomRegionWithExclusions(excludeRegionsForEKSTest)
require.NoError(t, err)

awsSession, err := session.NewSession(&awsgo.Config{
Expand All @@ -34,13 +40,13 @@ func TestListEksClusters(t *testing.T) {
cluster := createEKSCluster(t, awsSession, uniqueID, *role.Arn)
defer nukeAllEksClusters(awsSession, []*string{cluster.Name})

eksClusterNames, err := getAllEksClusters(awsSession, time.Now().Add(1*time.Hour*-1))
eksClusterNames, err := getAllEksClusters(awsSession, time.Now().Add(1*time.Hour*-1), config.Config{})
if err != nil {
assert.Failf(t, "Unable to fetch list of clusters: %s", err.Error())
}
assert.NotContains(t, awsgo.StringValueSlice(eksClusterNames), *cluster.Name)

eksClusterNames, err = getAllEksClusters(awsSession, time.Now().Add(1*time.Hour))
eksClusterNames, err = getAllEksClusters(awsSession, time.Now().Add(1*time.Hour), config.Config{})
if err != nil {
assert.Failf(t, "Unable to fetch list of clusters: %s", err.Error())
}
Expand All @@ -52,7 +58,7 @@ func TestListEksClusters(t *testing.T) {
func TestNukeEksClusters(t *testing.T) {
t.Parallel()

region, err := getRandomRegion()
region, err := getRandomRegionWithExclusions(excludeRegionsForEKSTest)
require.NoError(t, err)

awsSession, err := session.NewSession(&awsgo.Config{
Expand All @@ -69,7 +75,7 @@ func TestNukeEksClusters(t *testing.T) {
err = nukeAllEksClusters(awsSession, []*string{cluster.Name})
require.NoError(t, err)

eksClusterNames, err := getAllEksClusters(awsSession, time.Now().Add(1*time.Hour))
eksClusterNames, err := getAllEksClusters(awsSession, time.Now().Add(1*time.Hour), config.Config{})
require.NoError(t, err)
assert.NotContains(t, awsgo.StringValueSlice(eksClusterNames), *cluster.Name)
}
Expand All @@ -78,7 +84,7 @@ func TestNukeEksClusters(t *testing.T) {
func TestNukeEksClustersWithCompute(t *testing.T) {
t.Parallel()

region, err := getRandomRegion()
region, err := getRandomRegionWithExclusions(excludeRegionsForEKSTest)
require.NoError(t, err)

awsSession, err := session.NewSession(&awsgo.Config{
Expand Down Expand Up @@ -121,7 +127,7 @@ func TestNukeEksClustersWithCompute(t *testing.T) {
err = nukeAllEksClusters(awsSession, []*string{cluster.Name})
require.NoError(t, err)

eksClusterNames, err := getAllEksClusters(awsSession, time.Now().Add(1*time.Hour))
eksClusterNames, err := getAllEksClusters(awsSession, time.Now().Add(1*time.Hour), config.Config{})
require.NoError(t, err)
assert.NotContains(t, awsgo.StringValueSlice(eksClusterNames), *cluster.Name)
}
1 change: 1 addition & 0 deletions config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ type Config struct {
EC2 ResourceType `yaml:"EC2"`
CloudWatchLogGroup ResourceType `yaml:"CloudWatchLogGroup"`
KMSCustomerKeys ResourceType `yaml:"KMSCustomerKeys"`
EKSCluster ResourceType `yaml:"EKSCluster"`
}

type ResourceType struct {
Expand Down
1 change: 1 addition & 0 deletions config/config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ func emptyConfig() *Config {
ResourceType{FilterRule{}, FilterRule{}},
ResourceType{FilterRule{}, FilterRule{}},
ResourceType{FilterRule{}, FilterRule{}},
ResourceType{FilterRule{}, FilterRule{}},
}
}

Expand Down

0 comments on commit 33c7045

Please sign in to comment.