@@ -111,33 +111,6 @@ const handleExpiredTokenException = (): void => {
111111 process . exit ( ) ;
112112} ;
113113
114- /**
115- * Check if given region is enabled in the account info provided
116- * @param accountInfo aws account to check region
117- * @param region aws region to check
118- * @returns true if region is enabled in that account, false otherwise
119- */
120- const isRegionEnabled = async ( accountInfo : AWSAccountInfo , region : string , maxRetries = 3 ) : Promise < boolean > => {
121- for ( let attempt = 0 ; attempt < maxRetries ; attempt ++ ) {
122- try {
123- const account = new Account ( { ...accountInfo , region : 'us-east-1' } ) ;
124- const optStatus = await account . getRegionOptStatus ( { RegionName : region } ) . promise ( ) ;
125-
126- return optStatus . RegionOptStatus === 'ENABLED' || optStatus . RegionOptStatus === 'ENABLED_BY_DEFAULT' ;
127- } catch ( error ) {
128- if ( error . code === 'TooManyRequestsException' ) {
129- const backoffTime = Math . pow ( 2 , attempt ) * 1000 ; // exponential backoff: 1s, 2s, 4s
130- if ( attempt < maxRetries - 1 ) {
131- await sleep ( backoffTime ) ;
132- continue ;
133- }
134- }
135- throw error ; // rethrow if it's not a TooManyRequestsException or we're out of retries
136- }
137- }
138- throw new Error ( 'Max retries exceeded while checking region status' ) ;
139- } ;
140-
141114/**
142115 * We define a resource as viable for deletion if it matches TEST_REGEX in the name, and if it is > STALE_DURATION_MS old.
143116 */
@@ -193,7 +166,23 @@ const getOrphanTestIamRoles = async (account: AWSAccountInfo): Promise<IamRoleIn
193166 } ,
194167 ...( region ? { region } : { } ) ,
195168 maxRetries : 10 ,
196- } ) ;
169+ } ) ;
170+
171+ /**
172+ * Returns a list of regions enabled given the AWS account information
173+ * @param accountInfo aws account to check region
174+ * @returns Promise<string[]> a list of AWS regions enabled by the account
175+ */
176+ const getRegionsEnabled = async ( accountInfo : AWSAccountInfo ) : Promise < string [ ] > => {
177+ // Specify service region to avoid possible endpoint unavailable error
178+ const account = new Account ( { ...accountInfo , region : 'us-east-1' } ) ;
179+ const response = await account . listRegions ( ) . promise ( ) ;
180+ const enabledRegions = response . Regions . map ( r =>
181+ r . RegionOptStatus === 'ENABLED' || r . RegionOptStatus === 'ENABLED_BY_DEFAULT' ? r . RegionName : null ,
182+ ) . filter ( Boolean ) ;
183+
184+ return enabledRegions ;
185+ } ;
197186
198187/**
199188 * Returns a list of Amplify Apps in the region. The apps includes information about the CI build that created the app
@@ -202,11 +191,10 @@ const getOrphanTestIamRoles = async (account: AWSAccountInfo): Promise<IamRoleIn
202191 * @param region aws region to query for amplify Apps
203192 * @returns Promise<AmplifyAppInfo[]> a list of Amplify Apps in the region with build info
204193 */
205- const getAmplifyApps = async ( account : AWSAccountInfo , region : string ) : Promise < AmplifyAppInfo [ ] > => {
194+ const getAmplifyApps = async ( account : AWSAccountInfo , region : string , regionsEnabled : string [ ] ) : Promise < AmplifyAppInfo [ ] > => {
206195 const amplifyClient = new aws . Amplify ( getAWSConfig ( account , region ) ) ;
207196
208- const optStatus = await isRegionEnabled ( account , region ) ;
209- if ( ! optStatus ) {
197+ if ( ! regionsEnabled . includes ( region ) ) {
210198 console . error ( `Listing apps for account ${ account . accountId } -${ region } failed since ${ region } is not enabled. Skipping.` ) ;
211199 return [ ] ;
212200 }
@@ -280,11 +268,10 @@ const getStackDetails = async (stackName: string, account: AWSAccountInfo, regio
280268 } ;
281269} ;
282270
283- const getStacks = async ( account : AWSAccountInfo , region : string ) : Promise < StackInfo [ ] > => {
271+ const getStacks = async ( account : AWSAccountInfo , region : string , regionsEnabled : string [ ] ) : Promise < StackInfo [ ] > => {
284272 const cfnClient = new aws . CloudFormation ( getAWSConfig ( account , region ) ) ;
285273
286- const optStatus = await isRegionEnabled ( account , region ) ;
287- if ( ! optStatus ) {
274+ if ( ! regionsEnabled . includes ( region ) ) {
288275 console . error ( `Listing stacks for account ${ account . accountId } -${ region } failed since ${ region } is not enabled. Skipping.` ) ;
289276 return [ ] ;
290277 }
@@ -768,8 +755,10 @@ const getAccountsToCleanup = async (): Promise<AWSAccountInfo[]> => {
768755} ;
769756
770757const cleanupAccount = async ( account : AWSAccountInfo , accountIndex : number , filterPredicate : JobFilterPredicate ) : Promise < void > => {
771- const appPromises = AWS_REGIONS_TO_RUN_TESTS . map ( region => getAmplifyApps ( account , region ) ) ;
772- const stackPromises = AWS_REGIONS_TO_RUN_TESTS . map ( region => getStacks ( account , region ) ) ;
758+ const regionsEnabled = await getRegionsEnabled ( account ) ;
759+
760+ const appPromises = AWS_REGIONS_TO_RUN_TESTS . map ( region => getAmplifyApps ( account , region , regionsEnabled ) ) ;
761+ const stackPromises = AWS_REGIONS_TO_RUN_TESTS . map ( region => getStacks ( account , region , regionsEnabled ) ) ;
773762 const bucketPromise = getS3Buckets ( account ) ;
774763 const orphanBucketPromise = getOrphanS3TestBuckets ( account ) ;
775764 const orphanIamRolesPromise = getOrphanTestIamRoles ( account ) ;
0 commit comments