From 9e49b72a5c032878d7a87421229701d2828b7b3e Mon Sep 17 00:00:00 2001 From: filipw Date: Tue, 7 Aug 2018 09:55:09 +0200 Subject: [PATCH] use a new arg parsing library --- src/ScriptCs.Core/FrameworkUtils.cs | 2 +- .../ReplCommands/InstallCommand.cs | 2 +- .../Package/PackageContainer.cs | 2 +- src/ScriptCs/Config.cs | 10 ++ src/ScriptCs/Program.cs | 104 ++++++++++++++---- src/ScriptCs/ScriptCs.csproj | 6 + test/ScriptCs.Tests.Acceptance/CommandLine.cs | 2 +- .../Configuration.cs | 2 +- .../Support/ScriptCsExe.cs | 8 +- 9 files changed, 108 insertions(+), 30 deletions(-) diff --git a/src/ScriptCs.Core/FrameworkUtils.cs b/src/ScriptCs.Core/FrameworkUtils.cs index e92f7bd9..148fadce 100644 --- a/src/ScriptCs.Core/FrameworkUtils.cs +++ b/src/ScriptCs.Core/FrameworkUtils.cs @@ -17,7 +17,7 @@ public static string FrameworkName if (_frameworkName == null) { //Thanks to Dave Glick for this code contribution - var frameworkName = Assembly.GetExecutingAssembly().GetCustomAttributes(true) + var frameworkName = Assembly.GetEntryAssembly().GetCustomAttributes(true) .OfType() .Select(x => x.FrameworkName) .FirstOrDefault(); diff --git a/src/ScriptCs.Core/ReplCommands/InstallCommand.cs b/src/ScriptCs.Core/ReplCommands/InstallCommand.cs index 6f49ae21..e668c82c 100644 --- a/src/ScriptCs.Core/ReplCommands/InstallCommand.cs +++ b/src/ScriptCs.Core/ReplCommands/InstallCommand.cs @@ -55,7 +55,7 @@ public object Execute(IRepl repl, object[] args) _installationProvider.Initialize(); var packageRef = new PackageReference( - args[0].ToString(), new FrameworkName(".NETFramework,Version=v4.0"), version); + args[0].ToString(), new FrameworkName(".NETFramework,Version=v4.6.1"), version); _packageInstaller.InstallPackages(new[] { packageRef }, allowPre); _packageAssemblyResolver.SavePackages(); diff --git a/src/ScriptCs.Hosting/Package/PackageContainer.cs b/src/ScriptCs.Hosting/Package/PackageContainer.cs index 8b124751..1dc7c8c8 100644 --- a/src/ScriptCs.Hosting/Package/PackageContainer.cs +++ b/src/ScriptCs.Hosting/Package/PackageContainer.cs @@ -150,7 +150,7 @@ private static bool IsValidFramework(FrameworkName frameworkName) private static bool IsValidProfile(string profile) { - return profile == "net40" || profile == "net45"; + return profile == "net40" || profile == "net45" || profile == "net461" || profile == "netstandard20"; } } } \ No newline at end of file diff --git a/src/ScriptCs/Config.cs b/src/ScriptCs/Config.cs index 0dd790da..55adea80 100644 --- a/src/ScriptCs/Config.cs +++ b/src/ScriptCs/Config.cs @@ -64,6 +64,16 @@ public static Config Create(ScriptCsArgs commandArgs) .Apply(ConfigMask.Create(commandArgs)); } + public static Config Create(string maskFile, ConfigMask configMask) + { + Guard.AgainstNullArgument("configMask", configMask); + + return new Config() + .Apply(ConfigMask.ReadGlobalOrDefault()) + .Apply(maskFile == null ? ConfigMask.ReadLocalOrDefault() : ConfigMask.Read(maskFile)) + .Apply(configMask); + } + public Config Apply(ConfigMask mask) { if (mask == null) diff --git a/src/ScriptCs/Program.cs b/src/ScriptCs/Program.cs index 56aeb776..661fe343 100644 --- a/src/ScriptCs/Program.cs +++ b/src/ScriptCs/Program.cs @@ -1,4 +1,6 @@ -using System; +using McMaster.Extensions.CommandLineUtils; +using ScriptCs.Contracts; +using System; using System.Diagnostics; using System.IO; using System.Linq; @@ -10,40 +12,100 @@ internal static class Program [LoaderOptimizationAttribute(LoaderOptimization.MultiDomain)] private static int Main(string[] args) { + //args = args.Skip(2).ToArray(); ProfileOptimizationShim.SetProfileRoot(Path.GetDirectoryName(typeof(Program).Assembly.Location)); ProfileOptimizationShim.StartProfile(typeof(Program).Assembly.GetName().Name + ".profile"); + var nonScriptArgs = args.TakeWhile(arg => arg != "--").ToArray(); var scriptArgs = args.Skip(nonScriptArgs.Length + 1).ToArray(); - ScriptCsArgs commandArgs; - try + + var app = new CommandLineApplication(throwOnUnexpectedArg: true) { - commandArgs = ScriptCsArgs.Parse(nonScriptArgs); - } - catch (Exception ex) + ExtendedHelpText = "Usage: scriptcs options", + OptionsComparison = StringComparison.OrdinalIgnoreCase + }; + + var script = app.Argument("script", "Script file name, must be specified first"); + + var scriptNameFallback = app.Option("--scriptname | -script", "Alternative way to pass a script filename", CommandOptionType.NoValue); + var repl = app.Option("--repl | -r", "Launch REPL mode when running script. To just launch REPL, simply omit the 'script' argument", CommandOptionType.NoValue); + var eval = app.Option("--eval | -e", "Code to immediately evaluate", CommandOptionType.SingleValue); + var configFile = app.Option("--config | -co", "Defines config file name", CommandOptionType.SingleValue); + var debug = app.Option("--debug | -d", "Emits PDB symbols allowing for attaching a Visual Studio debugger", CommandOptionType.NoValue); + var version = app.Option("--version | -v", "Outputs version information", CommandOptionType.NoValue); + var cache = app.Option("--cache | -c", "Flag which determines whether to run in memory or from a .dll", CommandOptionType.NoValue); + var logLevel = app.Option("--loglevel | -log", "Flag which defines the log level used", CommandOptionType.SingleValue); + var watch = app.Option("--watch | -w", "Watch the script file and reload it when changed", CommandOptionType.NoValue); + var modules = app.Option("--modules | -m", "Specify modules to load (comma separated)", CommandOptionType.SingleValue); + var output = app.Option("--output | -o", "Write all console output to the specified file", CommandOptionType.SingleValue); + + app.HelpOption("-Help | -?"); + + app.Command("install", c => { - Console.WriteLine(ex.Message); - return 1; - } + var package = c.Argument("package", "Specific package to install, otherwise installs and restores packages which are specified in packages.config"); + var allowPrerelease = c.Option("--allowprerelease | -pre", "Allows installation of packages' prelease versions", CommandOptionType.NoValue); + var packageVersion = c.Option("--packageversion | -p", "Defines the version of the package to install", CommandOptionType.SingleValue); + var save = c.Option("--save | -s", "Creates a packages.config file based on the packages directory", CommandOptionType.NoValue); + var clean = c.Option("--clean | -cl", "Cleans installed packages from working directory", CommandOptionType.NoValue); + var global = c.Option("--global | -g", "Installs and restores global packages which are specified in packages.config", CommandOptionType.NoValue); - if (commandArgs.Help) + c.OnExecute(() => + { + var configMask = new ConfigMask(); + configMask.Repl = false; + configMask.Global = global.HasValue() ? true : (bool?)null; + configMask.Install = package.Value ?? string.Empty; // needed to trigger install of all packages! + configMask.PackageVersion = packageVersion.Value(); + configMask.AllowPreRelease = allowPrerelease.HasValue() ? true : (bool?)null; + configMask.Save = save.HasValue() ? true : (bool?)null; + configMask.Global = global.HasValue() ? true : (bool?)null; + configMask.Clean = clean.HasValue() ? true : (bool?)null; + configMask.Output = output.Value(); + configMask.Debug = debug.HasValue() ? true : (bool?)null; + configMask.LogLevel = logLevel.ParsedValue; + + return Application.Run(Config.Create(configFile.Value(), configMask), scriptArgs); + }); + }); + + app.OnExecute(() => { - Console.WriteLine(ScriptCsArgs.GetUsage()); - return 0; - } + if (configFile.HasValue() && !File.Exists(configFile.Value())) + { + Console.WriteLine("The specified config file does not exist."); + return 1; + } + + if (version.HasValue()) + { + VersionWriter.Write(); + return 0; + } + + var configMask = new ConfigMask(); + configMask.Repl = repl.HasValue() ? true : (bool?)null; + configMask.ScriptName = scriptNameFallback.HasValue() ? scriptNameFallback.Value() : script.Value; + configMask.Debug = debug.HasValue() ? true : (bool?)null; + configMask.Eval = eval.Value(); + configMask.Cache = cache.HasValue() ? true : (bool?)null; + configMask.Watch = watch.HasValue() ? true : (bool?)null; + configMask.LogLevel = logLevel.ParsedValue; + configMask.Modules = modules.Value(); + configMask.Output = output.Value(); - if (commandArgs.Version) + return Application.Run(Config.Create(configFile.Value(), configMask), scriptArgs); + }); + + try { - VersionWriter.Write(); - return 0; + return app.Execute(nonScriptArgs); } - - if (commandArgs.Config != null && !File.Exists(commandArgs.Config)) + catch (CommandParsingException e) { - Console.WriteLine("The specified config file does not exist."); + app.ShowHelp(); return 1; } - - return Application.Run(Config.Create(commandArgs), scriptArgs); } } } diff --git a/src/ScriptCs/ScriptCs.csproj b/src/ScriptCs/ScriptCs.csproj index fd6d7c40..1146ad3c 100644 --- a/src/ScriptCs/ScriptCs.csproj +++ b/src/ScriptCs/ScriptCs.csproj @@ -18,6 +18,7 @@ + @@ -26,4 +27,9 @@ + + + SettingsSingleFileGenerator + + \ No newline at end of file diff --git a/test/ScriptCs.Tests.Acceptance/CommandLine.cs b/test/ScriptCs.Tests.Acceptance/CommandLine.cs index 0de9aed6..b8e78bef 100644 --- a/test/ScriptCs.Tests.Acceptance/CommandLine.cs +++ b/test/ScriptCs.Tests.Acceptance/CommandLine.cs @@ -29,7 +29,7 @@ public static void UnexpectedOption(Exception exception) .x(() => { Console.WriteLine(exception); - exception.Message.ShouldContain("unknownoption"); + exception.Message.ShouldContain("Usage: scriptcs options"); }); } } diff --git a/test/ScriptCs.Tests.Acceptance/Configuration.cs b/test/ScriptCs.Tests.Acceptance/Configuration.cs index b01b1810..2c0861ed 100644 --- a/test/ScriptCs.Tests.Acceptance/Configuration.cs +++ b/test/ScriptCs.Tests.Acceptance/Configuration.cs @@ -41,7 +41,7 @@ public static void CustomConfiguration(ScenarioDirectory directory, string outpu "When I execute the script without the log level option but specifying the custom config" .x(() => { - var args = new[] { "-config", "custom.opts", }; + var args = new[] { "--config", "custom.opts", }; output = ScriptCsExe.Run("foo.csx", false, args, directory); }); diff --git a/test/ScriptCs.Tests.Acceptance/Support/ScriptCsExe.cs b/test/ScriptCs.Tests.Acceptance/Support/ScriptCsExe.cs index 6e344edd..d2013d71 100644 --- a/test/ScriptCs.Tests.Acceptance/Support/ScriptCsExe.cs +++ b/test/ScriptCs.Tests.Acceptance/Support/ScriptCsExe.cs @@ -73,7 +73,7 @@ public static string Run(string scriptName, bool debug, IEnumerable args debug && !args.Select(arg => arg.Trim().ToUpperInvariant()).Contains("-DEBUG") && !args.Select(arg => arg.Trim().ToUpperInvariant()).Contains("-D") - ? new[] { "-debug" } + ? new[] { "--debug" } : new string[0]; return Execute( @@ -102,17 +102,17 @@ public static string Install(string package, ScenarioDirectory directory) writer.Flush(); } - return Execute(new[] { "-install", package }, Enumerable.Empty(), directory); + return Execute(new[] { "install", package }, Enumerable.Empty(), directory); } public static string Save(ScenarioDirectory directory) { - return Execute(new[] { "-save" }, Enumerable.Empty(), directory); + return Execute(new[] { "install", "--save" }, Enumerable.Empty(), directory); } public static string Clean(ScenarioDirectory directory) { - return Execute(new[] { "-clean" }, Enumerable.Empty(), directory); + return Execute(new[] { "install", "--clean" }, Enumerable.Empty(), directory); } private static string Execute(