@@ -9,12 +9,14 @@ package main
99import (
1010 "context"
1111 "log"
12+ "os"
1213 "strings"
1314 "time"
1415
1516 "github.com/aws/aws-sdk-go-v2/aws"
1617 "github.com/aws/aws-sdk-go-v2/config"
1718 "github.com/aws/aws-sdk-go-v2/service/ecs"
19+ "github.com/aws/aws-sdk-go-v2/service/ecs/types"
1820
1921 "github.com/aws/amazon-cloudwatch-agent/tool/clean"
2022)
@@ -23,17 +25,20 @@ import (
2325
2426var expirationTimeOneWeek = time .Now ().UTC ().Add (- clean .KeepDurationOneWeek )
2527
26- const cwaIntegTestClusterPrefix = "cwagent-integ-test-cluster-"
28+ const clusterPrefix = "cwagent-integ-test-cluster-"
29+
30+ var taskdefPrefixes = []string {"cwagent-integ-test-" , "extra-apps-family-" , "cwagent-task-family-" }
2731
2832func main () {
2933 ctx := context .Background ()
30- defaultConfig , err := config .LoadDefaultConfig (ctx )
34+ defaultConfig , err := config .LoadDefaultConfig (ctx , config . WithRegion ( os . Args [ 1 ]) )
3135 if err != nil {
3236 log .Fatalf ("Error loading AWS config for ECS cleanup: %v" , err )
3337 }
3438
3539 ecsClient := ecs .NewFromConfig (defaultConfig )
3640 terminateClusters (ctx , ecsClient )
41+ deleteInactiveTaskDefinitions (ctx , ecsClient )
3742}
3843
3944func terminateClusters (ctx context.Context , client * ecs.Client ) {
@@ -65,7 +70,7 @@ func terminateClusters(ctx context.Context, client *ecs.Client) {
6570 */
6671
6772 for _ , cluster := range describeClustersOutput .Clusters {
68- if ! strings .HasPrefix (* cluster .ClusterName , cwaIntegTestClusterPrefix ) {
73+ if ! strings .HasPrefix (* cluster .ClusterName , clusterPrefix ) {
6974 continue
7075 }
7176 if cluster .RunningTasksCount == 0 && cluster .PendingTasksCount == 0 {
@@ -86,6 +91,10 @@ func terminateClusters(ctx context.Context, client *ecs.Client) {
8691 ecsListClusterInput .NextToken = listClusterOutput .NextToken
8792 }
8893
94+ if len (clusterIds ) == 0 {
95+ log .Print ("No clusters to delete." )
96+ }
97+
8998 // Deletion Logic
9099 for _ , clusterId := range clusterIds {
91100 log .Printf ("Cluster to terminate: %s" , * clusterId )
@@ -168,3 +177,68 @@ func isClusterTasksExpired(ctx context.Context, client *ecs.Client, clusterArn *
168177 }
169178 return true
170179}
180+
181+ func deleteInactiveTaskDefinitions (ctx context.Context , client * ecs.Client ) {
182+ log .Print ("Begin cleanup of inactive task definitions" )
183+
184+ taskDefsToDelete := getECSTaskDefsToDelete (ctx , client )
185+
186+ if len (taskDefsToDelete ) == 0 {
187+ log .Printf ("No inactive task definitions to delete" )
188+ return
189+ }
190+
191+ log .Printf ("Found %d inactive task definitions to delete" , len (taskDefsToDelete ))
192+
193+ // Batch delete task definitions (API supports up to 10 at a time)
194+ const batchSize = 10
195+ totalDeleted := 0
196+
197+ for i := 0 ; i < len (taskDefsToDelete ); i += batchSize {
198+ end := min (i + batchSize , len (taskDefsToDelete ))
199+ output , err := client .DeleteTaskDefinitions (ctx , & ecs.DeleteTaskDefinitionsInput {
200+ TaskDefinitions : taskDefsToDelete [i :end ],
201+ })
202+ if err != nil {
203+ log .Printf ("Error batch deleting task definitions: %v" , err )
204+ continue
205+ }
206+
207+ totalDeleted += len (output .TaskDefinitions )
208+ for _ , failure := range output .Failures {
209+ log .Printf ("Failed to delete task definition %s: %s" , * failure .Arn , * failure .Reason )
210+ }
211+ }
212+
213+ log .Printf ("Successfully deleted %d task definitions" , totalDeleted )
214+ }
215+
216+ func getECSTaskDefsToDelete (ctx context.Context , client * ecs.Client ) []string {
217+ taskDefsToDelete := make ([]string , 0 )
218+
219+ for _ , prefix := range taskdefPrefixes {
220+ // List inactive task definitions with integration test prefix
221+ listTaskDefsInput := ecs.ListTaskDefinitionsInput {
222+ FamilyPrefix : aws .String (prefix ),
223+ Status : types .TaskDefinitionStatusInactive ,
224+ }
225+
226+ for {
227+ listTaskDefsOutput , err := client .ListTaskDefinitions (ctx , & listTaskDefsInput )
228+ if err != nil {
229+ log .Printf ("Error listing task definitions: %v" , err )
230+ break
231+ }
232+ if len (listTaskDefsOutput .TaskDefinitionArns ) == 0 {
233+ break
234+ }
235+
236+ taskDefsToDelete = append (taskDefsToDelete , listTaskDefsOutput .TaskDefinitionArns ... )
237+ if listTaskDefsOutput .NextToken == nil {
238+ break
239+ }
240+ listTaskDefsInput .NextToken = listTaskDefsOutput .NextToken
241+ }
242+ }
243+ return taskDefsToDelete
244+ }
0 commit comments