@@ -665,49 +665,127 @@ async function deleteTier(
665665 context : ApimServiceContext ,
666666 descriptors : ResourceDescriptor [ ]
667667) : Promise < PublishActionResult [ ] > {
668- const tasks = descriptors . map ( ( descriptor ) => async ( ) => {
669- try {
670- const deleted = await client . deleteResource ( context , descriptor ) ;
668+ const apiDescriptors = descriptors . filter ( ( d ) => d . type === ResourceType . Api ) ;
669+ const nonApiDescriptors = descriptors . filter ( ( d ) => d . type !== ResourceType . Api ) ;
671670
672- return {
673- descriptor,
674- action : 'delete' as const ,
675- status : deleted ? ( 'success' as const ) : ( 'skipped' as const ) ,
676- } ;
677- } catch ( error ) {
678- logger . error (
679- `Failed to delete ${ buildResourceLabel ( descriptor ) } :` ,
680- error
681- ) ;
682- return {
683- descriptor,
684- action : 'delete' as const ,
685- status : 'failed' as const ,
686- error : error instanceof Error ? error : new Error ( String ( error ) ) ,
687- } ;
671+ const results : PublishActionResult [ ] = [ ] ;
672+
673+ if ( nonApiDescriptors . length > 0 ) {
674+ const nonApiResults = await deleteDescriptorsInParallel (
675+ client ,
676+ context ,
677+ nonApiDescriptors
678+ ) ;
679+ results . push ( ...nonApiResults ) ;
680+ }
681+
682+ if ( apiDescriptors . length > 0 ) {
683+ const orderedApiDescriptors = orderApiDescriptorsForDelete ( apiDescriptors ) ;
684+ const apiResults = await deleteDescriptorsSequentially (
685+ client ,
686+ context ,
687+ orderedApiDescriptors
688+ ) ;
689+ results . push ( ...apiResults ) ;
690+ }
691+
692+ return results ;
693+ }
694+
695+ function orderApiDescriptorsForDelete (
696+ descriptors : ResourceDescriptor [ ]
697+ ) : ResourceDescriptor [ ] {
698+ return [ ...descriptors ] . sort ( ( a , b ) => {
699+ const aName = getNamePart ( a . nameParts , 0 ) ;
700+ const bName = getNamePart ( b . nameParts , 0 ) ;
701+ const aRoot = getApiRootName ( aName ) ;
702+ const bRoot = getApiRootName ( bName ) ;
703+
704+ if ( aRoot !== bRoot ) {
705+ return aRoot . localeCompare ( bRoot ) ;
706+ }
707+
708+ const aIsRevision = isApiRevisionName ( aName ) ;
709+ const bIsRevision = isApiRevisionName ( bName ) ;
710+
711+ if ( aIsRevision === bIsRevision ) {
712+ return aName . localeCompare ( bName ) ;
688713 }
714+
715+ return aIsRevision ? - 1 : 1 ;
689716 } ) ;
717+ }
718+
719+ async function deleteDescriptorsSequentially (
720+ client : IApimClient ,
721+ context : ApimServiceContext ,
722+ descriptors : ResourceDescriptor [ ]
723+ ) : Promise < PublishActionResult [ ] > {
724+ const results : PublishActionResult [ ] = [ ] ;
725+
726+ for ( const descriptor of descriptors ) {
727+ results . push ( await deleteDescriptor ( client , context , descriptor ) ) ;
728+ }
729+
730+ return results ;
731+ }
732+
733+ async function deleteDescriptorsInParallel (
734+ client : IApimClient ,
735+ context : ApimServiceContext ,
736+ descriptors : ResourceDescriptor [ ]
737+ ) : Promise < PublishActionResult [ ] > {
738+ const tasks = descriptors . map ( ( descriptor ) => async ( ) =>
739+ deleteDescriptor ( client , context , descriptor )
740+ ) ;
690741
691742 const taskResults = await runParallel ( tasks , 5 ) ;
692743
693744 return taskResults . map ( ( tr , index ) => {
694745 if ( tr . status === 'fulfilled' && tr . value ) {
695746 return tr . value ;
696- } else {
697- const descriptor = descriptors [ index ] ;
698- if ( ! descriptor ) {
699- throw new Error ( 'No descriptor found for failed task' ) ;
700- }
701- return {
702- descriptor,
703- action : 'delete' as const ,
704- status : 'failed' as const ,
705- error : tr . reason || new Error ( 'Unknown error' ) ,
706- } ;
707747 }
748+
749+ const descriptor = descriptors [ index ] ;
750+ if ( ! descriptor ) {
751+ throw new Error ( 'No descriptor found for failed task' ) ;
752+ }
753+ return {
754+ descriptor,
755+ action : 'delete' as const ,
756+ status : 'failed' as const ,
757+ error : tr . reason || new Error ( 'Unknown error' ) ,
758+ } ;
708759 } ) ;
709760}
710761
762+ async function deleteDescriptor (
763+ client : IApimClient ,
764+ context : ApimServiceContext ,
765+ descriptor : ResourceDescriptor
766+ ) : Promise < PublishActionResult > {
767+ try {
768+ const deleted = await client . deleteResource ( context , descriptor ) ;
769+
770+ return {
771+ descriptor,
772+ action : 'delete' as const ,
773+ status : deleted ? ( 'success' as const ) : ( 'skipped' as const ) ,
774+ } ;
775+ } catch ( error ) {
776+ logger . error (
777+ `Failed to delete ${ buildResourceLabel ( descriptor ) } :` ,
778+ error
779+ ) ;
780+ return {
781+ descriptor,
782+ action : 'delete' as const ,
783+ status : 'failed' as const ,
784+ error : error instanceof Error ? error : new Error ( String ( error ) ) ,
785+ } ;
786+ }
787+ }
788+
711789/**
712790 * Convert ResourcePublishResult to PublishActionResult.
713791 */
0 commit comments