【问题标题】:Compatibility shim used by .NET Standard 2.0.NET Standard 2.0 使用的兼容性填充程序
【发布时间】:2017-06-09 18:54:38
【问题描述】:

.NET Standard 2.0 的概述 (example) 说它现在使用某种兼容性填充程序来修复第三方库的兼容性问题。因此,您可以将第三方库与 .NET Standard 一起使用,直到它不使用 .NET Standard 所没有的任何 API。

不清楚的是

  • 这个垫片是如何工作的?有什么缺点吗?

  • 如何检查是否支持第三方库?通过直接将其添加到项目中,然后尝试编译?

【问题讨论】:

  • @leppie 评论不是为了回答 :)

标签: .net-core .net-standard


【解决方案1】:

这是通过创建经典 .NET 库引用的所有必要库来实现的。

例如在 .NET Core 中,ObjectAttribute 的实现在 System.Runtime 中定义。编译代码时,生成的代码始终引用程序集和类型 => [System.Runtime]System.Object。然而,经典 .NET 项目从 mscorlib 引用 System.Object。当尝试在 .NET Core 1.0/1.1 上使用经典的 .NET 程序集时,这通常会导致找不到类型。在 .NET Core 2.0 中,mscorlib 中会有“假”类型,运行时知道如何转发到实际的实现位置。

您可以阅读更多关于assembly unification works on the dotnet/standard GitHub repo 的信息,但最重要的场景是这样的(图片取自此存储库):

这显示了场景应该如何工作:当第 3 方 dll 引用 [mscorlib]Microsoft.Win32.RegistryKey 时,将有一个 mscorlib.dll 包含一个转发到 [Microsoft.Win32.Registry] Microsoft.Win32.RegistryKey 的类型,因此当存在 Microsoft.Win32.RegistryKey.dll 时它会工作.

这也显示了主要的缺点:注册表是一个仅限 Windows 的概念,在 Mac 或 Linux 上不可用,因此此特定代码可能无法在非 Windows 平台上运行。但如果您只使用库中不使用此功能的部分,它可能适用于跨平台场景。

另一个问题是,即使 API 是“可用于”编译和引用的,它仍然可能抛出 PlatformNotSupportedException

例如,实现序列化/反序列化文件格式的库无需修改即可工作,即使它是为 .NET Framework 3.5 构建的。

要查找特定库使用的 API 函数,.NET Portability Analyzer 可用于扫描 dll 并显示该库是否兼容,如果不兼容,哪些 API 被阻塞。

【讨论】:

  • 我如何注意到引用的 .NET Framework 库是否与 .NET Standard 兼容?是编译时错误还是运行时错误?
猜你喜欢
  • 1970-01-01
  • 2021-11-16
  • 1970-01-01
  • 2023-02-01
  • 1970-01-01
  • 2018-11-19
  • 2023-03-16
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多