From b7777431fdb944d4669ca7239316f0742c11b6ec Mon Sep 17 00:00:00 2001 From: Guy Fankam Date: Mon, 29 Jul 2024 15:40:23 -0400 Subject: [PATCH] Handle root API deletion --- tools/code/aspire/Program.cs | 1 - tools/code/publisher/Api.cs | 72 +++++++++++++++++++----------------- 2 files changed, 39 insertions(+), 34 deletions(-) diff --git a/tools/code/aspire/Program.cs b/tools/code/aspire/Program.cs index b9b5d3ce..c7c3b18e 100644 --- a/tools/code/aspire/Program.cs +++ b/tools/code/aspire/Program.cs @@ -7,7 +7,6 @@ private static void Main(string[] args) { var builder = DistributedApplication.CreateBuilder(args); - //builder.AddProject("extractor"); builder.AddProject("integration-tests"); builder.Build().Run(); diff --git a/tools/code/publisher/Api.cs b/tools/code/publisher/Api.cs index 7c28ff27..cdf271cd 100644 --- a/tools/code/publisher/Api.cs +++ b/tools/code/publisher/Api.cs @@ -596,7 +596,9 @@ private static DeleteApi GetDeleteApi(IServiceProvider provider) var taskDictionary = new ConcurrentDictionary>(); - return async (name, cancellationToken) => + return deleteApi; + + async ValueTask deleteApi(ApiName name, CancellationToken cancellationToken) { using var _ = activitySource.StartActivity(nameof(DeleteApi)) ?.AddTag("api.name", name); @@ -610,39 +612,40 @@ await taskDictionary.GetOrAdd(name, .WithCancellation(cancellationToken); }; - async ValueTask deleteApiInner(ApiName name, CancellationToken cancellationToken) - { - if (await isApiRevisionNumberCurrentInSourceControl(name, cancellationToken)) - { - logger.LogInformation("API {ApiName} is the current revision in source control. Skipping deletion...", name); - return; - } + async ValueTask deleteApiInner(ApiName name, CancellationToken cancellationToken) => + await ApiName.TryParseRevisionedName(name) + .Map(async api => await processRevisionedApi(api.RootName, api.RevisionNumber, cancellationToken)) + .IfLeft(async _ => await processRootApi(name, cancellationToken)); + async ValueTask processRootApi(ApiName name, CancellationToken cancellationToken) => await deleteFromApim(name, cancellationToken); - } - /// - /// We don't want to delete a revision if it was just made current. For instance: - /// 1. Dev has apiA with revision 1 (current) and revision 2. Artifacts folder has: - /// - /apis/apiA/apiInformation.json with revision 1 as current - /// - /apis/apiA;rev=2/apiInformation.json - /// 2. User makes revision 2 current in dev APIM. - /// 3. User runs extractor for dev APIM. Artifacts folder has: - /// - /apis/apiA/apiInformation.json with revision 2 as current - /// - /apis/apiA;rev=1/apiInformation.json - /// - /apis/apiA;rev=2 folder gets deleted. - /// 4. User runs publisher to prod APIM. We don't want to handle the deletion of folder /apis/apiA;rev=2, as it's the current revision. - async ValueTask isApiRevisionNumberCurrentInSourceControl(ApiName name, CancellationToken cancellationToken) => - await ApiName.TryParseRevisionedName(name) - .Match(async _ => await ValueTask.FromResult(false), - async api => - { - var (rootName, revisionNumber) = api; - var sourceControlRevisionNumberOption = await tryGetRevisionNumberInSourceControl(rootName, cancellationToken); - return sourceControlRevisionNumberOption - .Map(sourceControlRevisionNumber => sourceControlRevisionNumber == revisionNumber) - .IfNone(false); - }); + async ValueTask processRevisionedApi(ApiName name, ApiRevisionNumber revisionNumber, CancellationToken cancellationToken) + { + var rootName = ApiName.GetRootName(name); + var currentRevisionNumberOption = await tryGetRevisionNumberInSourceControl(rootName, cancellationToken); + + await currentRevisionNumberOption.Match(// If the current revision in source control has a different revision number, delete this revision. + // We don't want to delete a revision if it was just made current. For instance: + // 1. Dev has apiA with revision 1 (current) and revision 2. Artifacts folder has: + // - /apis/apiA/apiInformation.json with revision 1 as current + // - /apis/apiA;rev=2/apiInformation.json + // 2. User makes revision 2 current in dev APIM. + // 3. User runs extractor for dev APIM. Artifacts folder has: + // - /apis/apiA/apiInformation.json with revision 2 as current + // - /apis/apiA;rev=1/apiInformation.json + // - /apis/apiA;rev=2 folder gets deleted. + // 4. User runs publisher to prod APIM. We don't want to handle the deletion of folder /apis/apiA;rev=2, as it's the current revision. + async currentRevisionNumber => + { + if (currentRevisionNumber != revisionNumber) + { + await deleteFromApim(name, cancellationToken); + } + }, + // If there is no current revision in source control, process the root API deletion + async () => await deleteApi(rootName, cancellationToken)); + } async ValueTask> tryGetRevisionNumberInSourceControl(ApiName name, CancellationToken cancellationToken) { @@ -670,8 +673,11 @@ private static DeleteApiFromApim GetDeleteApiFromApim(IServiceProvider provider) { logger.LogInformation("Deleting API {ApiName}...", name); - await ApiUri.From(name, serviceUri) - .Delete(pipeline, cancellationToken); + var apiUri = ApiUri.From(name, serviceUri); + + await (ApiName.IsRevisioned(name) + ? apiUri.Delete(pipeline, cancellationToken) + : apiUri.DeleteAllRevisions(pipeline, cancellationToken)); }; } }