From 084e294c038a49094941f93d47025ef64e7189f9 Mon Sep 17 00:00:00 2001
From: metoule <m520152112e@gmail.com>
Date: Sun, 18 Aug 2024 18:26:03 +0200
Subject: [PATCH] Extract LateBinders

---
 src/DynamicExpresso.Core/Parsing/Parser.cs    | 70 ------------------
 .../Resolution/LateBinders.cs                 | 71 +++++++++++++++++++
 2 files changed, 71 insertions(+), 70 deletions(-)
 create mode 100644 src/DynamicExpresso.Core/Resolution/LateBinders.cs

diff --git a/src/DynamicExpresso.Core/Parsing/Parser.cs b/src/DynamicExpresso.Core/Parsing/Parser.cs
index df5050a..282526e 100644
--- a/src/DynamicExpresso.Core/Parsing/Parser.cs
+++ b/src/DynamicExpresso.Core/Parsing/Parser.cs
@@ -1,14 +1,10 @@
 using System;
 using System.Collections;
 using System.Collections.Generic;
-using System.Collections.ObjectModel;
-using System.Dynamic;
 using System.Globalization;
 using System.Linq;
 using System.Linq.Expressions;
 using System.Reflection;
-using System.Runtime.CompilerServices;
-using System.Security;
 using System.Text;
 using DynamicExpresso.Exceptions;
 using DynamicExpresso.Reflection;
@@ -2590,71 +2586,5 @@ private static Expression GenerateNullableTypeConversion(Expression expr)
 			var conversionType = typeof(Nullable<>).MakeGenericType(exprType);
 			return Expression.ConvertChecked(expr, conversionType);
 		}
-
-		/// <summary>
-		/// Binds to a member access of an instance as late as possible.  This allows the use of anonymous types on dynamic values.
-		/// </summary>
-		private class LateGetMemberCallSiteBinder : CallSiteBinder
-		{
-			private readonly string _propertyOrFieldName;
-
-			public LateGetMemberCallSiteBinder(string propertyOrFieldName)
-			{
-				_propertyOrFieldName = propertyOrFieldName;
-			}
-
-			public override Expression Bind(object[] args, ReadOnlyCollection<ParameterExpression> parameters, LabelTarget returnLabel)
-			{
-				var binder = Microsoft.CSharp.RuntimeBinder.Binder.GetMember(
-					Microsoft.CSharp.RuntimeBinder.CSharpBinderFlags.None,
-					_propertyOrFieldName,
-					TypeUtils.RemoveArrayType(args[0]?.GetType()),
-					new[] { Microsoft.CSharp.RuntimeBinder.CSharpArgumentInfo.Create(Microsoft.CSharp.RuntimeBinder.CSharpArgumentInfoFlags.None, null) }
-				);
-				return binder.Bind(args, parameters, returnLabel);
-			}
-		}
-
-		/// <summary>
-		/// Binds to a method invocation of an instance as late as possible.  This allows the use of anonymous types on dynamic values.
-		/// </summary>
-		private class LateInvokeMethodCallSiteBinder : CallSiteBinder
-		{
-			private readonly string _methodName;
-
-			public LateInvokeMethodCallSiteBinder(string methodName)
-			{
-				_methodName = methodName;
-			}
-
-			public override Expression Bind(object[] args, ReadOnlyCollection<ParameterExpression> parameters, LabelTarget returnLabel)
-			{
-				var binderM = Microsoft.CSharp.RuntimeBinder.Binder.InvokeMember(
-					Microsoft.CSharp.RuntimeBinder.CSharpBinderFlags.None,
-					_methodName,
-					null,
-					TypeUtils.RemoveArrayType(args[0]?.GetType()),
-					parameters.Select(x => Microsoft.CSharp.RuntimeBinder.CSharpArgumentInfo.Create(Microsoft.CSharp.RuntimeBinder.CSharpArgumentInfoFlags.None, null))
-				);
-				return binderM.Bind(args, parameters, returnLabel);
-			}
-		}
-
-		/// <summary>
-		/// Binds to an items invocation of an instance as late as possible.  This allows the use of anonymous types on dynamic values.
-		/// </summary>
-		private class LateInvokeIndexCallSiteBinder : CallSiteBinder
-		{
-			public override Expression Bind(object[] args, ReadOnlyCollection<ParameterExpression> parameters, LabelTarget returnLabel)
-			{
-				var binder = Microsoft.CSharp.RuntimeBinder.Binder.GetIndex(
-					Microsoft.CSharp.RuntimeBinder.CSharpBinderFlags.None,
-					TypeUtils.RemoveArrayType(args[0]?.GetType()),
-					parameters.Select(x => Microsoft.CSharp.RuntimeBinder.CSharpArgumentInfo.Create(Microsoft.CSharp.RuntimeBinder.CSharpArgumentInfoFlags.None, null))
-				);
-				return binder.Bind(args, parameters, returnLabel);
-			}
-		}
-
 	}
 }
diff --git a/src/DynamicExpresso.Core/Resolution/LateBinders.cs b/src/DynamicExpresso.Core/Resolution/LateBinders.cs
new file mode 100644
index 0000000..6fc40b0
--- /dev/null
+++ b/src/DynamicExpresso.Core/Resolution/LateBinders.cs
@@ -0,0 +1,71 @@
+using System.Collections.ObjectModel;
+using System.Linq;
+using System.Linq.Expressions;
+using System.Runtime.CompilerServices;
+using DynamicExpresso.Reflection;
+using Microsoft.CSharp.RuntimeBinder;
+
+namespace DynamicExpresso.Resolution
+{
+	internal class LateGetMemberCallSiteBinder : CallSiteBinder
+	{
+		private readonly string _propertyOrFieldName;
+
+		public LateGetMemberCallSiteBinder(string propertyOrFieldName)
+		{
+			_propertyOrFieldName = propertyOrFieldName;
+		}
+
+		public override Expression Bind(object[] args, ReadOnlyCollection<ParameterExpression> parameters, LabelTarget returnLabel)
+		{
+			var binder = Binder.GetMember(
+				CSharpBinderFlags.None,
+				_propertyOrFieldName,
+				TypeUtils.RemoveArrayType(args[0]?.GetType()),
+				new[] { CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null) }
+			);
+			return binder.Bind(args, parameters, returnLabel);
+		}
+	}
+
+	/// <summary>
+	/// Binds to a method invocation of an instance as late as possible.  This allows the use of anonymous types on dynamic values.
+	/// </summary>
+	internal class LateInvokeMethodCallSiteBinder : CallSiteBinder
+	{
+		private readonly string _methodName;
+
+		public LateInvokeMethodCallSiteBinder(string methodName)
+		{
+			_methodName = methodName;
+		}
+
+		public override Expression Bind(object[] args, ReadOnlyCollection<ParameterExpression> parameters, LabelTarget returnLabel)
+		{
+			var binderM = Binder.InvokeMember(
+				CSharpBinderFlags.None,
+				_methodName,
+				null,
+				TypeUtils.RemoveArrayType(args[0]?.GetType()),
+				parameters.Select(x => CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null))
+			);
+			return binderM.Bind(args, parameters, returnLabel);
+		}
+	}
+
+	/// <summary>
+	/// Binds to an items invocation of an instance as late as possible.  This allows the use of anonymous types on dynamic values.
+	/// </summary>
+	internal class LateInvokeIndexCallSiteBinder : CallSiteBinder
+	{
+		public override Expression Bind(object[] args, ReadOnlyCollection<ParameterExpression> parameters, LabelTarget returnLabel)
+		{
+			var binder = Binder.GetIndex(
+				CSharpBinderFlags.None,
+				TypeUtils.RemoveArrayType(args[0]?.GetType()),
+				parameters.Select(x => CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null))
+			);
+			return binder.Bind(args, parameters, returnLabel);
+		}
+	}
+}