rip out the static ParseResult and instead compute a PR once and flow it through the command handlers

This commit is contained in:
Chet Husk 2024-03-12 15:53:28 -05:00
Родитель 9df17cb7b0
Коммит e372839b99
6 изменённых файлов: 58 добавлений и 69 удалений

Просмотреть файл

@ -18,28 +18,8 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Commands
{
internal static class CommandBundleFilter
{
private static readonly Lazy<string> _assemblyVersion =
new Lazy<string>(() =>
{
var assembly = Assembly.GetEntryAssembly() ?? Assembly.GetExecutingAssembly();
var assemblyVersionAttribute = assembly.GetCustomAttribute<AssemblyInformationalVersionAttribute>();
if (assemblyVersionAttribute == null)
{
return assembly.GetName().Version.ToString();
}
else
{
return assemblyVersionAttribute.InformationalVersion;
}
});
public static IEnumerable<Bundle> GetFilteredBundles(IEnumerable<Bundle> allBundles, ParseResult parseResult = null)
public static IEnumerable<Bundle> GetFilteredBundles(IEnumerable<Bundle> allBundles, ParseResult parseResult)
{
if (parseResult == null)
{
parseResult = CommandLineConfigs.CommandLineParseResult;
}
var option = parseResult.CommandResult.GetUninstallMainOption();
var typeSelection = parseResult.GetTypeSelection();
var archSelection = parseResult.GetArchSelection();
@ -52,7 +32,7 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Commands
throw new RequiredArgMissingForUninstallCommandException();
}
bundles = OptionFilterers.UninstallNoOptionFilterer.Filter(
bundles = OptionFilterers.UninstallNoOptionFilterer.Filter(
parseResult.CommandResult.Tokens.Select(t => t.Value),
bundles,
typeSelection,
@ -79,24 +59,15 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Commands
return bundles;
}
public static IDictionary<Bundle, string> GetFilteredWithRequirementStrings(IBundleCollector bundleCollector)
public static IDictionary<Bundle, string> GetFilteredWithRequirementStrings(IBundleCollector bundleCollector, ParseResult parseResult)
{
var allBundles = bundleCollector.GetAllInstalledBundles();
var filteredBundles = GetFilteredBundles(allBundles);
var filteredBundles = GetFilteredBundles(allBundles, parseResult);
return VisualStudioSafeVersionsExtractor.GetReasonRequiredStrings(allBundles)
.Where(pair => filteredBundles.Contains(pair.Key))
.ToDictionary(i => i.Key, i => i.Value);
}
public static void HandleVersionOption()
{
if (CommandLineConfigs.CommandLineParseResult.FindResultFor(CommandLineConfigs.VersionOption) != null)
{
Console.WriteLine(_assemblyVersion.Value);
Environment.Exit(0);
}
}
private static IEnumerable<Bundle> FilterRequiredBundles(IEnumerable<Bundle> allBundles, IEnumerable<Token> tokens)
{
var explicitlyListedBundles = tokens

Просмотреть файл

@ -7,29 +7,28 @@ using Microsoft.DotNet.Tools.Uninstall.Shared.BundleInfo;
using System.Linq;
using Microsoft.DotNet.Tools.Uninstall.Shared.Utils;
using Microsoft.DotNet.Tools.Uninstall.MacOs;
using System.CommandLine.Parsing;
namespace Microsoft.DotNet.Tools.Uninstall.Shared.Commands
{
internal static class DryRunCommandExec
{
public static void Execute(IBundleCollector bundleCollector)
public static void Execute(IBundleCollector bundleCollector, ParseResult parseResult)
{
CommandBundleFilter.HandleVersionOption();
var filtered = CommandBundleFilter.GetFilteredWithRequirementStrings(bundleCollector);
var filtered = CommandBundleFilter.GetFilteredWithRequirementStrings(bundleCollector, parseResult);
TryIt(filtered);
}
private static void TryIt(IDictionary<Bundle, string> bundles)
{
var displayNames = string.Join("\n", bundles.Select(bundle => $" {bundle.Key.DisplayName}"));
Console.WriteLine(string.Format(RuntimeInfo.RunningOnWindows ?
Console.WriteLine(string.Format(RuntimeInfo.RunningOnWindows ?
LocalizableStrings.WindowsDryRunOutputFormat : LocalizableStrings.MacDryRunOutputFormat, displayNames));
foreach (var pair in bundles.Where(b => !b.Value.Equals(string.Empty)))
{
Console.ForegroundColor = ConsoleColor.Red;
Console.Write(string.Format(RuntimeInfo.RunningOnWindows ? LocalizableStrings.WindowsRequiredBundleConfirmationPromptWarningFormat :
Console.Write(string.Format(RuntimeInfo.RunningOnWindows ? LocalizableStrings.WindowsRequiredBundleConfirmationPromptWarningFormat :
LocalizableStrings.MacRequiredBundleConfirmationPromptWarningFormat, pair.Key.DisplayName, pair.Value));
Console.ResetColor();
}

Просмотреть файл

@ -20,14 +20,14 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Commands
{
internal static class ListCommandExec
{
public static void Execute(IBundleCollector bundleCollector)
public static int Execute(IBundleCollector bundleCollector)
{
Execute(
return Execute(
bundleCollector.GetAllInstalledBundles(),
bundleCollector.GetSupportedBundleTypes());
}
private static void Execute(
private static int Execute(
IEnumerable<Bundle> bundles,
IEnumerable<BundleTypePrintInfo> supportedBundleTypes)
{
@ -66,11 +66,13 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Commands
stackView.Render(
new ConsoleRenderer(new SystemConsole()),
new Region(0, 0, int.MaxValue, int.MaxValue));
return 0;
}
public static Dictionary<BundleTypePrintInfo, Dictionary<Bundle, string>> GetFilteredBundlesWithRequirements(
IEnumerable<Bundle> bundles,
IEnumerable<BundleTypePrintInfo> supportedBundleTypes,
IEnumerable<BundleTypePrintInfo> supportedBundleTypes,
ParseResult parseResult)
{
var uninstallMap = VisualStudioSafeVersionsExtractor.GetReasonRequiredStrings(bundles);

Просмотреть файл

@ -15,6 +15,7 @@ using System.Security.Principal;
using System.Runtime.InteropServices;
using System.ComponentModel;
using Microsoft.DotNet.Tools.Uninstall.MacOs;
using System.CommandLine.Parsing;
namespace Microsoft.DotNet.Tools.Uninstall.Shared.Commands
{
@ -30,20 +31,19 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Commands
[MarshalAs(UnmanagedType.LPWStr)] string lpCmdLine,
out int pNumArgs);
public static void Execute(IBundleCollector bundleCollector)
public static void Execute(IBundleCollector bundleCollector, ParseResult parseResult)
{
CommandBundleFilter.HandleVersionOption();
var filtered = CommandBundleFilter.GetFilteredWithRequirementStrings(bundleCollector, parseResult);
var verbosity = parseResult.CommandResult.GetVerbosityLevel();
var filtered = CommandBundleFilter.GetFilteredWithRequirementStrings(bundleCollector);
if (CommandLineConfigs.CommandLineParseResult.FindResultFor(CommandLineConfigs.YesOption) != null)
if (parseResult.FindResultFor(CommandLineConfigs.YesOption) != null)
{
if (!IsAdmin())
{
throw new NotAdminException();
}
DoIt(filtered.Keys);
DoIt(filtered.Keys, verbosity);
}
else
{
@ -56,15 +56,14 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Commands
{
if (AskWithWarningsForRequiredBundles(filtered))
{
DoIt(filtered.Keys);
DoIt(filtered.Keys, verbosity);
}
}
}
}
private static void DoIt(IEnumerable<Bundle> bundles)
private static void DoIt(IEnumerable<Bundle> bundles, VerbosityLevel verbosityLevel)
{
var verbosityLevel = CommandLineConfigs.CommandLineParseResult.CommandResult.GetVerbosityLevel();
var verbosityLogger = new VerbosityLogger(verbosityLevel);
var canceled = false;
@ -214,7 +213,7 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Commands
public static bool AskItAndReturnUserAnswer(IDictionary<Bundle, string> bundles, string userResponse = null)
{
var displayNames = string.Join("\n", bundles.Select(bundle => $" {bundle.Key.DisplayName}"));
Console.Write(string.Format(RuntimeInfo.RunningOnWindows ? LocalizableStrings.WindowsConfirmationPromptOutputFormat :
Console.Write(string.Format(RuntimeInfo.RunningOnWindows ? LocalizableStrings.WindowsConfirmationPromptOutputFormat :
LocalizableStrings.MacConfirmationPromptOutputFormat, displayNames));
var response = userResponse == null ? Console.ReadLine().Trim().ToUpper() : userResponse.ToUpper();
@ -233,19 +232,19 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Commands
}
}
public static bool AskWithWarningsForRequiredBundles(IDictionary<Bundle, string> bundles, string userResponse = null)
public static bool AskWithWarningsForRequiredBundles(IDictionary<Bundle, string> bundles, string userResponse = null)
{
var requiredBundles = bundles.Where(b => !b.Value.Equals(string.Empty));
foreach (var pair in requiredBundles)
{
Console.ForegroundColor = ConsoleColor.Red;
Console.Write(string.Format(RuntimeInfo.RunningOnWindows ? LocalizableStrings.WindowsRequiredBundleConfirmationPromptOutputFormat :
Console.Write(string.Format(RuntimeInfo.RunningOnWindows ? LocalizableStrings.WindowsRequiredBundleConfirmationPromptOutputFormat :
LocalizableStrings.MacRequiredBundleConfirmationPromptOutputFormat, pair.Key.DisplayName, pair.Value));
Console.ResetColor();
var response = userResponse == null ? Console.ReadLine().Trim().ToUpper() : userResponse.ToUpper();
if (response.Equals("N"))
{
return false ;
return false;
}
else if (!(response.Equals("Y") || response.Equals("YES")))
{

Просмотреть файл

@ -8,6 +8,7 @@ using System.CommandLine.Builder;
using System.CommandLine.Invocation;
using System.CommandLine.Parsing;
using System.Linq;
using System.Reflection;
using System.Runtime.InteropServices;
using Microsoft.DotNet.Tools.Uninstall.MacOs;
using Microsoft.DotNet.Tools.Uninstall.Shared.BundleInfo;
@ -29,7 +30,7 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Configs
private static readonly string RemoveCommandName = "remove";
public static readonly RootCommand UninstallRootCommand = new RootCommand(
RuntimeInfo.RunningOnWindows ? LocalizableStrings.UninstallNoOptionDescriptionWindows
RuntimeInfo.RunningOnWindows ? LocalizableStrings.UninstallNoOptionDescriptionWindows
: LocalizableStrings.UninstallNoOptionDescriptionMac);
public static readonly Command ListCommand = new Command(
@ -120,7 +121,7 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Configs
$"--{X86OptionName}",
LocalizableStrings.ListX86OptionDescription);
public static readonly Option VersionOption = new Option("--version")
public static readonly Command VersionSubcommand = new Command("--version")
{
IsHidden = true
};
@ -171,11 +172,10 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Configs
public static readonly Option[] AdditionalUninstallOptions = new Option[]
{
VerbosityOption,
VersionOption,
ForceOption
};
public static readonly Dictionary<string, VerbosityLevel> VerbosityLevels = new Dictionary<string, VerbosityLevel>
public static readonly Dictionary<string, VerbosityLevel> VerbosityLevels = new Dictionary<string, VerbosityLevel>
{
{ "q", VerbosityLevel.Quiet }, { "quiet", VerbosityLevel.Quiet },
{ "m", VerbosityLevel.Minimal }, { "minimal", VerbosityLevel.Minimal },
@ -184,19 +184,34 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Configs
{ "diag", VerbosityLevel.Diagnostic }, { "diagnostic", VerbosityLevel.Diagnostic }
};
public static ParseResult CommandLineParseResult;
public static readonly IEnumerable<Option> RemoveAuxOptions;
public static readonly IEnumerable<Option> DryRunAuxOptions;
public static readonly IEnumerable<Option> WhatIfAuxOptions;
public static readonly IEnumerable<Option> ListAuxOptions;
static CommandLineConfigs()
private static readonly Lazy<string> _assemblyVersion =
new Lazy<string>(() =>
{
var assembly = Assembly.GetEntryAssembly() ?? Assembly.GetExecutingAssembly();
var assemblyVersionAttribute = assembly.GetCustomAttribute<AssemblyInformationalVersionAttribute>();
if (assemblyVersionAttribute == null)
{
return assembly.GetName().Version.ToString();
}
else
{
return assemblyVersionAttribute.InformationalVersion;
}
});
static CommandLineConfigs()
{
DryRunCommand.AddAlias(WhatIfCommandName);
UninstallRootCommand.AddCommand(ListCommand);
UninstallRootCommand.AddCommand(DryRunCommand);
UninstallRootCommand.AddCommand(RemoveCommand);
UninstallRootCommand.AddCommand(VersionSubcommand);
var supportedBundleTypeNames = SupportedBundleTypeConfigs.GetSupportedBundleTypes().Select(type => type.OptionName);
@ -233,15 +248,18 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Configs
AssignOptionsToCommand(ListCommand, ListAuxOptions);
var bundleCollector = OperatingSystem.IsWindows() ? new RegistryQuery() as IBundleCollector : new FileSystemExplorer() as IBundleCollector;
ListCommand.Handler = CommandHandler.Create(ExceptionHandler.HandleException(() => ListCommandExec.Execute(bundleCollector)));
DryRunCommand.Handler = CommandHandler.Create(ExceptionHandler.HandleException(() => DryRunCommandExec.Execute(bundleCollector)));
RemoveCommand.Handler = CommandHandler.Create(ExceptionHandler.HandleException(() => UninstallCommandExec.Execute(bundleCollector)));
ListCommand.Handler = CommandHandler.Create(ExceptionHandler.HandleException((ParseResult parseResult) => ListCommandExec.Execute(bundleCollector)));
DryRunCommand.Handler = CommandHandler.Create(ExceptionHandler.HandleException((ParseResult parseResult) => DryRunCommandExec.Execute(bundleCollector, parseResult)));
RemoveCommand.Handler = CommandHandler.Create(ExceptionHandler.HandleException((ParseResult parseResult) => UninstallCommandExec.Execute(bundleCollector, parseResult)));
VersionSubcommand.Handler = CommandHandler.Create(() =>
{
Console.WriteLine(_assemblyVersion.Value);
});
UninstallCommandParser = new CommandLineBuilder(UninstallRootCommand)
.UseDefaults()
.UseHelpBuilder(context => new UninstallHelpBuilder(context.Console))
.Build();
CommandLineParseResult = UninstallCommandParser.Parse(Environment.GetCommandLineArgs());
}
public static Option GetUninstallMainOption(this CommandResult commandResult)

Просмотреть файл

@ -7,13 +7,13 @@ namespace Microsoft.DotNet.Tools.Uninstall.Shared.Exceptions
{
internal static class ExceptionHandler
{
public static Action HandleException(Action action)
public static Action<T> HandleException<T>(Action<T> action)
{
return () =>
return (x) =>
{
try
{
action.Invoke();
action.Invoke(x);
}
catch (DotNetUninstallException e)
{