Skip to content

Commit b20c910

Browse files
authored
Merge pull request #75 from lofcz/master
Check whether extension method is defined and no overload found
2 parents 47496ec + 9b74422 commit b20c910

File tree

1 file changed

+35
-0
lines changed

1 file changed

+35
-0
lines changed

CodingSeb.ExpressionEvaluator/ExpressionEvaluator.cs

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818
using System.Runtime.InteropServices;
1919
using System.Text;
2020
using System.Text.RegularExpressions;
21+
using System.Runtime.CompilerServices;
2122

2223
namespace CodingSeb.ExpressionEvaluator
2324
{
@@ -836,6 +837,13 @@ public bool OptionNewFunctionEvaluationActive
836837
/// </summary>
837838
public bool OptionAllowNonPublicMembersAccess { get; set; }
838839

840+
/// <summary>
841+
/// If <c>true</c> On unsuccessful call to an extension method, all defined overloads of that method are detected to resolve whether method is defined and called with wrong arguments or method is not defined.
842+
/// If <c>false</c> Unsucessful call to an extension method will always result in "Method {name} is not defined on type {type}"
843+
/// Default : true
844+
/// </summary>
845+
public bool OptionDetectExtensionMethodsOverloadsOnExtensionMethodNotFound { get; set; } = true;
846+
839847
#endregion
840848

841849
#region Reflection flags
@@ -1954,6 +1962,33 @@ protected virtual bool EvaluateVarOrFunc(string expression, Stack<object> stack,
19541962
}
19551963
else
19561964
{
1965+
if (OptionDetectExtensionMethodsOverloadsOnExtensionMethodNotFound)
1966+
{
1967+
IEnumerable<MethodInfo> query = from type in StaticTypesForExtensionsMethods
1968+
where
1969+
!type.IsGenericType &&
1970+
type.IsSealed &&
1971+
!type.IsNested
1972+
from method in type.GetMethods(BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic)
1973+
where method.IsDefined(typeof(ExtensionAttribute), false)
1974+
where method.GetParameters()[0].ParameterType == objType // static extMethod(this outType, ...)
1975+
select method;
1976+
1977+
if (query.Any())
1978+
{
1979+
string fnArgsPrint = string.Join(",", funcArgs);
1980+
string fnOverloadsPrint = "";
1981+
1982+
foreach (MethodInfo mi in query)
1983+
{
1984+
ParameterInfo[] parInfo = mi.GetParameters();
1985+
fnOverloadsPrint += string.Join(",", parInfo.Select(x => x.ParameterType.FullName ?? x.ParameterType.Name)) + "\n";
1986+
}
1987+
1988+
throw new ExpressionEvaluatorSyntaxErrorException($"[{objType}] extension method \"{varFuncName}\" has no overload for arguments: {fnArgsPrint}. Candidates: {fnOverloadsPrint}");
1989+
}
1990+
}
1991+
19571992
throw new ExpressionEvaluatorSyntaxErrorException($"[{objType}] object has no Method named \"{varFuncName}\".");
19581993
}
19591994
}

0 commit comments

Comments
 (0)