-
Notifications
You must be signed in to change notification settings - Fork 268
/
Copy pathRaiseEventWrapper.cs
49 lines (40 loc) · 1.99 KB
/
RaiseEventWrapper.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
using System.Reflection;
using NSubstitute.Exceptions;
namespace NSubstitute.Core.Events;
public abstract class RaiseEventWrapper
{
protected abstract object?[] WorkOutRequiredArguments(ICall call);
protected abstract string RaiseMethodName { get; }
protected EventArgs GetDefaultForEventArgType(Type type)
{
if (type == typeof(EventArgs)) return EventArgs.Empty;
var defaultConstructor = GetPublicDefaultConstructor(type) ?? GetInternalDefaultConstructor(type);
if (defaultConstructor is null)
{
var message = string.Format(
"Cannot create {0} for this event as it has no default constructor. " +
"Provide arguments for this event by calling {1}({0})."
, type.Name, RaiseMethodName);
throw new CannotCreateEventArgsException(message);
}
return (EventArgs)defaultConstructor.Invoke([]);
}
private static ConstructorInfo? GetInternalDefaultConstructor(Type type)
{
var nonPublicDefaultConstructor = GetNonPublicDefaultConstructor(type);
var isInternalDefaultConstructor = nonPublicDefaultConstructor?.IsAssembly == true;
return isInternalDefaultConstructor ? nonPublicDefaultConstructor : null;
}
private static ConstructorInfo? GetPublicDefaultConstructor(Type type)
=> GetDefaultConstructor(type, BindingFlags.Public);
private static ConstructorInfo? GetNonPublicDefaultConstructor(Type type)
=> GetDefaultConstructor(type, BindingFlags.NonPublic);
private static ConstructorInfo? GetDefaultConstructor(Type type, BindingFlags bindingFlags)
=> type.GetConstructor(
BindingFlags.Instance | BindingFlags.ExactBinding | bindingFlags, null, Type.EmptyTypes, null);
protected static void RaiseEvent(RaiseEventWrapper wrapper)
{
var context = SubstitutionContext.Current;
context.ThreadContext.SetPendingRaisingEventArgumentsFactory(call => wrapper.WorkOutRequiredArguments(call));
}
}