c# - 如何查看 .NET IServiceProvider 可以提供的所有服务?

标签 c# .net

这是关于 .NET 的一般性问题

我得到了一个 IServiceProvider 的实例接口(interface),但我几乎没有关于从中可以得到什么的文档。我如何找到它可能提供的所有服务的列表?

最佳答案

更新:本文最初写于 2015 年,此后情况发生了变化。如果您在阅读时仍然接受此答案,请参阅下面的其他答案。


System.IServiceProvider有一个方法 .GetService(Type),它返回一个服务。它本质上是一个从类型到服务的映射。对您的问题至关重要的是,它提供对所有 key 的访问,可能是因为它旨在通过网络实现。

实现接口(interface)的类来公开允许发现它提供的服务的方法或属性 - 没有通用的方法可以单独使用接口(interface)查看所有提供的服务.

解决方案:

  • 如果您可以控制服务提供商的来源,请制作一个允许您想要的子界面

      interface IBetterServiceProvider : System.IServiceProvider
         {
             IList<object> GetAllServices();
             IList<Type> GetAllServicedTypes();
         }
    

    并让您的服务实现它。

  • 如果您不能控制服务提供者的来源,要么强制转换为IServiceProvider 实现类型,要么使用反射来查找属性或告诉你你想要什么的方法。如果您正在使用的提供程序中似乎有一种一致的 .GetServices() 方法,那么您可以使用动态调度 1 , 2 , 3 无需强制转换即可访问该方法。


也就是说,即使是 Microsoft 自己的类实现也有点像兔子洞。引用文档,

The IServiceProvider interface is implemented by a number of types, including System.Web.HttpContext, System.ComponentModel.LicenseContext, System.ComponentModel.MarshalByValueComponent, and System.ComponentModel.Design.ServiceContainer.

  • HttpContext 实现接口(interface),但 GetService(Type) 方法被记录为仅供内部使用,并且它包含的唯一服务(在公共(public) API 中, 至少) 是 PageInstrumentation .无法在此实现中查询所有服务。

  • ServiceContainer实际上并没有实现该接口(interface)(虽然它确实有一个该接口(interface)类型的 internal field。)即使 ServiceContainer 没有实现该接口(interface),它 确实实现了该方法,并且it's a bit scary .它确实证实了怀疑——它是一个美化的字典,将类型映射到服务。同样,这个实现没有提供自己的方式来获取它拥有的所有服务。这是我所期望的,因为它明确地是一个服务容器。

  • LicenseContext.GetService(类型) just returns null unless its overridden.也许这个类的一些子类提供了一种获取所有服务的方法,但这个没有。

我已经完成了对源代码和文档的挖掘。它看起来有点困惑,但上面的简短答案是:旧名称或新名称,伪实现或实际实现:没有办法单独从 IServiceProvider 接口(interface)获取所有服务,并且 Microsoft 的实现都没有我发现也为您提供了一种方法。

关于c# - 如何查看 .NET IServiceProvider 可以提供的所有服务?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33943876/

相关文章:

c# - 使用 Visual Studio Code 创建 C# .sln 文件

c# - 在 WCF 服务上启用 CORS。获取 HTTP 405 : Method Not Allowed

c# - 在使用 LINQ 时,我们是否为了实现代码可读性而牺牲了性能?

c# - (276/304)*304 的小数舍入关闭

c# - 多行文本作为 Windows 窗体中的按钮标签

c# - 如何将 vb .net 函数转换为 c#?

.net - 有关调试器使用的调试引擎的信息

c# - 这里用checked有什么意义

c# - 使用 CodeDom 指定类型别名

C#:在 GPU 上执行操作,而不是 CPU(计算 Pi)