From e1fedf994b112a3865ef990025312c4ab3523f26 Mon Sep 17 00:00:00 2001 From: maliming Date: Thu, 25 May 2023 14:53:13 +0800 Subject: [PATCH] Add `ClearDownloadCacheCommand`. Resolve #16641 --- .../Volo/Abp/Cli/AbpCliCoreModule.cs | 3 +- .../Cli/Commands/ClearDownloadCacheCommand.cs | 60 +++++++++++++++++++ .../Volo/Abp/Cli/Commands/NewCommand.cs | 37 ++++++------ .../Commands/ProjectCreationCommandBase.cs | 38 +++++++----- .../ProjectBuilding/AbpIoSourceCodeStore.cs | 12 ++-- .../Cli/ProjectBuilding/ProjectBuildArgs.cs | 6 +- 6 files changed, 117 insertions(+), 39 deletions(-) create mode 100644 framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/ClearDownloadCacheCommand.cs diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/AbpCliCoreModule.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/AbpCliCoreModule.cs index d1736ee8c1..e7289b7edd 100644 --- a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/AbpCliCoreModule.cs +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/AbpCliCoreModule.cs @@ -64,7 +64,8 @@ public class AbpCliCoreModule : AbpModule options.Commands[InstallLibsCommand.Name] = typeof(InstallLibsCommand); options.Commands[CleanCommand.Name] = typeof(CleanCommand); options.Commands[CliCommand.Name] = typeof(CliCommand); - + options.Commands[ClearDownloadCacheCommand.Name] = typeof(ClearDownloadCacheCommand); + options.DisabledModulesToAddToSolution.Add("Volo.Abp.LeptonXTheme.Pro"); options.DisabledModulesToAddToSolution.Add("Volo.Abp.LeptonXTheme.Lite"); }); diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/ClearDownloadCacheCommand.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/ClearDownloadCacheCommand.cs new file mode 100644 index 0000000000..981bdb4311 --- /dev/null +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/ClearDownloadCacheCommand.cs @@ -0,0 +1,60 @@ +using System; +using System.IO; +using System.Text; +using System.Threading.Tasks; +using Microsoft.Extensions.Logging; +using Microsoft.Extensions.Logging.Abstractions; +using Volo.Abp.Cli.Args; +using Volo.Abp.DependencyInjection; + +namespace Volo.Abp.Cli.Commands; + +public class ClearDownloadCacheCommand : IConsoleCommand, ITransientDependency +{ + public const string Name = "clear-download-cache"; + + public ILogger Logger { get; set; } + + + public ClearDownloadCacheCommand() + { + Logger = NullLogger.Instance; + } + + public async Task ExecuteAsync(CommandLineArgs commandLineArgs) + { + Logger.LogInformation("Clearing the templates download cache..."); + foreach (var cacheFile in Directory.GetFiles(CliPaths.TemplateCache, "*.zip")) + { + Logger.LogInformation($"Deleting {cacheFile}"); + try + { + File.Delete(cacheFile); + } + catch (Exception e) + { + Logger.LogError(e, $"Could not delete {cacheFile}"); + } + } + Logger.LogInformation("Done."); + await Task.CompletedTask; + } + + public string GetUsageInfo() + { + var sb = new StringBuilder(); + + sb.AppendLine(""); + sb.AppendLine("Usage:"); + sb.AppendLine(" abp clear-download-cache"); + sb.AppendLine(""); + sb.AppendLine("See the documentation for more info: https://docs.abp.io/en/abp/latest/CLI"); + + return sb.ToString(); + } + + public string GetShortDescription() + { + return "Clears the templates download cache."; + } +} diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/NewCommand.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/NewCommand.cs index 3336e9f5c7..676b42081f 100644 --- a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/NewCommand.cs +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/NewCommand.cs @@ -24,40 +24,40 @@ namespace Volo.Abp.Cli.Commands; public class NewCommand : ProjectCreationCommandBase, IConsoleCommand, ITransientDependency { public const string Name = "new"; - + protected TemplateProjectBuilder TemplateProjectBuilder { get; } public ITemplateInfoProvider TemplateInfoProvider { get; } - + public NewCommand( - ConnectionStringProvider connectionStringProvider, + ConnectionStringProvider connectionStringProvider, SolutionPackageVersionFinder solutionPackageVersionFinder, ICmdHelper cmdHelper, - IInstallLibsService installLibsService, + IInstallLibsService installLibsService, CliService cliService, - AngularPwaSupportAdder angularPwaSupportAdder, + AngularPwaSupportAdder angularPwaSupportAdder, InitialMigrationCreator initialMigrationCreator, - ThemePackageAdder themePackageAdder, - ILocalEventBus eventBus, + ThemePackageAdder themePackageAdder, + ILocalEventBus eventBus, IBundlingService bundlingService, - ITemplateInfoProvider templateInfoProvider, + ITemplateInfoProvider templateInfoProvider, TemplateProjectBuilder templateProjectBuilder, AngularThemeConfigurer angularThemeConfigurer) : base(connectionStringProvider, - solutionPackageVersionFinder, - cmdHelper, - installLibsService, - cliService, + solutionPackageVersionFinder, + cmdHelper, + installLibsService, + cliService, angularPwaSupportAdder, initialMigrationCreator, - themePackageAdder, - eventBus, + themePackageAdder, + eventBus, bundlingService, angularThemeConfigurer) { TemplateInfoProvider = templateInfoProvider; TemplateProjectBuilder = templateProjectBuilder; } - + public async Task ExecuteAsync(CommandLineArgs commandLineArgs) { var projectName = NamespaceHelper.NormalizeNamespace(commandLineArgs.Target); @@ -100,20 +100,20 @@ public class NewCommand : ProjectCreationCommandBase, IConsoleCommand, ITransien ConfigureNpmPackagesForTheme(projectArgs); await RunGraphBuildForMicroserviceServiceTemplate(projectArgs); await CreateInitialMigrationsAsync(projectArgs); - + var skipInstallLibs = commandLineArgs.Options.ContainsKey(Options.SkipInstallingLibs.Long) || commandLineArgs.Options.ContainsKey(Options.SkipInstallingLibs.Short); if (!skipInstallLibs) { await RunInstallLibsForWebTemplateAsync(projectArgs); ConfigureAngularJsonForThemeSelection(projectArgs); } - + var skipBundling = commandLineArgs.Options.ContainsKey(Options.SkipBundling.Long) || commandLineArgs.Options.ContainsKey(Options.SkipBundling.Short); if (!skipBundling) { await RunBundleForBlazorWasmOrMauiBlazorTemplateAsync(projectArgs); } - + await ConfigurePwaSupportForAngular(projectArgs); OpenRelatedWebPage(projectArgs, template, isTiered, commandLineArgs); @@ -149,6 +149,7 @@ public class NewCommand : ProjectCreationCommandBase, IConsoleCommand, ITransien sb.AppendLine("--local-framework-ref --abp-path (keeps local references to projects instead of replacing with NuGet package references)"); sb.AppendLine("-sib|--skip-installing-libs (Doesn't run `abp install-libs` command after project creation)"); sb.AppendLine("-sb|--skip-bundling (Doesn't run `abp bundle` command after Blazor Wasm project creation)"); + sb.AppendLine("-sc|--skip-cache (Always download the latest from our server and refresh their templates folder cache)"); sb.AppendLine(""); sb.AppendLine("Examples:"); sb.AppendLine(""); diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/ProjectCreationCommandBase.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/ProjectCreationCommandBase.cs index f092c2782e..65982e8567 100644 --- a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/ProjectCreationCommandBase.cs +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/Commands/ProjectCreationCommandBase.cs @@ -39,7 +39,7 @@ public abstract class ProjectCreationCommandBase public ILogger Logger { get; set; } public ThemePackageAdder ThemePackageAdder { get; } - + public AngularThemeConfigurer AngularThemeConfigurer { get; } public ProjectCreationCommandBase( @@ -52,7 +52,7 @@ public abstract class ProjectCreationCommandBase InitialMigrationCreator initialMigrationCreator, ThemePackageAdder themePackageAdder, ILocalEventBus eventBus, - IBundlingService bundlingService, + IBundlingService bundlingService, AngularThemeConfigurer angularThemeConfigurer) { _bundlingService = bundlingService; @@ -221,10 +221,12 @@ public abstract class ProjectCreationCommandBase } commandLineArgs.Options.Add(CliConsts.Command, commandLineArgs.Command); - + var theme = uiFramework == UiFramework.None ? (Theme?)null : GetThemeByTemplateOrNull(commandLineArgs, template); var themeStyle = theme.HasValue ? GetThemeStyleOrNull(commandLineArgs, theme.Value) : (ThemeStyle?)null; + var skipCache = commandLineArgs.Options.ContainsKey(Options.SkipCache.Long) || commandLineArgs.Options.ContainsKey(Options.SkipCache.Short); + return new ProjectBuildArgs( solutionName, template, @@ -242,7 +244,8 @@ public abstract class ProjectCreationCommandBase connectionString, pwa, theme, - themeStyle + themeStyle, + skipCache ); } @@ -417,7 +420,7 @@ public abstract class ProjectCreationCommandBase protected async Task RunBundleForBlazorWasmOrMauiBlazorTemplateAsync(ProjectBuildArgs projectArgs) { - if ((AppTemplateBase.IsAppTemplate(projectArgs.TemplateName) || AppNoLayersTemplateBase.IsAppNoLayersTemplate(projectArgs.TemplateName)) + if ((AppTemplateBase.IsAppTemplate(projectArgs.TemplateName) || AppNoLayersTemplateBase.IsAppNoLayersTemplate(projectArgs.TemplateName)) && projectArgs.UiFramework is UiFramework.Blazor or UiFramework.MauiBlazor) { var isWebassembly = projectArgs.UiFramework == UiFramework.Blazor; @@ -432,7 +435,7 @@ public abstract class ProjectCreationCommandBase var directory = Path.GetDirectoryName( Directory.GetFiles(projectArgs.OutputFolder, isWebassembly? "*.Blazor.csproj" :"*.MauiBlazor.csproj", SearchOption.AllDirectories).First() ); - + await _bundlingService.BundleAsync(directory, true, projectType: isWebassembly ? BundlingConsts.WebAssembly : BundlingConsts.MauiBlazor); } } @@ -584,10 +587,10 @@ public abstract class ProjectCreationCommandBase { // null or "leptonx-lite" => Theme.LeptonXLite, "basic" => Theme.Basic, - _ => Theme.LeptonXLite + _ => Theme.LeptonXLite }; } - + Theme GetAppProTheme() { return theme switch @@ -600,16 +603,16 @@ public abstract class ProjectCreationCommandBase } } - protected virtual ThemeStyle? GetThemeStyleOrNull(CommandLineArgs commandLineArgs, Theme theme) + protected virtual ThemeStyle? GetThemeStyleOrNull(CommandLineArgs commandLineArgs, Theme theme) { - if(theme != Theme.LeptonX) + if(theme != Theme.LeptonX) { return null; } var themeStyle = commandLineArgs.Options.GetOrNull(Options.ThemeStyle.Long)?.ToLower(); - - return themeStyle switch + + return themeStyle switch { "system" or null => ThemeStyle.System, "dim" => ThemeStyle.Dim, @@ -660,7 +663,7 @@ public abstract class ProjectCreationCommandBase ThemePackageAdder.AddAngularPackage(projectArgs.OutputFolder, "@abp/ng.theme.basic", projectArgs.Version); } } - + private void ConfigureNpmPackagesForLeptonTheme(ProjectBuildArgs projectArgs) { if (projectArgs.UiFramework is not UiFramework.None or UiFramework.Angular) @@ -686,7 +689,7 @@ public abstract class ProjectCreationCommandBase { return; } - + if (projectArgs.Theme.HasValue && projectArgs.UiFramework == UiFramework.Angular) { var angularFolderPath = projectArgs.TemplateName == MicroserviceProTemplate.TemplateName @@ -790,6 +793,13 @@ public abstract class ProjectCreationCommandBase public const string Long = "skip-bundling"; } + public static class SkipCache + { + public const string Short = "sc"; + public const string Long = "skip-cache"; + } + + public static class Tiered { public const string Long = "tiered"; diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/AbpIoSourceCodeStore.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/AbpIoSourceCodeStore.cs index 7dceb70337..a364e85f79 100644 --- a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/AbpIoSourceCodeStore.cs +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/AbpIoSourceCodeStore.cs @@ -59,7 +59,8 @@ public class AbpIoSourceCodeStore : ISourceCodeStore, ITransientDependency string type, string version = null, string templateSource = null, - bool includePreReleases = false) + bool includePreReleases = false, + bool skipCache = false) { DirectoryHelper.CreateIfNotExists(CliPaths.TemplateCache); var latestVersion = version ?? await GetLatestSourceCodeVersionAsync(name, type, null, includePreReleases); @@ -111,7 +112,7 @@ public class AbpIoSourceCodeStore : ISourceCodeStore, ITransientDependency } #endif - if (Options.CacheTemplates && File.Exists(localCacheFile) && templateSource.IsNullOrWhiteSpace()) + if (Options.CacheTemplates && !skipCache && File.Exists(localCacheFile) && templateSource.IsNullOrWhiteSpace()) { Logger.LogInformation("Using cached " + type + ": " + name + ", version: " + version); return new TemplateFile(File.ReadAllBytes(localCacheFile), version, latestVersion, nugetVersion); @@ -132,6 +133,7 @@ public class AbpIoSourceCodeStore : ISourceCodeStore, ITransientDependency if (Options.CacheTemplates && templateSource.IsNullOrWhiteSpace()) { + File.Delete(localCacheFile); File.WriteAllBytes(localCacheFile, fileContent); } @@ -218,7 +220,7 @@ public class AbpIoSourceCodeStore : ISourceCodeStore, ITransientDependency var result = await response.Content.ReadAsStringAsync(); var versions = JsonSerializer.Deserialize(result); - return templateName.Contains("LeptonX") ? + return templateName.Contains("LeptonX") ? versions.LeptonXVersions.Any(v => v.Name == version) : versions.FrameworkAndCommercialVersions.Any(v => v.Name == version); } @@ -335,7 +337,7 @@ public class AbpIoSourceCodeStore : ISourceCodeStore, ITransientDependency public class GithubReleaseVersions { public List FrameworkAndCommercialVersions { get; set; } - + public List LeptonXVersions { get; set; } } -} \ No newline at end of file +} diff --git a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/ProjectBuildArgs.cs b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/ProjectBuildArgs.cs index b4b4429767..cdeba4eaeb 100644 --- a/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/ProjectBuildArgs.cs +++ b/framework/src/Volo.Abp.Cli.Core/Volo/Abp/Cli/ProjectBuilding/ProjectBuildArgs.cs @@ -46,6 +46,8 @@ public class ProjectBuildArgs public ThemeStyle? ThemeStyle { get; set; } + public bool SkipCache { get; set; } + [NotNull] public Dictionary ExtraProperties { get; set; } @@ -66,7 +68,8 @@ public class ProjectBuildArgs [CanBeNull] string connectionString = null, bool pwa = false, Theme? theme = null, - ThemeStyle? themeStyle = null) + ThemeStyle? themeStyle = null, + bool skipCache = false) { SolutionName = Check.NotNull(solutionName, nameof(solutionName)); TemplateName = templateName; @@ -85,5 +88,6 @@ public class ProjectBuildArgs Pwa = pwa; Theme = theme; ThemeStyle = themeStyle; + SkipCache = skipCache; } }