diff --git a/CHANGELOG.md b/CHANGELOG.md index da9e5fb8b2..5090b6a2d3 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,8 @@ # Changelog +## [Unreleased] +* Format files in parallel [#2624](https://github.com/fsprojects/fantomas/issues/2624) + ## [5.1.4] - 2022-11-30 ### Fixed diff --git a/fantomas.sln b/fantomas.sln index d1b1f4ad68..6b26b4a0dd 100644 --- a/fantomas.sln +++ b/fantomas.sln @@ -39,6 +39,10 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution README.md = README.md EndProjectSection EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "src", "src", "{D55FCBF0-2648-43B3-B55F-853DD0A91085}" +EndProject +Project("{F2A71F9B-5D33-465A-A702-920D77279786}") = "Fantomas.CLI.Benchmarks", "src\Fantomas.CLI.Benchmarks\Fantomas.CLI.Benchmarks.fsproj", "{717DBF5B-9BE2-47EC-88E9-23BFE96441CE}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -133,6 +137,18 @@ Global {B39D50EE-0307-4C08-81F5-97418A946F63}.Release|x64.Build.0 = Release|Any CPU {B39D50EE-0307-4C08-81F5-97418A946F63}.Release|x86.ActiveCfg = Release|Any CPU {B39D50EE-0307-4C08-81F5-97418A946F63}.Release|x86.Build.0 = Release|Any CPU + {717DBF5B-9BE2-47EC-88E9-23BFE96441CE}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {717DBF5B-9BE2-47EC-88E9-23BFE96441CE}.Debug|Any CPU.Build.0 = Debug|Any CPU + {717DBF5B-9BE2-47EC-88E9-23BFE96441CE}.Debug|x64.ActiveCfg = Debug|Any CPU + {717DBF5B-9BE2-47EC-88E9-23BFE96441CE}.Debug|x64.Build.0 = Debug|Any CPU + {717DBF5B-9BE2-47EC-88E9-23BFE96441CE}.Debug|x86.ActiveCfg = Debug|Any CPU + {717DBF5B-9BE2-47EC-88E9-23BFE96441CE}.Debug|x86.Build.0 = Debug|Any CPU + {717DBF5B-9BE2-47EC-88E9-23BFE96441CE}.Release|Any CPU.ActiveCfg = Release|Any CPU + {717DBF5B-9BE2-47EC-88E9-23BFE96441CE}.Release|Any CPU.Build.0 = Release|Any CPU + {717DBF5B-9BE2-47EC-88E9-23BFE96441CE}.Release|x64.ActiveCfg = Release|Any CPU + {717DBF5B-9BE2-47EC-88E9-23BFE96441CE}.Release|x64.Build.0 = Release|Any CPU + {717DBF5B-9BE2-47EC-88E9-23BFE96441CE}.Release|x86.ActiveCfg = Release|Any CPU + {717DBF5B-9BE2-47EC-88E9-23BFE96441CE}.Release|x86.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE @@ -141,5 +157,6 @@ Global SolutionGuid = {DEBFC920-A647-4859-890D-B59793D27594} EndGlobalSection GlobalSection(NestedProjects) = preSolution + {717DBF5B-9BE2-47EC-88E9-23BFE96441CE} = {D55FCBF0-2648-43B3-B55F-853DD0A91085} EndGlobalSection EndGlobal diff --git a/src/Fantomas.CLI.Benchmarks/Fantomas.CLI.Benchmarks.fsproj b/src/Fantomas.CLI.Benchmarks/Fantomas.CLI.Benchmarks.fsproj new file mode 100644 index 0000000000..29c98478f0 --- /dev/null +++ b/src/Fantomas.CLI.Benchmarks/Fantomas.CLI.Benchmarks.fsproj @@ -0,0 +1,20 @@ + + + + Exe + net7.0 + false + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/Fantomas.CLI.Benchmarks/Program.fs b/src/Fantomas.CLI.Benchmarks/Program.fs new file mode 100644 index 0000000000..6e628f8111 --- /dev/null +++ b/src/Fantomas.CLI.Benchmarks/Program.fs @@ -0,0 +1,11 @@ +module Fantomas.CLI.Benchmarks.Program + +open System.Reflection +open BenchmarkDotNet.Running +open Fantomas.CLI.Benchmarks.Runners + +[] +let main _ = + BenchmarkRunner.Run(Assembly.GetAssembly(typeof)) |> ignore + //ColdStart().CheckInParallelServerGc() + 0 diff --git a/src/Fantomas.CLI.Benchmarks/Runners.fs b/src/Fantomas.CLI.Benchmarks/Runners.fs new file mode 100644 index 0000000000..d3767a11f5 --- /dev/null +++ b/src/Fantomas.CLI.Benchmarks/Runners.fs @@ -0,0 +1,34 @@ +module Fantomas.CLI.Benchmarks.Runners + +open BenchmarkDotNet.Attributes +open BenchmarkDotNet.Engines +open Fantomas.Core +open System.IO + +let config = FormatConfig.FormatConfig.Default + +let () x y = Path.Combine(x, y) + +[] +[] +[] +type ColdStart() = + + let tmpDir = __SOURCE_DIRECTORY__ ".." ".." "tmp" + + [] + member val projects = "" with get, set + + [] + member val processInParallel = false with get, set + + [] + [] + member this.FormatCode() = + let projectDir = tmpDir this.projects + Directory.SetCurrentDirectory(projectDir) + + let args = + Array.append (if this.processInParallel then [| "--parallel" |] else [||]) [| "-r"; projectDir |] + + Program.main args |> ignore diff --git a/src/Fantomas.CLI.Benchmarks/packages.lock.json b/src/Fantomas.CLI.Benchmarks/packages.lock.json new file mode 100644 index 0000000000..9ba8fb8144 --- /dev/null +++ b/src/Fantomas.CLI.Benchmarks/packages.lock.json @@ -0,0 +1,1047 @@ +{ + "version": 1, + "dependencies": { + "net7.0": { + "BenchmarkDotNet": { + "type": "Direct", + "requested": "[0.13.2, )", + "resolved": "0.13.2", + "contentHash": "82IflYxY8qnQXEA3kXtqC9pntrkJYJZbQ9PV7hEV/XcfCtOdwLz84ilyO8tLRVbiliWttvmt/v44P+visN+fPQ==", + "dependencies": { + "BenchmarkDotNet.Annotations": "0.13.2", + "CommandLineParser": "2.4.3", + "Iced": "1.17.0", + "Microsoft.CodeAnalysis.CSharp": "3.0.0", + "Microsoft.Diagnostics.Runtime": "2.2.332302", + "Microsoft.Diagnostics.Tracing.TraceEvent": "3.0.2", + "Microsoft.DotNet.PlatformAbstractions": "3.1.6", + "Perfolizer": "0.2.1", + "System.Management": "6.0.0", + "System.Reflection.Emit": "4.7.0", + "System.Reflection.Emit.Lightweight": "4.7.0", + "System.Threading.Tasks.Extensions": "4.5.4" + } + }, + "FSharp.Core": { + "type": "Direct", + "requested": "[6.0.4, )", + "resolved": "6.0.4", + "contentHash": "CYqAfmO7JvN38M+ACkstS8taVfl8C0mCkvSiBAshfKuu2Nut6+8MuFU7Wahu09wGIyFPlRz5ArFWxSOM5mhMSA==" + }, + "Argu": { + "type": "Transitive", + "resolved": "6.1.1", + "contentHash": "5SBLYihaZ6/YNpRU+0v0QLsCk7ABmOWNOUwkXVUql2w7kJ6Hi4AFhgIv5XLTtxTid5/xrJAL+PglQkNcjANCJg==", + "dependencies": { + "FSharp.Core": "4.3.2", + "System.Configuration.ConfigurationManager": "4.4.0" + } + }, + "BenchmarkDotNet.Annotations": { + "type": "Transitive", + "resolved": "0.13.2", + "contentHash": "+SGOYyXT6fiagbtrni38B8BqBgjruYKU3PfROI0lDIYo8jQ+APUmLKMEswK7zwR5fEOCrDmoAHSH6oykBkqPgA==" + }, + "CommandLineParser": { + "type": "Transitive", + "resolved": "2.4.3", + "contentHash": "U2FC9Y8NyIxxU6MpFFdWWu1xwiqz/61v/Doou7kmVjpeIEMLWyiNNkzNlSE84kyJ0O1LKApuEj5z48Ow0Hi4OQ==" + }, + "editorconfig": { + "type": "Transitive", + "resolved": "0.13.0", + "contentHash": "1IAdbakbxaKyVv/gr3VTHkbFMFgfOSpP4VRSvOg50Ee9qAfXDr4F8FvOtwq7Pi6fcoxxXYfOYceT1U3oODdpFg==" + }, + "Fable.Core": { + "type": "Transitive", + "resolved": "3.0.0", + "contentHash": "pkCOWJKAkCk36f5+q4F3XqlfsgCJL6i2lTLl4ZZVDswn8rjXo21EBG/gJ296a88LVBkI5LL2VwxQYqGZncomJw==", + "dependencies": { + "FSharp.Core": "4.5.2" + } + }, + "Iced": { + "type": "Transitive", + "resolved": "1.17.0", + "contentHash": "8x+HCVTl/HHTGpscH3vMBhV8sknN/muZFw9s3TsI8SA6+c43cOTCi2+jE4KsU8pNLbJ++iF2ZFcpcXHXtDglnw==" + }, + "Ignore": { + "type": "Transitive", + "resolved": "0.1.46", + "contentHash": "pmSSh25tuSY7a0Iqcs6TRGGZut8SGogNUlsH7g8E3YY9kLu+qOMIpqa2h26+Q4V6yVp71vQbzqrYENuVecKyxQ==" + }, + "MessagePack": { + "type": "Transitive", + "resolved": "2.2.85", + "contentHash": "3SqAgwNV5LOf+ZapHmjQMUc7WDy/1ur9CfFNjgnfMZKCB5CxkVVbyHa06fObjGTEHZI7mcDathYjkI+ncr92ZQ==", + "dependencies": { + "MessagePack.Annotations": "2.2.85", + "Microsoft.Bcl.AsyncInterfaces": "1.0.0", + "System.Collections.Immutable": "1.5.0", + "System.Memory": "4.5.3", + "System.Reflection.Emit": "4.6.0", + "System.Reflection.Emit.Lightweight": "4.6.0", + "System.Runtime.CompilerServices.Unsafe": "4.5.2", + "System.Threading.Tasks.Extensions": "4.5.3" + } + }, + "MessagePack.Annotations": { + "type": "Transitive", + "resolved": "2.2.85", + "contentHash": "YptRsDCQK35K5FhmZ0LojW4t8I6DpetLfK5KG8PVY2f6h7/gdyr8f4++xdSEK/xS6XX7/GPvEpqszKVPksCsiQ==" + }, + "Microsoft.Bcl.AsyncInterfaces": { + "type": "Transitive", + "resolved": "5.0.0", + "contentHash": "W8DPQjkMScOMTtJbPwmPyj9c3zYSFGawDW3jwlBOOsnY+EzZFLgNQ/UMkK35JmkNOVPdCyPr2Tw7Vv9N+KA3ZQ==" + }, + "Microsoft.CodeAnalysis.Analyzers": { + "type": "Transitive", + "resolved": "2.6.2-beta2", + "contentHash": "rg5Ql73AmGCMG5Q40Kzbndq7C7S4XvsJA+2QXfZBCy2dRqD+a7BSbx/3942EoRUJ/8Wh9+kLg2G2qC46o3f1Aw==" + }, + "Microsoft.CodeAnalysis.Common": { + "type": "Transitive", + "resolved": "3.0.0", + "contentHash": "HEnLZ9Op5IoXeuokhfSLIXstXfEyPzXhQ/xsnvUmxzb+7YpwuLk57txArzGs/Wne5bWmU7Uey4Q1jUZ3++heqg==", + "dependencies": { + "Microsoft.CodeAnalysis.Analyzers": "2.6.2-beta2", + "System.Collections.Immutable": "1.5.0", + "System.Memory": "4.5.1", + "System.Reflection.Metadata": "1.6.0", + "System.Runtime.CompilerServices.Unsafe": "4.5.0", + "System.Text.Encoding.CodePages": "4.5.0", + "System.Threading.Tasks.Extensions": "4.5.0" + } + }, + "Microsoft.CodeAnalysis.CSharp": { + "type": "Transitive", + "resolved": "3.0.0", + "contentHash": "hWFUxc0iUbVvIKWJODErOeOa5GiqZuEcetxaCfHqZ04zHy0ZCLx3v4/TdF/6Erx1mXPHfoT2Tiz5rZCQZ6OyxQ==", + "dependencies": { + "Microsoft.CodeAnalysis.Common": "[3.0.0]" + } + }, + "Microsoft.Diagnostics.NETCore.Client": { + "type": "Transitive", + "resolved": "0.2.251802", + "contentHash": "bqnYl6AdSeboeN4v25hSukK6Odm6/54E3Y2B8rBvgqvAW0mF8fo7XNRVE2DMOG7Rk0fiuA079QIH28+V+W1Zdg==", + "dependencies": { + "Microsoft.Bcl.AsyncInterfaces": "1.1.0", + "Microsoft.Extensions.Logging": "2.1.1" + } + }, + "Microsoft.Diagnostics.Runtime": { + "type": "Transitive", + "resolved": "2.2.332302", + "contentHash": "Hp84ivxSKIMTBzYSATxmUsm3YSXHWivcwiRRbsydGmqujMUK8BAueLN0ssAVEOkOBmh0vjUBhrq7YcroT7VCug==", + "dependencies": { + "Microsoft.Diagnostics.NETCore.Client": "0.2.251802", + "System.Collections.Immutable": "5.0.0", + "System.Runtime.CompilerServices.Unsafe": "5.0.0" + } + }, + "Microsoft.Diagnostics.Tracing.TraceEvent": { + "type": "Transitive", + "resolved": "3.0.2", + "contentHash": "Pr7t+Z/qBe6DxCow4BmYmDycHe2MrGESaflWXRcSUI4XNGyznx1ttS+9JNOxLuBZSoBSPTKw9Dyheo01Yi6anQ==", + "dependencies": { + "System.Runtime.CompilerServices.Unsafe": "4.5.3" + } + }, + "Microsoft.DotNet.PlatformAbstractions": { + "type": "Transitive", + "resolved": "3.1.6", + "contentHash": "jek4XYaQ/PGUwDKKhwR8K47Uh1189PFzMeLqO83mXrXQVIpARZCcfuDedH50YDTepBkfijCZN5U/vZi++erxtg==" + }, + "Microsoft.Extensions.Configuration": { + "type": "Transitive", + "resolved": "2.1.1", + "contentHash": "LjVKO6P2y52c5ZhTLX/w8zc5H4Y3J/LJsgqTBj49TtFq/hAtVNue/WA0F6/7GMY90xhD7K0MDZ4qpOeWXbLvzg==", + "dependencies": { + "Microsoft.Extensions.Configuration.Abstractions": "2.1.1" + } + }, + "Microsoft.Extensions.Configuration.Abstractions": { + "type": "Transitive", + "resolved": "2.1.1", + "contentHash": "VfuZJNa0WUshZ/+8BFZAhwFKiKuu/qOUCFntfdLpHj7vcRnsGHqd3G2Hse78DM+pgozczGM63lGPRLmy+uhUOA==", + "dependencies": { + "Microsoft.Extensions.Primitives": "2.1.1" + } + }, + "Microsoft.Extensions.Configuration.Binder": { + "type": "Transitive", + "resolved": "2.1.1", + "contentHash": "fcLCTS03poWE4v9tSNBr3pWn0QwGgAn1vzqHXlXgvqZeOc7LvQNzaWcKRQZTdEc3+YhQKwMsOtm3VKSA2aWQ8w==", + "dependencies": { + "Microsoft.Extensions.Configuration": "2.1.1" + } + }, + "Microsoft.Extensions.DependencyInjection.Abstractions": { + "type": "Transitive", + "resolved": "2.1.1", + "contentHash": "MgYpU5cwZohUMKKg3sbPhvGG+eAZ/59E9UwPwlrUkyXU+PGzqwZg9yyQNjhxuAWmoNoFReoemeCku50prYSGzA==" + }, + "Microsoft.Extensions.Logging": { + "type": "Transitive", + "resolved": "2.1.1", + "contentHash": "hh+mkOAQDTp6XH80xJt3+wwYVzkbwYQl9XZRCz4Um0JjP/o7N9vHM3rZ6wwwtr+BBe/L6iBO2sz0px6OWBzqZQ==", + "dependencies": { + "Microsoft.Extensions.Configuration.Binder": "2.1.1", + "Microsoft.Extensions.DependencyInjection.Abstractions": "2.1.1", + "Microsoft.Extensions.Logging.Abstractions": "2.1.1", + "Microsoft.Extensions.Options": "2.1.1" + } + }, + "Microsoft.Extensions.Logging.Abstractions": { + "type": "Transitive", + "resolved": "2.1.1", + "contentHash": "XRzK7ZF+O6FzdfWrlFTi1Rgj2080ZDsd46vzOjadHUB0Cz5kOvDG8vI7caa5YFrsHQpcfn0DxtjS4E46N4FZsA==" + }, + "Microsoft.Extensions.Options": { + "type": "Transitive", + "resolved": "2.1.1", + "contentHash": "V7lXCU78lAbzaulCGFKojcCyG8RTJicEbiBkPJjFqiqXwndEBBIehdXRMWEVU3UtzQ1yDvphiWUL9th6/4gJ7w==", + "dependencies": { + "Microsoft.Extensions.DependencyInjection.Abstractions": "2.1.1", + "Microsoft.Extensions.Primitives": "2.1.1" + } + }, + "Microsoft.Extensions.Primitives": { + "type": "Transitive", + "resolved": "2.1.1", + "contentHash": "scJ1GZNIxMmjpENh0UZ8XCQ6vzr/LzeF9WvEA51Ix2OQGAs9WPgPu8ABVUdvpKPLuor/t05gm6menJK3PwqOXg==", + "dependencies": { + "System.Memory": "4.5.1", + "System.Runtime.CompilerServices.Unsafe": "4.5.1" + } + }, + "Microsoft.NETCore.Platforms": { + "type": "Transitive", + "resolved": "5.0.0", + "contentHash": "VyPlqzH2wavqquTcYpkIIAQ6WdenuKoFN0BdYBbCWsclXacSOHNQn66Gt4z5NBqEYW0FAPm5rlvki9ZiCij5xQ==" + }, + "Microsoft.NETCore.Targets": { + "type": "Transitive", + "resolved": "1.1.3", + "contentHash": "3Wrmi0kJDzClwAC+iBdUBpEKmEle8FQNsCs77fkiOIw/9oYA07bL1EZNX0kQ2OMN3xpwvl0vAtOCYY3ndDNlhQ==" + }, + "Microsoft.VisualStudio.Threading": { + "type": "Transitive", + "resolved": "16.9.60", + "contentHash": "9igpltD4NDMb1QeLiuAShr4inAG/MEm/GL0VE3tCUXQmwrfrbrmwrhAn5fXy2uiZ1g2s2qSUkyEvx7sp2h7M8Q==", + "dependencies": { + "Microsoft.Bcl.AsyncInterfaces": "5.0.0", + "Microsoft.VisualStudio.Threading.Analyzers": "16.9.60", + "Microsoft.VisualStudio.Validation": "16.8.33", + "Microsoft.Win32.Registry": "5.0.0", + "System.Threading.Tasks.Extensions": "4.5.4" + } + }, + "Microsoft.VisualStudio.Threading.Analyzers": { + "type": "Transitive", + "resolved": "16.9.60", + "contentHash": "kbl+ra5Ao93lDar3A2vUSdfWiHMYBBsLM3Z6i/t6fH2iPHGyMTqvt3z20XCZ+L+1gcc8lpbhmkFS4rh+zwfsTg==" + }, + "Microsoft.VisualStudio.Validation": { + "type": "Transitive", + "resolved": "16.8.33", + "contentHash": "onzrXL8gsjht1knmmViGLTU3l1LIKoVLDL+gLN9Pdd+gclED9jLgxx/5X3mJHqETHMi7Va//hNCekiJ11LezSg==" + }, + "Microsoft.Win32.Primitives": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "9ZQKCWxH7Ijp9BfahvL2Zyf1cJIk8XYLF6Yjzr2yi0b2cOut/HQ31qf1ThHAgCc3WiZMdnWcfJCgN82/0UunxA==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Runtime": "4.3.0" + } + }, + "Microsoft.Win32.Registry": { + "type": "Transitive", + "resolved": "5.0.0", + "contentHash": "dDoKi0PnDz31yAyETfRntsLArTlVAVzUzCIvvEDsDsucrl33Dl8pIJG06ePTJTI3tGpeyHS9Cq7Foc/s4EeKcg==", + "dependencies": { + "System.Security.AccessControl": "5.0.0", + "System.Security.Principal.Windows": "5.0.0" + } + }, + "Nerdbank.Streams": { + "type": "Transitive", + "resolved": "2.6.81", + "contentHash": "htBHFE359qyyFwrvAGvFxrbBAoldZdl0XjtQdDWTJ8t5sWWs7QVXID5y1ZGJE61UgpV5CqWsj/NT0LOAn5GdZw==", + "dependencies": { + "Microsoft.Bcl.AsyncInterfaces": "1.1.1", + "Microsoft.VisualStudio.Threading": "16.7.56", + "Microsoft.VisualStudio.Validation": "15.5.31", + "System.IO.Pipelines": "4.7.2", + "System.Net.WebSockets": "4.3.0", + "System.Runtime.CompilerServices.Unsafe": "4.7.1" + } + }, + "Newtonsoft.Json": { + "type": "Transitive", + "resolved": "12.0.2", + "contentHash": "rTK0s2EKlfHsQsH6Yx2smvcTCeyoDNgCW7FEYyV01drPlh2T243PR2DiDXqtC5N4GDm4Ma/lkxfW5a/4793vbA==" + }, + "Perfolizer": { + "type": "Transitive", + "resolved": "0.2.1", + "contentHash": "Dt4aCxCT8NPtWBKA8k+FsN/RezOQ2C6omNGm5o/qmYRiIwlQYF93UgFmeF1ezVNsztTnkg7P5P63AE+uNkLfrw==", + "dependencies": { + "System.Memory": "4.5.3" + } + }, + "runtime.debian.8-x64.runtime.native.System.Security.Cryptography.OpenSsl": { + "type": "Transitive", + "resolved": "4.3.2", + "contentHash": "7VSGO0URRKoMEAq0Sc9cRz8mb6zbyx/BZDEWhgPdzzpmFhkam3fJ1DAGWFXBI4nGlma+uPKpfuMQP5LXRnOH5g==" + }, + "runtime.fedora.23-x64.runtime.native.System.Security.Cryptography.OpenSsl": { + "type": "Transitive", + "resolved": "4.3.2", + "contentHash": "0oAaTAm6e2oVH+/Zttt0cuhGaePQYKII1dY8iaqP7CvOpVKgLybKRFvQjXR2LtxXOXTVPNv14j0ot8uV+HrUmw==" + }, + "runtime.fedora.24-x64.runtime.native.System.Security.Cryptography.OpenSsl": { + "type": "Transitive", + "resolved": "4.3.2", + "contentHash": "G24ibsCNi5Kbz0oXWynBoRgtGvsw5ZSVEWjv13/KiCAM8C6wz9zzcCniMeQFIkJ2tasjo2kXlvlBZhplL51kGg==" + }, + "runtime.native.System": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "c/qWt2LieNZIj1jGnVNsE2Kl23Ya2aSTBuXMD6V7k9KWr6l16Tqdwq+hJScEpWER9753NWC8h96PaVNY5Ld7Jw==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0" + } + }, + "runtime.native.System.Net.Http": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "ZVuZJqnnegJhd2k/PtAbbIcZ3aZeITq3sj06oKfMBSfphW3HDmk/t4ObvbOk/JA/swGR0LNqMksAh/f7gpTROg==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0" + } + }, + "runtime.native.System.Security.Cryptography.Apple": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "DloMk88juo0OuOWr56QG7MNchmafTLYWvABy36izkrLI5VledI0rq28KGs1i9wbpeT9NPQrx/wTf8U2vazqQ3Q==", + "dependencies": { + "runtime.osx.10.10-x64.runtime.native.System.Security.Cryptography.Apple": "4.3.0" + } + }, + "runtime.native.System.Security.Cryptography.OpenSsl": { + "type": "Transitive", + "resolved": "4.3.2", + "contentHash": "QR1OwtwehHxSeQvZKXe+iSd+d3XZNkEcuWMFYa2i0aG1l+lR739HPicKMlTbJst3spmeekDVBUS7SeS26s4U/g==", + "dependencies": { + "runtime.debian.8-x64.runtime.native.System.Security.Cryptography.OpenSsl": "4.3.2", + "runtime.fedora.23-x64.runtime.native.System.Security.Cryptography.OpenSsl": "4.3.2", + "runtime.fedora.24-x64.runtime.native.System.Security.Cryptography.OpenSsl": "4.3.2", + "runtime.opensuse.13.2-x64.runtime.native.System.Security.Cryptography.OpenSsl": "4.3.2", + "runtime.opensuse.42.1-x64.runtime.native.System.Security.Cryptography.OpenSsl": "4.3.2", + "runtime.osx.10.10-x64.runtime.native.System.Security.Cryptography.OpenSsl": "4.3.2", + "runtime.rhel.7-x64.runtime.native.System.Security.Cryptography.OpenSsl": "4.3.2", + "runtime.ubuntu.14.04-x64.runtime.native.System.Security.Cryptography.OpenSsl": "4.3.2", + "runtime.ubuntu.16.04-x64.runtime.native.System.Security.Cryptography.OpenSsl": "4.3.2", + "runtime.ubuntu.16.10-x64.runtime.native.System.Security.Cryptography.OpenSsl": "4.3.2" + } + }, + "runtime.opensuse.13.2-x64.runtime.native.System.Security.Cryptography.OpenSsl": { + "type": "Transitive", + "resolved": "4.3.2", + "contentHash": "I+GNKGg2xCHueRd1m9PzeEW7WLbNNLznmTuEi8/vZX71HudUbx1UTwlGkiwMri7JLl8hGaIAWnA/GONhu+LOyQ==" + }, + "runtime.opensuse.42.1-x64.runtime.native.System.Security.Cryptography.OpenSsl": { + "type": "Transitive", + "resolved": "4.3.2", + "contentHash": "1Z3TAq1ytS1IBRtPXJvEUZdVsfWfeNEhBkbiOCGEl9wwAfsjP2lz3ZFDx5tq8p60/EqbS0HItG5piHuB71RjoA==" + }, + "runtime.osx.10.10-x64.runtime.native.System.Security.Cryptography.Apple": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "kVXCuMTrTlxq4XOOMAysuNwsXWpYeboGddNGpIgNSZmv1b6r/s/DPk0fYMB7Q5Qo4bY68o48jt4T4y5BVecbCQ==" + }, + "runtime.osx.10.10-x64.runtime.native.System.Security.Cryptography.OpenSsl": { + "type": "Transitive", + "resolved": "4.3.2", + "contentHash": "6mU/cVmmHtQiDXhnzUImxIcDL48GbTk+TsptXyJA+MIOG9LRjPoAQC/qBFB7X+UNyK86bmvGwC8t+M66wsYC8w==" + }, + "runtime.rhel.7-x64.runtime.native.System.Security.Cryptography.OpenSsl": { + "type": "Transitive", + "resolved": "4.3.2", + "contentHash": "vjwG0GGcTW/PPg6KVud8F9GLWYuAV1rrw1BKAqY0oh4jcUqg15oYF1+qkGR2x2ZHM4DQnWKQ7cJgYbfncz/lYg==" + }, + "runtime.ubuntu.14.04-x64.runtime.native.System.Security.Cryptography.OpenSsl": { + "type": "Transitive", + "resolved": "4.3.2", + "contentHash": "7KMFpTkHC/zoExs+PwP8jDCWcrK9H6L7soowT80CUx3e+nxP/AFnq0AQAW5W76z2WYbLAYCRyPfwYFG6zkvQRw==" + }, + "runtime.ubuntu.16.04-x64.runtime.native.System.Security.Cryptography.OpenSsl": { + "type": "Transitive", + "resolved": "4.3.2", + "contentHash": "xrlmRCnKZJLHxyyLIqkZjNXqgxnKdZxfItrPkjI+6pkRo5lHX8YvSZlWrSI5AVwLMi4HbNWP7064hcAWeZKp5w==" + }, + "runtime.ubuntu.16.10-x64.runtime.native.System.Security.Cryptography.OpenSsl": { + "type": "Transitive", + "resolved": "4.3.2", + "contentHash": "leXiwfiIkW7Gmn7cgnNcdtNAU70SjmKW3jxGj1iKHOvdn0zRWsgv/l2OJUO5zdGdiv2VRFnAsxxhDgMzofPdWg==" + }, + "SemanticVersioning": { + "type": "Transitive", + "resolved": "2.0.2", + "contentHash": "4EQgYdNZ92SyaO7YFk6olVnebF5V+jrHyMUjvPq89tLeMo8NSfgDF+6Zwq/lgh9j/0yfQp9Lkm0ZA0rUATCZFA==" + }, + "Serilog": { + "type": "Transitive", + "resolved": "2.8.0", + "contentHash": "zjuKXW5IQws43IHX7VY9nURsaCiBYh2kyJCWLJRSWrTsx/syBKHV8MibWe2A+QH3Er0AiwA+OJmO3DhFJDY1+A==", + "dependencies": { + "System.Collections.NonGeneric": "4.3.0" + } + }, + "SerilogTraceListener": { + "type": "Transitive", + "resolved": "3.2.1-dev-00011", + "contentHash": "Lcd96moPFhTzFOJR+EIxu0PSzZPPoX1BGNfpm7ArJ4/3MnMw3iTblEJBn8EpcSzS66DJyiy+WaXVkE7fuHhU3A==", + "dependencies": { + "Serilog": "2.8.0" + } + }, + "StreamJsonRpc": { + "type": "Transitive", + "resolved": "2.8.28", + "contentHash": "i2hKUXJSLEoWpPqQNyISqLDqmFHMiyasjTC/PrrHNWhQyauFeVoebSct3E4OTUzRC1DYjVJ9AMiVbp/uVYLnjQ==", + "dependencies": { + "MessagePack": "2.2.85", + "Microsoft.Bcl.AsyncInterfaces": "5.0.0", + "Microsoft.VisualStudio.Threading": "16.9.60", + "Nerdbank.Streams": "2.6.81", + "Newtonsoft.Json": "12.0.2", + "System.Collections.Immutable": "5.0.0", + "System.Diagnostics.DiagnosticSource": "5.0.1", + "System.IO.Pipelines": "5.0.1", + "System.Memory": "4.5.4", + "System.Net.Http": "4.3.4", + "System.Net.WebSockets": "4.3.0", + "System.Reflection.Emit": "4.7.0", + "System.Threading.Tasks.Dataflow": "5.0.0", + "System.Threading.Tasks.Extensions": "4.5.4" + } + }, + "System.CodeDom": { + "type": "Transitive", + "resolved": "6.0.0", + "contentHash": "CPc6tWO1LAer3IzfZufDBRL+UZQcj5uS207NHALQzP84Vp/z6wF0Aa0YZImOQY8iStY0A2zI/e3ihKNPfUm8XA==" + }, + "System.Collections": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "3Dcj85/TBdVpL5Zr+gEEBUuFe2icOnLalmEh9hfck1PTYbbyWuZgh4fmm2ysCLTrqLQw6t3TgTyJ+VLp+Qb+Lw==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Runtime": "4.3.0" + } + }, + "System.Collections.Concurrent": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "ztl69Xp0Y/UXCL+3v3tEU+lIy+bvjKNUmopn1wep/a291pVPK7dxBd6T7WnlQqRog+d1a/hSsgRsmFnIBKTPLQ==", + "dependencies": { + "System.Collections": "4.3.0", + "System.Diagnostics.Debug": "4.3.0", + "System.Diagnostics.Tracing": "4.3.0", + "System.Globalization": "4.3.0", + "System.Reflection": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Extensions": "4.3.0", + "System.Threading": "4.3.0", + "System.Threading.Tasks": "4.3.0" + } + }, + "System.Collections.Immutable": { + "type": "Transitive", + "resolved": "5.0.0", + "contentHash": "FXkLXiK0sVVewcso0imKQoOxjoPAj42R8HtjjbSjVPAzwDfzoyoznWxgA3c38LDbN9SJux1xXoXYAhz98j7r2g==" + }, + "System.Collections.NonGeneric": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "prtjIEMhGUnQq6RnPEYLpFt8AtLbp9yq2zxOSrY7KJJZrw25Fi97IzBqY7iqssbM61Ek5b8f3MG/sG1N2sN5KA==", + "dependencies": { + "System.Diagnostics.Debug": "4.3.0", + "System.Globalization": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Extensions": "4.3.0", + "System.Threading": "4.3.0" + } + }, + "System.Configuration.ConfigurationManager": { + "type": "Transitive", + "resolved": "4.4.0", + "contentHash": "gWwQv/Ug1qWJmHCmN17nAbxJYmQBM/E94QxKLksvUiiKB1Ld3Sc/eK1lgmbSjDFxkQhVuayI/cGFZhpBSodLrg==", + "dependencies": { + "System.Security.Cryptography.ProtectedData": "4.4.0" + } + }, + "System.Diagnostics.Debug": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "ZUhUOdqmaG5Jk3Xdb8xi5kIyQYAA4PnTNlHx1mu9ZY3qv4ELIdKbnL/akbGaKi2RnNUWaZsAs31rvzFdewTj2g==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Runtime": "4.3.0" + } + }, + "System.Diagnostics.DiagnosticSource": { + "type": "Transitive", + "resolved": "5.0.1", + "contentHash": "uXQEYqav2V3zP6OwkOKtLv+qIi6z3m1hsGyKwXX7ZA7htT4shoVccGxnJ9kVRFPNAsi1ArZTq2oh7WOto6GbkQ==" + }, + "System.Diagnostics.Tracing": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "rswfv0f/Cqkh78rA5S8eN8Neocz234+emGCtTF3lxPY96F+mmmUen6tbn0glN6PMvlKQb9bPAY5e9u7fgPTkKw==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Runtime": "4.3.0" + } + }, + "System.Globalization": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "kYdVd2f2PAdFGblzFswE4hkNANJBKRmsfa2X5LG2AcWE1c7/4t0pYae1L8vfZ5xvE2nK/R9JprtToA61OSHWIg==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Runtime": "4.3.0" + } + }, + "System.Globalization.Calendars": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "GUlBtdOWT4LTV3I+9/PJW+56AnnChTaOqqTLFtdmype/L500M2LIyXgmtd9X2P2VOkmJd5c67H5SaC2QcL1bFA==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Globalization": "4.3.0", + "System.Runtime": "4.3.0" + } + }, + "System.Globalization.Extensions": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "FhKmdR6MPG+pxow6wGtNAWdZh7noIOpdD5TwQ3CprzgIE1bBBoim0vbR1+AWsWjQmU7zXHgQo4TWSP6lCeiWcQ==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "System.Globalization": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Extensions": "4.3.0", + "System.Runtime.InteropServices": "4.3.0" + } + }, + "System.IO": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "3qjaHvxQPDpSOYICjUoTsmoq5u6QJAFRUITgeT/4gqkF1bajbSmb1kwSxEA8AHlofqgcKJcM8udgieRNhaJ5Cg==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Runtime": "4.3.0", + "System.Text.Encoding": "4.3.0", + "System.Threading.Tasks": "4.3.0" + } + }, + "System.IO.Abstractions": { + "type": "Transitive", + "resolved": "17.2.3", + "contentHash": "VcozGeE4SxIo0cnXrDHhbrh/Gb8KQnZ3BvMelvh+iw0PrIKtuuA46U2Xm4e4pgnaWFgT4RdZfTpWl/WPRdw0WQ==" + }, + "System.IO.FileSystem": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "3wEMARTnuio+ulnvi+hkRNROYwa1kylvYahhcLk4HSoVdl+xxTFVeVlYOfLwrDPImGls0mDqbMhrza8qnWPTdA==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.IO": "4.3.0", + "System.IO.FileSystem.Primitives": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Handles": "4.3.0", + "System.Text.Encoding": "4.3.0", + "System.Threading.Tasks": "4.3.0" + } + }, + "System.IO.FileSystem.Primitives": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "6QOb2XFLch7bEc4lIcJH49nJN2HV+OC3fHDgsLVsBVBk3Y4hFAnOBGzJ2lUu7CyDDFo9IBWkSsnbkT6IBwwiMw==", + "dependencies": { + "System.Runtime": "4.3.0" + } + }, + "System.IO.Pipelines": { + "type": "Transitive", + "resolved": "5.0.1", + "contentHash": "qEePWsaq9LoEEIqhbGe6D5J8c9IqQOUuTzzV6wn1POlfdLkJliZY3OlB0j0f17uMWlqZYjH7txj+2YbyrIA8Yg==" + }, + "System.Linq": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "5DbqIUpsDp0dFftytzuMmc0oeMdQwjcP/EWxsksIz/w1TcFRkZ3yKKz0PqiYFMmEwPSWw+qNVqD7PJ889JzHbw==", + "dependencies": { + "System.Collections": "4.3.0", + "System.Diagnostics.Debug": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Extensions": "4.3.0" + } + }, + "System.Management": { + "type": "Transitive", + "resolved": "6.0.0", + "contentHash": "sHsESYMmPDhQuOC66h6AEOs/XowzKsbT9srMbX71TCXP58hkpn1BqBjdmKj1+DCA/WlBETX1K5WjQHwmV0Txrg==", + "dependencies": { + "System.CodeDom": "6.0.0" + } + }, + "System.Memory": { + "type": "Transitive", + "resolved": "4.5.4", + "contentHash": "1MbJTHS1lZ4bS4FmsJjnuGJOu88ZzTT2rLvrhW7Ygic+pC0NWA+3hgAen0HRdsocuQXCkUTdFn9yHJJhsijDXw==" + }, + "System.Net.Http": { + "type": "Transitive", + "resolved": "4.3.4", + "contentHash": "aOa2d51SEbmM+H+Csw7yJOuNZoHkrP2XnAurye5HWYgGVVU54YZDvsLUYRv6h18X3sPnjNCANmN7ZhIPiqMcjA==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.1", + "System.Collections": "4.3.0", + "System.Diagnostics.Debug": "4.3.0", + "System.Diagnostics.DiagnosticSource": "4.3.0", + "System.Diagnostics.Tracing": "4.3.0", + "System.Globalization": "4.3.0", + "System.Globalization.Extensions": "4.3.0", + "System.IO": "4.3.0", + "System.IO.FileSystem": "4.3.0", + "System.Net.Primitives": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Extensions": "4.3.0", + "System.Runtime.Handles": "4.3.0", + "System.Runtime.InteropServices": "4.3.0", + "System.Security.Cryptography.Algorithms": "4.3.0", + "System.Security.Cryptography.Encoding": "4.3.0", + "System.Security.Cryptography.OpenSsl": "4.3.0", + "System.Security.Cryptography.Primitives": "4.3.0", + "System.Security.Cryptography.X509Certificates": "4.3.0", + "System.Text.Encoding": "4.3.0", + "System.Threading": "4.3.0", + "System.Threading.Tasks": "4.3.0", + "runtime.native.System": "4.3.0", + "runtime.native.System.Net.Http": "4.3.0", + "runtime.native.System.Security.Cryptography.OpenSsl": "4.3.2" + } + }, + "System.Net.Primitives": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "qOu+hDwFwoZPbzPvwut2qATe3ygjeQBDQj91xlsaqGFQUI5i4ZnZb8yyQuLGpDGivEPIt8EJkd1BVzVoP31FXA==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Runtime": "4.3.0", + "System.Runtime.Handles": "4.3.0" + } + }, + "System.Net.WebSockets": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "u6fFNY5q4T8KerUAVbya7bR6b7muBuSTAersyrihkcmE5QhEOiH3t5rh4il15SexbVlpXFHGuMwr/m8fDrnkQg==", + "dependencies": { + "Microsoft.Win32.Primitives": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Threading.Tasks": "4.3.0" + } + }, + "System.Reflection": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "KMiAFoW7MfJGa9nDFNcfu+FpEdiHpWgTcS2HdMpDvt9saK3y/G4GwprPyzqjFH9NTaGPQeWNHU+iDlDILj96aQ==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.IO": "4.3.0", + "System.Reflection.Primitives": "4.3.0", + "System.Runtime": "4.3.0" + } + }, + "System.Reflection.Emit": { + "type": "Transitive", + "resolved": "4.7.0", + "contentHash": "VR4kk8XLKebQ4MZuKuIni/7oh+QGFmZW3qORd1GvBq/8026OpW501SzT/oypwiQl4TvT8ErnReh/NzY9u+C6wQ==" + }, + "System.Reflection.Emit.Lightweight": { + "type": "Transitive", + "resolved": "4.7.0", + "contentHash": "a4OLB4IITxAXJeV74MDx49Oq2+PsF6Sml54XAFv+2RyWwtDBcabzoxiiJRhdhx+gaohLh4hEGCLQyBozXoQPqA==" + }, + "System.Reflection.Metadata": { + "type": "Transitive", + "resolved": "1.6.0", + "contentHash": "COC1aiAJjCoA5GBF+QKL2uLqEBew4JsCkQmoHKbN3TlOZKa2fKLz5CpiRQKDz0RsAOEGsVKqOD5bomsXq/4STQ==" + }, + "System.Reflection.Primitives": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "5RXItQz5As4xN2/YUDxdpsEkMhvw3e6aNveFXUn4Hl/udNTCNhnKp8lT9fnc3MhvGKh1baak5CovpuQUXHAlIA==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Runtime": "4.3.0" + } + }, + "System.Resources.ResourceManager": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "/zrcPkkWdZmI4F92gL/TPumP98AVDu/Wxr3CSJGQQ+XN6wbRZcyfSKVoPo17ilb3iOr0cCRqJInGwNMolqhS8A==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Globalization": "4.3.0", + "System.Reflection": "4.3.0", + "System.Runtime": "4.3.0" + } + }, + "System.Runtime": { + "type": "Transitive", + "resolved": "4.3.1", + "contentHash": "abhfv1dTK6NXOmu4bgHIONxHyEqFjW8HwXPmpY9gmll+ix9UNo4XDcmzJn6oLooftxNssVHdJC1pGT9jkSynQg==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.1", + "Microsoft.NETCore.Targets": "1.1.3" + } + }, + "System.Runtime.CompilerServices.Unsafe": { + "type": "Transitive", + "resolved": "5.0.0", + "contentHash": "ZD9TMpsmYJLrxbbmdvhwt9YEgG5WntEnZ/d1eH8JBX9LBp+Ju8BSBhUGbZMNVHHomWo2KVImJhTDl2hIgw/6MA==" + }, + "System.Runtime.Extensions": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "guW0uK0fn5fcJJ1tJVXYd7/1h5F+pea1r7FLSOz/f8vPEqbR2ZAknuRDvTQ8PzAilDveOxNjSfr0CHfIQfFk8g==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Runtime": "4.3.0" + } + }, + "System.Runtime.Handles": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "OKiSUN7DmTWeYb3l51A7EYaeNMnvxwE249YtZz7yooT4gOZhmTjIn48KgSsw2k2lYdLgTKNJw/ZIfSElwDRVgg==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Runtime": "4.3.0" + } + }, + "System.Runtime.InteropServices": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "uv1ynXqiMK8mp1GM3jDqPCFN66eJ5w5XNomaK2XD+TuCroNTLFGeZ+WCmBMcBDyTFKou3P6cR6J/QsaqDp7fGQ==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Reflection": "4.3.0", + "System.Reflection.Primitives": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Handles": "4.3.0" + } + }, + "System.Runtime.Numerics": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "yMH+MfdzHjy17l2KESnPiF2dwq7T+xLnSJar7slyimAkUh/gTrS9/UQOtv7xarskJ2/XDSNvfLGOBQPjL7PaHQ==", + "dependencies": { + "System.Globalization": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Extensions": "4.3.0" + } + }, + "System.Security.AccessControl": { + "type": "Transitive", + "resolved": "5.0.0", + "contentHash": "dagJ1mHZO3Ani8GH0PHpPEe/oYO+rVdbQjvjJkBRNQkX4t0r1iaeGn8+/ybkSLEan3/slM0t59SVdHzuHf2jmw==", + "dependencies": { + "Microsoft.NETCore.Platforms": "5.0.0", + "System.Security.Principal.Windows": "5.0.0" + } + }, + "System.Security.Cryptography.Algorithms": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "W1kd2Y8mYSCgc3ULTAZ0hOP2dSdG5YauTb1089T0/kRcN2MpSAW1izOFROrJgxSlMn3ArsgHXagigyi+ibhevg==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "System.Collections": "4.3.0", + "System.IO": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Extensions": "4.3.0", + "System.Runtime.Handles": "4.3.0", + "System.Runtime.InteropServices": "4.3.0", + "System.Runtime.Numerics": "4.3.0", + "System.Security.Cryptography.Encoding": "4.3.0", + "System.Security.Cryptography.Primitives": "4.3.0", + "System.Text.Encoding": "4.3.0", + "runtime.native.System.Security.Cryptography.Apple": "4.3.0", + "runtime.native.System.Security.Cryptography.OpenSsl": "4.3.0" + } + }, + "System.Security.Cryptography.Cng": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "03idZOqFlsKRL4W+LuCpJ6dBYDUWReug6lZjBa3uJWnk5sPCUXckocevTaUA8iT/MFSrY/2HXkOt753xQ/cf8g==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "System.IO": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Extensions": "4.3.0", + "System.Runtime.Handles": "4.3.0", + "System.Runtime.InteropServices": "4.3.0", + "System.Security.Cryptography.Algorithms": "4.3.0", + "System.Security.Cryptography.Encoding": "4.3.0", + "System.Security.Cryptography.Primitives": "4.3.0", + "System.Text.Encoding": "4.3.0" + } + }, + "System.Security.Cryptography.Csp": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "X4s/FCkEUnRGnwR3aSfVIkldBmtURMhmexALNTwpjklzxWU7yjMk7GHLKOZTNkgnWnE0q7+BCf9N2LVRWxewaA==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "System.IO": "4.3.0", + "System.Reflection": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Extensions": "4.3.0", + "System.Runtime.Handles": "4.3.0", + "System.Runtime.InteropServices": "4.3.0", + "System.Security.Cryptography.Algorithms": "4.3.0", + "System.Security.Cryptography.Encoding": "4.3.0", + "System.Security.Cryptography.Primitives": "4.3.0", + "System.Text.Encoding": "4.3.0", + "System.Threading": "4.3.0" + } + }, + "System.Security.Cryptography.Encoding": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "1DEWjZZly9ae9C79vFwqaO5kaOlI5q+3/55ohmq/7dpDyDfc8lYe7YVxJUZ5MF/NtbkRjwFRo14yM4OEo9EmDw==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "System.Collections": "4.3.0", + "System.Collections.Concurrent": "4.3.0", + "System.Linq": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Extensions": "4.3.0", + "System.Runtime.Handles": "4.3.0", + "System.Runtime.InteropServices": "4.3.0", + "System.Security.Cryptography.Primitives": "4.3.0", + "System.Text.Encoding": "4.3.0", + "runtime.native.System.Security.Cryptography.OpenSsl": "4.3.0" + } + }, + "System.Security.Cryptography.OpenSsl": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "h4CEgOgv5PKVF/HwaHzJRiVboL2THYCou97zpmhjghx5frc7fIvlkY1jL+lnIQyChrJDMNEXS6r7byGif8Cy4w==", + "dependencies": { + "System.Collections": "4.3.0", + "System.IO": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Extensions": "4.3.0", + "System.Runtime.Handles": "4.3.0", + "System.Runtime.InteropServices": "4.3.0", + "System.Runtime.Numerics": "4.3.0", + "System.Security.Cryptography.Algorithms": "4.3.0", + "System.Security.Cryptography.Encoding": "4.3.0", + "System.Security.Cryptography.Primitives": "4.3.0", + "System.Text.Encoding": "4.3.0", + "runtime.native.System.Security.Cryptography.OpenSsl": "4.3.0" + } + }, + "System.Security.Cryptography.Primitives": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "7bDIyVFNL/xKeFHjhobUAQqSpJq9YTOpbEs6mR233Et01STBMXNAc/V+BM6dwYGc95gVh/Zf+iVXWzj3mE8DWg==", + "dependencies": { + "System.Diagnostics.Debug": "4.3.0", + "System.Globalization": "4.3.0", + "System.IO": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Threading": "4.3.0", + "System.Threading.Tasks": "4.3.0" + } + }, + "System.Security.Cryptography.ProtectedData": { + "type": "Transitive", + "resolved": "4.4.0", + "contentHash": "cJV7ScGW7EhatRsjehfvvYVBvtiSMKgN8bOVI0bQhnF5bU7vnHVIsH49Kva7i7GWaWYvmEzkYVk1TC+gZYBEog==" + }, + "System.Security.Cryptography.X509Certificates": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "t2Tmu6Y2NtJ2um0RtcuhP7ZdNNxXEgUm2JeoA/0NvlMjAhKCnM1NX07TDl3244mVp3QU6LPEhT3HTtH1uF7IYw==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "System.Collections": "4.3.0", + "System.Diagnostics.Debug": "4.3.0", + "System.Globalization": "4.3.0", + "System.Globalization.Calendars": "4.3.0", + "System.IO": "4.3.0", + "System.IO.FileSystem": "4.3.0", + "System.IO.FileSystem.Primitives": "4.3.0", + "System.Resources.ResourceManager": "4.3.0", + "System.Runtime": "4.3.0", + "System.Runtime.Extensions": "4.3.0", + "System.Runtime.Handles": "4.3.0", + "System.Runtime.InteropServices": "4.3.0", + "System.Runtime.Numerics": "4.3.0", + "System.Security.Cryptography.Algorithms": "4.3.0", + "System.Security.Cryptography.Cng": "4.3.0", + "System.Security.Cryptography.Csp": "4.3.0", + "System.Security.Cryptography.Encoding": "4.3.0", + "System.Security.Cryptography.OpenSsl": "4.3.0", + "System.Security.Cryptography.Primitives": "4.3.0", + "System.Text.Encoding": "4.3.0", + "System.Threading": "4.3.0", + "runtime.native.System": "4.3.0", + "runtime.native.System.Net.Http": "4.3.0", + "runtime.native.System.Security.Cryptography.OpenSsl": "4.3.0" + } + }, + "System.Security.Principal.Windows": { + "type": "Transitive", + "resolved": "5.0.0", + "contentHash": "t0MGLukB5WAVU9bO3MGzvlGnyJPgUlcwerXn1kzBRjwLKixT96XV0Uza41W49gVd8zEMFu9vQEFlv0IOrytICA==" + }, + "System.Text.Encoding": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "BiIg+KWaSDOITze6jGQynxg64naAPtqGHBwDrLaCtixsa5bKiR8dpPOHA7ge3C0JJQizJE+sfkz1wV+BAKAYZw==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Runtime": "4.3.0" + } + }, + "System.Text.Encoding.CodePages": { + "type": "Transitive", + "resolved": "4.5.0", + "contentHash": "S0wEUiKcLvRlkFUXca8uio1UQ5bYQzYgOmOKtCqaBQC3GR9AJjh43otcM32IGsAyvadFTaAMw9Irm6dS4Evfng==", + "dependencies": { + "Microsoft.NETCore.Platforms": "2.0.0", + "System.Runtime.CompilerServices.Unsafe": "4.5.0" + } + }, + "System.Threading": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "VkUS0kOBcUf3Wwm0TSbrevDDZ6BlM+b/HRiapRFWjM5O0NS0LviG0glKmFK+hhPDd1XFeSdU1GmlLhb2CoVpIw==", + "dependencies": { + "System.Runtime": "4.3.0", + "System.Threading.Tasks": "4.3.0" + } + }, + "System.Threading.Tasks": { + "type": "Transitive", + "resolved": "4.3.0", + "contentHash": "LbSxKEdOUhVe8BezB/9uOGGppt+nZf6e1VFyw6v3DN6lqitm0OSn2uXMOdtP0M3W4iMcqcivm2J6UgqiwwnXiA==", + "dependencies": { + "Microsoft.NETCore.Platforms": "1.1.0", + "Microsoft.NETCore.Targets": "1.1.0", + "System.Runtime": "4.3.0" + } + }, + "System.Threading.Tasks.Dataflow": { + "type": "Transitive", + "resolved": "5.0.0", + "contentHash": "NBp0zSAMZp4muDje6XmbDfmkqw9+qsDCHp+YMEtnVgHEjQZ3Q7MzFTTp3eHqpExn4BwMrS7JkUVOTcVchig4Sw==" + }, + "System.Threading.Tasks.Extensions": { + "type": "Transitive", + "resolved": "4.5.4", + "contentHash": "zteT+G8xuGu6mS+mzDzYXbzS7rd3K6Fjb9RiZlYlJPam2/hU7JCBZBVEcywNuR+oZ1ncTvc/cq0faRr3P01OVg==" + }, + "Thoth.Json.Net": { + "type": "Transitive", + "resolved": "8.0.0", + "contentHash": "C/b+8g/xUTJTn7pbKC4bMAOy2tyolXAuHTXguT5TNzDKQ6sjnUfFa9B81fTt9PuUOdWFLyRKlXASuFhSQciJGQ==", + "dependencies": { + "FSharp.Core": "4.7.2", + "Fable.Core": "[3.0.0, 4.0.0)", + "Newtonsoft.Json": "11.0.2" + } + }, + "fantomas": { + "type": "Project", + "dependencies": { + "Argu": "[6.1.1, )", + "FSharp.Core": "[6.0.1, )", + "Fantomas.Client": "[1.0.0, )", + "Fantomas.Core": "[1.0.0, )", + "Ignore": "[0.1.46, )", + "SerilogTraceListener": "[3.2.1-dev-00011, )", + "StreamJsonRpc": "[2.8.28, )", + "System.IO.Abstractions": "[17.2.3, )", + "Thoth.Json.Net": "[8.0.0, )", + "editorconfig": "[0.13.0, )" + } + }, + "fantomas.client": { + "type": "Project", + "dependencies": { + "FSharp.Core": "[5.0.1, )", + "SemanticVersioning": "[2.0.2, )", + "StreamJsonRpc": "[2.8.28, )" + } + }, + "fantomas.core": { + "type": "Project", + "dependencies": { + "FSharp.Core": "[6.0.1, )", + "Fantomas.FCS": "[1.0.0, )" + } + }, + "fantomas.fcs": { + "type": "Project", + "dependencies": { + "FSharp.Core": "[6.0.1, )", + "System.Memory": "[4.5.4, )", + "System.Runtime": "[4.3.1, )" + } + } + } + } +} \ No newline at end of file diff --git a/src/Fantomas/Fantomas.fsproj b/src/Fantomas/Fantomas.fsproj index 9b5c233e04..26329b7b01 100644 --- a/src/Fantomas/Fantomas.fsproj +++ b/src/Fantomas/Fantomas.fsproj @@ -2,6 +2,7 @@ Exe net6.0 + true en diff --git a/src/Fantomas/Format.fs b/src/Fantomas/Format.fs index ee7e276eed..14671c23f9 100644 --- a/src/Fantomas/Format.fs +++ b/src/Fantomas/Format.fs @@ -81,9 +81,10 @@ let private formatFileInternalAsync (compareWithoutLineEndings: bool) (file: str if IgnoreFile.isIgnoredFile (IgnoreFile.current.Force()) file then async { return IgnoredFile file } else - let originalContent = File.ReadAllText file async { + let! originalContent = File.ReadAllTextAsync file |> Async.AwaitTask + let! formatted = originalContent |> formatContentInternalAsync compareWithoutLineEndings config file diff --git a/src/Fantomas/Program.fs b/src/Fantomas/Program.fs index b5dcdc247f..149a7ee8b9 100644 --- a/src/Fantomas/Program.fs +++ b/src/Fantomas/Program.fs @@ -6,6 +6,8 @@ open Fantomas.Daemon open Argu open System.Text open Fantomas.Format +open System.Threading.Tasks +open System.Runtime.ExceptionServices let extensions = set [| ".fs"; ".fsx"; ".fsi"; ".ml"; ".mli" |] @@ -16,6 +18,7 @@ type Arguments = | [] Out of string | [] Check | [] Daemon + | [] Parallel | [] Version | [] Input of string list @@ -35,13 +38,16 @@ type Arguments = sprintf "Input paths: can be multiple folders or files with %s extension." (Seq.map (fun s -> "*" + s) extensions |> String.concat ",") + | Parallel -> "Process files in parallel." -let time f = - let sw = Diagnostics.Stopwatch.StartNew() - let res = f () - sw.Stop() - printfn "Time taken: %O s" sw.Elapsed - res +let timeAsync f = + async { + let sw = Diagnostics.Stopwatch.StartNew() + let! res = f () + sw.Stop() + printfn "Time taken: %O s" sw.Elapsed + return res + } [] type InputPath = @@ -82,41 +88,46 @@ let rec allFiles isRec path = /// Fantomas assumes the input files are UTF-8 /// As is stated in F# language spec: https://fsharp.org/specs/language-spec/4.1/FSharpSpec-4.1-latest.pdf#page=25 let private hasByteOrderMark file = - if File.Exists(file) then - let preamble = Encoding.UTF8.GetPreamble() + async { + if File.Exists(file) then + let preamble = Encoding.UTF8.GetPreamble() - use file = new FileStream(file, FileMode.Open, FileAccess.Read) + use file = new FileStream(file, FileMode.Open, FileAccess.Read) - let mutable bom = Array.zeroCreate 3 - file.Read(bom, 0, 3) |> ignore - bom = preamble - else - false + let mutable bom = Array.zeroCreate 3 + do! file.ReadAsync(bom, 0, 3) |> Async.AwaitTask |> Async.Ignore + return bom = preamble + else + return false + } /// Format a source string using given config and write to a text writer let processSourceString (force: bool) s (fileName: string) config = let writeResult (formatted: string) = - if hasByteOrderMark fileName then - File.WriteAllText(fileName, formatted, Encoding.UTF8) - else - File.WriteAllText(fileName, formatted) + async { + let! hasBom = hasByteOrderMark fileName - printfn $"%s{fileName} has been written." + if hasBom then + do! File.WriteAllTextAsync(fileName, formatted, Encoding.UTF8) |> Async.AwaitTask + else + do! File.WriteAllTextAsync(fileName, formatted) |> Async.AwaitTask + + printfn $"%s{fileName} has been written." + } async { let! formatted = s |> Format.formatContentAsync config fileName match formatted with - | Format.FormatResult.Formatted(_, formattedContent) -> formattedContent |> writeResult + | Format.FormatResult.Formatted(_, formattedContent) -> do! formattedContent |> writeResult | Format.InvalidCode(file, formattedContent) when force -> printfn $"%s{file} was not valid after formatting." - formattedContent |> writeResult + do! formattedContent |> writeResult | Format.FormatResult.Unchanged file -> printfn $"'%s{file}' was unchanged" | Format.IgnoredFile file -> printfn $"'%s{file}' was ignored" | Format.FormatResult.Error(_, ex) -> raise ex | Format.InvalidCode(file, _) -> raise (exn $"Formatting {file} lead to invalid F# code") } - |> Async.RunSynchronously /// Format inFile and write to text writer let processSourceFile (force: bool) inFile (tw: TextWriter) = @@ -124,16 +135,17 @@ let processSourceFile (force: bool) inFile (tw: TextWriter) = let! formatted = Format.formatFileAsync inFile match formatted with - | Format.FormatResult.Formatted(_, formattedContent) -> tw.Write(formattedContent) + | Format.FormatResult.Formatted(_, formattedContent) -> do! tw.WriteAsync(formattedContent) |> Async.AwaitTask | Format.InvalidCode(file, formattedContent) when force -> printfn $"%s{file} was not valid after formatting." - tw.Write(formattedContent) - | Format.FormatResult.Unchanged _ -> inFile |> File.ReadAllText |> tw.Write + do! tw.WriteAsync(formattedContent) |> Async.AwaitTask + | Format.FormatResult.Unchanged _ -> + let! input = inFile |> File.ReadAllTextAsync |> Async.AwaitTask + do! input |> tw.WriteAsync |> Async.AwaitTask | Format.IgnoredFile file -> printfn $"'%s{file}' was ignored" | Format.FormatResult.Error(_, ex) -> raise ex | Format.InvalidCode(file, _) -> raise (exn $"Formatting {file} lead to invalid F# code") } - |> Async.RunSynchronously let private writeInColor consoleColor (content: string) = let currentColor = Console.ForegroundColor @@ -271,58 +283,70 @@ let main argv = let version = results.TryGetResult <@ Arguments.Version @> + let inline reraiseAsync (e: exn) = + let edi = ExceptionDispatchInfo.Capture e + edi.Throw() + let fileToFile (force: bool) (inFile: string) (outFile: string) = - try - printfn $"Processing %s{inFile}" - let hasByteOrderMark = hasByteOrderMark inFile - - use buffer = - if hasByteOrderMark then - new StreamWriter( - new FileStream(outFile, FileMode.OpenOrCreate, FileAccess.ReadWrite), - Encoding.UTF8 - ) + async { + try + printfn $"Processing %s{inFile}" + let! hasByteOrderMark = hasByteOrderMark inFile + + use buffer = + if hasByteOrderMark then + new StreamWriter( + new FileStream(outFile, FileMode.OpenOrCreate, FileAccess.ReadWrite), + Encoding.UTF8 + ) + else + new StreamWriter(outFile) + + if profile then + let! length = File.ReadAllLinesAsync(inFile) |> Async.AwaitTask + length |> Seq.length |> printfn "Line count: %i" + + do! timeAsync (fun () -> processSourceFile force inFile buffer) else - new StreamWriter(outFile) - - if profile then - File.ReadLines(inFile) |> Seq.length |> printfn "Line count: %i" - - time (fun () -> processSourceFile force inFile buffer) - else - processSourceFile force inFile buffer + do! processSourceFile force inFile buffer - buffer.Flush() - printfn "%s has been written." outFile - with exn -> - reraise () + buffer.Flush() + printfn "%s has been written." outFile + with exn -> + reraiseAsync exn + } let stringToFile (force: bool) (s: string) (outFile: string) config = - try - if profile then - printfn "Line count: %i" (s.Length - s.Replace(Environment.NewLine, "").Length) + async { + try + if profile then + printfn "Line count: %i" (s.Length - s.Replace(Environment.NewLine, "").Length) - time (fun () -> processSourceString force s outFile config) - else - processSourceString force s outFile config - with exn -> - reraise () + do! timeAsync (fun () -> processSourceString force s outFile config) + else + do! processSourceString force s outFile config + with exn -> + reraiseAsync exn + } let processFile force inputFile outputFile = - if inputFile <> outputFile then - fileToFile force inputFile outputFile - else - printfn "Processing %s" inputFile - let content = File.ReadAllText inputFile - let config = EditorConfig.readConfiguration inputFile - stringToFile force content inputFile config + async { + if inputFile <> outputFile then + return! fileToFile force inputFile outputFile + else + printfn "Processing %s" inputFile + let! content = File.ReadAllTextAsync inputFile |> Async.AwaitTask + let config = EditorConfig.readConfiguration inputFile + return! stringToFile force content inputFile config + } let processFolder force inputFolder outputFolder = if not <| Directory.Exists(outputFolder) then Directory.CreateDirectory(outputFolder) |> ignore allFiles recurse inputFolder - |> Seq.iter (fun i -> + |> Seq.toList + |> List.map (fun i -> // s supposes to have form s1/suffix let suffix = i.Substring(inputFolder.Length + 1) @@ -334,19 +358,32 @@ let main argv = processFile force i o) - let filesAndFolders force (files: string list) (folders: string list) : unit = - files - |> List.iter (fun file -> - if (IgnoreFile.isIgnoredFile (IgnoreFile.current.Force()) file) then - printfn "'%s' was ignored" file - else - processFile force file file) + let filesAndFolders force (files: string list) (folders: string list) = + let fileTasks = + files + |> List.map (fun file -> + if (IgnoreFile.isIgnoredFile (IgnoreFile.current.Force()) file) then + printfn "'%s' was ignored" file + async.Return() + else + processFile force file file) - folders |> List.iter (fun folder -> processFolder force folder folder) + let folderTasks = + folders |> List.collect (fun folder -> processFolder force folder folder) + + (fileTasks @ folderTasks) let check = results.Contains <@ Arguments.Check @> let isDaemon = results.Contains <@ Arguments.Daemon @> + let asyncRunner = + if results.Contains <@ Arguments.Parallel @> then + Async.Parallel + else + Async.Sequential + >> Async.Ignore + >> Async.RunSynchronously + if Option.isSome version then let version = CodeFormatter.GetVersion() printfn $"Fantomas v%s{version}" @@ -374,11 +411,12 @@ let main argv = exit 1 | InputPath.File f, _ when (IgnoreFile.isIgnoredFile (IgnoreFile.current.Force()) f) -> printfn "'%s' was ignored" f - | InputPath.Folder p1, OutputPath.NotKnown -> processFolder force p1 p1 - | InputPath.File p1, OutputPath.NotKnown -> processFile force p1 p1 - | InputPath.File p1, OutputPath.IO p2 -> processFile force p1 p2 - | InputPath.Folder p1, OutputPath.IO p2 -> processFolder force p1 p2 - | InputPath.Multiple(files, folders), OutputPath.NotKnown -> filesAndFolders force files folders + | InputPath.Folder p1, OutputPath.NotKnown -> processFolder force p1 p1 |> asyncRunner + | InputPath.File p1, OutputPath.NotKnown -> processFile force p1 p1 |> List.singleton |> asyncRunner + | InputPath.File p1, OutputPath.IO p2 -> processFile force p1 p2 |> List.singleton |> asyncRunner + | InputPath.Folder p1, OutputPath.IO p2 -> processFolder force p1 p2 |> asyncRunner + | InputPath.Multiple(files, folders), OutputPath.NotKnown -> + filesAndFolders force files folders |> asyncRunner | InputPath.Multiple _, OutputPath.IO _ -> eprintfn "Multiple input files are not supported with the --out flag." exit 1