【发布时间】:2015-07-30 22:03:02
【问题描述】:
我在下面有一个非常简单的组件。我正在尝试使用 Mono.Cecil 对其进行反思,以找到传递给所有 CallApiAsync 调用的参数。当我
隔离调用的 MethodReference 我似乎无法获得参数 x.GetResponse(new SomeRequestType()),我只获得了委托定义 ApiMethodAsync<T, TResult>。我对此一无所知,任何帮助表示赞赏。
public class ApiWrapper
{
public delegate Task<TResult> ApiMethodAsync<T, TResult>(T api);
public virtual async Task<SomeResponseType> MakeSomeRequestToApi()
{
return await CallApiAsync<ISomeApi, SomeResponseType>(x => x.GetResponse(new SomeRequestType()));
}
public virtual async Task<TResult> CallApiAsync<T, TResult>(ApiMethodAsync<T, TResult> apiMethod) where TResult : new()
{
return await Task.FromResult(new TResult());
}
}
public interface ISomeApi
{
Task<SomeResponseType> GetResponse(SomeRequestType request);
}
public class SomeResponseType { }
public class SomeRequestType { }
下面是我用来识别对 CallApiAsync 的调用的 Mono Cecil 代码
var moduleDefinition = ModuleDefinition.ReadModule("SimpleAssembly.dll");
var targetClass = moduleDefinition.Types.Where(t => t.FullName.Contains("ApiWrapper")).Single();
var nestedMethodInstructions = targetClass.NestedTypes
.SelectMany(p => p.Methods)
.Where(m => m.HasBody)
.SelectMany(t => t.Body.Instructions).ToList();
foreach (var instr in nestedMethodInstructions)
{
if (instr.Operand != null)
{
var methodRef = instr.Operand as MethodReference;
if (methodRef != null && methodRef.FullName.Contains("CallApiAsync"))
{
// Get the full delegate parameter, ie GetResponse(new SomeRequestType())
}
}
}
【问题讨论】:
-
所以让我直说吧;你想拦截对
CallApiAsync方法的所有调用并保存传递给它的参数吗? -
是的,我想捕获通用参数和作为参数传入的 lambda 表达式
标签: reflection delegates mono.cecil