<PackageReference Include="Castle.Core" Version="5.1.0" />

AbstractInvocation

public abstract class AbstractInvocation : IInvocation
using System; using System.Reflection; namespace Castle.DynamicProxy { public abstract class AbstractInvocation : IInvocation { private sealed class ProceedInfo : IInvocationProceedInfo { private readonly AbstractInvocation invocation; private readonly int interceptorIndex; public ProceedInfo(AbstractInvocation invocation) { this.invocation = invocation; interceptorIndex = invocation.currentInterceptorIndex; } public void Invoke() { int currentInterceptorIndex = invocation.currentInterceptorIndex; try { invocation.currentInterceptorIndex = interceptorIndex; invocation.Proceed(); } finally { invocation.currentInterceptorIndex = currentInterceptorIndex; } } } private readonly IInterceptor[] interceptors; private readonly object[] arguments; private int currentInterceptorIndex = -1; private Type[] genericMethodArguments; private readonly MethodInfo proxiedMethod; protected readonly object proxyObject; public abstract object InvocationTarget { get; } public abstract Type TargetType { get; } public abstract MethodInfo MethodInvocationTarget { get; } public Type[] GenericArguments => genericMethodArguments; public object Proxy => proxyObject; public MethodInfo Method => proxiedMethod; public object ReturnValue { get; set; } public object[] Arguments => arguments; protected AbstractInvocation(object proxy, IInterceptor[] interceptors, MethodInfo proxiedMethod, object[] arguments) { proxyObject = proxy; this.interceptors = interceptors; this.proxiedMethod = proxiedMethod; this.arguments = arguments; } public void SetGenericMethodArguments(Type[] arguments) { genericMethodArguments = arguments; } public MethodInfo GetConcreteMethod() { return EnsureClosedMethod(Method); } public MethodInfo GetConcreteMethodInvocationTarget() { get; } public void SetArgumentValue(int index, object value) { arguments[index] = value; } public object GetArgumentValue(int index) { return arguments[index]; } public void Proceed() { if (interceptors == null) InvokeMethodOnTarget(); else { currentInterceptorIndex++; try { if (currentInterceptorIndex == interceptors.Length) InvokeMethodOnTarget(); else { if (currentInterceptorIndex > interceptors.Length) throw new InvalidOperationException("Cannot proceed past the end of the interception pipeline. This likely signifies a bug in the calling code."); interceptors[currentInterceptorIndex].Intercept(this); } } finally { currentInterceptorIndex--; } } } public IInvocationProceedInfo CaptureProceedInfo() { return new ProceedInfo(this); } protected abstract void InvokeMethodOnTarget(); protected void ThrowOnNoTarget() { string text = (interceptors.Length != 0) ? "The interceptor attempted to 'Proceed'" : "There are no interceptors specified"; string text2; string text3; if (Method.DeclaringType.IsClass && Method.IsAbstract) { text2 = "is abstract"; text3 = "an abstract method"; } else { text2 = "has no target"; text3 = "method without target"; } throw new NotImplementedException($"""{text}""{Method}""{text2}""{text3}"""); } private MethodInfo EnsureClosedMethod(MethodInfo method) { if (method.ContainsGenericParameters) return method.GetGenericMethodDefinition().MakeGenericMethod(genericMethodArguments); return method; } } }