在.NET Core CLI(dotnet build)下构建Mono.Options

3

我正在尝试在.NET Core下使用Mono.Options,并使用它的命令行工具。

我最初尝试通过在project.json文件中声明依赖关系,从NuGet加载它,但是dotnet restore抱怨该包与dnxcore50框架不兼容。²

因此,我决定尝试从源代码构建它。我在Mono.Options源代码中注意到它有一个PCL构建选项。想着PCL可能是一个足够接近.NET Core的近似版本,我尝试创建了一个启用该设置的DLL项目来构建它:

{
    "version": "0.0.0-d95ccb2ca5",
    "compilationOptions": {
        "emitEntryPoint": false,
        "define": [ "PCL" ],
    },

    "dependencies": {
        "NETStandard.Library": "1.0.0-rc2-23811"
    },

    "compile": [ "*.cs" ],

    "frameworks": {
        "dnxcore50": { }
    }
}

我将从上面链接下载的 Options.cs 文件副本放置在同一目录下并输入 dotnet build 命令,结果出现以下错误:

.../Mono/Options.cs(137,22): error CS0234: The
type or namespace name 'Serialization' does not exist in the namespace
'System.Runtime' (are you missing an assembly reference?)
.../Mono/Options.cs(729,27): error CS0246: The
type or namespace name 'KeyedCollection<,>' could not be found (are you
missing a using directive or an assembly reference?)

我有几个问题:

...还有其他一些错误都源自这两个关键错误。

  1. Why is System.Runtime.Serialization missing? According to the docs, it is supposed to be part of .NET Core.

  2. I later added explicit dependencies for the parent packages of the two namespaces the compiler is complaining about:

    ...
    "frameworks": {
        "dotnet5.4": {
            "dependencies": {
                "System.ObjectModel": "4.0.*",
                "System.Runtime": "4.1.0-rc2-23811"
            }
        }
    }
    

    dotnet restore then succeeds, and most of the build errors go away, but the first error about Serialization continues to occur. Is .NET Core simply incomplete at this time?

  3. Is there a workaround other than just waiting for this class to be ported over?

  4. I used dnxcore50 in the initial project file because that's how dotnet new generated it. The change to dotnet5.4 seems to be necessary according to the ASP.NET 5 package search engine, but is that change kosher with .NET Core?³


侧记

  1. 为什么? 因为现在是 2016 年,然而 .NET 仍未加入命令行选项解析。真让人恼火。或许微软收购 Xamarin 将会使 Mono.Options 被包含进 .NET Core 中。与此同时...

  2. Mono.Options 4.2.2.1 — 在这个问题被提出后发布 — 解决了这个兼容性问题。

  3. ASP.NET 5 的软件包搜索结果表明 netcore50 也应该对我的目的有效,但随后我收到有关 no run-time assembly compatible with osx.10.10-x64 的投诉。

    这是在一台安装了 Mono 4.2.1 的 OS X 10.10 机器上发生的。很显然,Mono.Options 确实可以在该版本下构建。我提出了这个问题是因为我正在尝试将一些更简单的现有项目切换到这个新的、更轻量级的运行时。


2
微软现在提供 https://www.nuget.org/packages/Microsoft.Extensions.CommandLineUtils/ 。这里有一个有用的文档 https://msdn.microsoft.com/en-us/magazine/mt763239.aspx。 - Smartkid
@Smartkid:谢谢!虽然晚了11年,但终于来了。 :) - Warren Young
3个回答

1
System.Runtime.Serialization 机制已被 有意地从.NET Core中删除。(请向下滚动到“二进制序列化”部分。) 幸运的是,当您在PCL模式下构建时,Mono.Options实际上并未使用该接口,因此修复很简单:将using System.Runtime.Serialization行向下移动几行,放在#else子句中,这样在定义PCL时就不会看到它。
如果可能的话,请避免使用RC2。它仍在开发中,我在GitHub上看到了几个问题。
一旦使用RC1,您可以使用http://packagesearch.azurewebsites.net来查找RC1中缺少的软件包及其版本。
最好针对特定的.NET平台标准进行构建,而不是针对单个配置文件进行构建,例如RC1中的5.4(RC2中为1.3)。
至于您的其他问题,
  • 已经有许多开源的命令行解析库,因此微软不会强制你使用其中任何一个。
  • .NET Core与.NET Framework和Mono具有不同的设计。因此,迁移过程可能会很困难,但当微软拥有所有工具链时,可以轻松解决这些问题。等待并耐心等待。

关于包搜索:这是一个很有用的工具,谢谢!根据它的提示,我按照编辑后的问题更新了项目文件,但“Serialization”问题仍然存在。有什么建议吗? - Warren Young
关于命令行解析库:我并不要求微软“强制”我使用他们的库。我只是认为,如果微软提供了一个标准实现,我们就会少很多重复造轮子的情况;肯定会花费更少的时间去追踪 NuGet 包,并处理非 MSDN 文档的质量普遍较低的问题。在 POSIX 平台上存在 getopt(3),这使得这些平台上的命令行解析库数量较少。“足够好且预安装”的方案总是胜过第三方库。 - Warren Young
关于RC2:我使用的许多软件都有开放的Github问题。如果您知道与此问题相关的特定问题,请指出。在那之前,我会相信微软使用“RC”的方式与其他软件世界一样,意味着“发布候选版”,暗示“功能完成但可能存在错误”,其中RC2比RC1更少出现错误。 - Warren Young
@WarrenYoung MSDN博客文章解释了序列化部分。 - Lex Li
确实如此!我已经编辑了您的答案,并提供了解决问题的明确方案。(我将会向 Mono.Options 的维护者反馈他们代码中的错误。 :) ) - Warren Young

1

您是否已经更新到最新版本:4.2.2?这是现在的PCL程序集,应该支持所有.NET平台,包括.NETCore4.5。

除了支持更多平台外,此版本还允许对参数进行基本类型转换。唯一的限制是不支持操作,但所有操作都是支持的。

这些都是在此PR中完成的:https://github.com/mono/mono/pull/2662


问题在Options.cs文件的第137行的 using System.Runtime.Serialization语句上。在PCL模式下,Options.cs并没有实际使用该命名空间(请参见下面被ifdef掉的“Serializable”内容),因此,如果将其移动到#else块中的下面约4行,Options.cs将直接在.NET Core构建,而不是通过NuGet从.NET Core项目中可引用。我已经通过nuget.org的反馈机制向项目维护者发送了电子邮件。 - Warren Young
我是其中一个维护者。我会更新源代码。感谢您让我们知道。当被引用时,这个组装是否工作?对 Mono 的 PR 需要一些时间 :) - Matthew
刚刚更新了Mono.Options到v4.2.2.1版本:https://www.nuget.org/packages/Mono.Options/4.2.2.1 这应该解决了问题。 - Matthew
我尝试使用F#控制台应用程序,一切都应该在那里 :) 你可能需要手动添加“System.ObjectModel”:“4.0.0.0”依赖项... - Matthew
1
验证通过!谢谢! - Warren Young
显示剩余2条评论

0

文档在技术上并没有错误。在.NET Core 1.0 RC2中,System.Runtime.Serialization命名空间仍然存在,但由于二进制序列化的删除,命名空间的顶层现在几乎为空。这就是为什么即使明确依赖于System.Runtimeusing System.Runtime.Serialization行也会失败的原因。

链接文档页面上的所有类型都在.NET Core的Primitives子命名空间中实现。因此,将以下内容添加到您的project.json文件中也将允许using语句成功:

"System.Runtime.Serialization.Primitives": "4.1.0-beta-23516"

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接