如何排查C#依赖注入中自定义服务的请求注入来源?
调试C#依赖注入中服务的请求来源
方法1:用调试调用栈直接追踪(最省心)
在MyCustomService的构造函数里打断点,程序命中后看「调用栈(Call Stack)」窗口:
- 往上翻调用链,跳过
Microsoft.Extensions.DependencyInjection开头的框架代码,找到业务层的调用,就能看到是哪个类(比如SomeOtherThing)的构造函数在请求注入 - 直接看调用栈里的类型名就行,一目了然
方法2:注入IServiceProvider查看上下文
如果调用栈信息不够明确,修改MyCustomService的构造函数,把IServiceProvider传进来,然后调试时看它的内部状态:
public class MyCustomService { public MyCustomService(IServiceProvider serviceProvider) { // 断点打这里,在Visual Studio的「局部变量」窗口展开serviceProvider // 找内部的`_scope`或`_rootProvider`字段,里面会保存当前正在解析的服务类型,就是请求你的消费者 } }
注:这个方法依赖DI容器的内部实现,不同版本的微软DI可能结构不一样,优先用方法1。
方法3:自定义注册逻辑拦截追踪
如果需要批量记录所有请求,替换原来的服务注册代码,加个拦截逻辑:
// 替换原来的services.AddTransient<MyCustomService>(); services.AddTransient<MyCustomService>(sp => { // 通过反射拿到当前正在解析的服务类型 var consumerType = GetCurrentResolvingService(sp); Console.WriteLine($"MyCustomService被{consumerType?.Name}请求注入"); return new MyCustomService(); }); // 辅助方法:针对微软DI的内部结构写的反射逻辑 private static Type GetCurrentResolvingService(IServiceProvider sp) { var scopeField = sp.GetType().GetField("_scope", BindingFlags.NonPublic | BindingFlags.Instance); var scope = scopeField?.GetValue(sp); var resolvingField = scope?.GetType().GetField("_resolvingService", BindingFlags.NonPublic | BindingFlags.Instance); return resolvingField?.GetValue(scope) as Type; }
注意:这个方法依赖DI框架的私有字段,框架升级后可能失效,只用来临时调试就行。
内容的提问来源于stack exchange,提问作者devlop
相关产品推荐
相关产品推荐

