Permalink
Browse files

Refactored Dynamic linq to LinqInstanceProxy

  • Loading branch information...
1 parent 1eb0c05 commit 5b743c6e3484d5d5db6dcb059267744a53371c42 @jbtule jbtule committed Aug 27, 2012
Showing with 425 additions and 288 deletions.
  1. +1 −1 ImpromptuInterface.FSharp/AssemblyInfo.fs
  2. +2 −2 ImpromptuInterface.MVVM/Properties/AssemblyInfo.cs
  3. +5 −2 ImpromptuInterface.Silverlight/ImpromptuInterface (Silverlight).csproj
  4. +5 −2 ImpromptuInterface.Silverlight5/ImpromptuInterface (Silverlight5).csproj
  5. +2 −1 ImpromptuInterface/ImpromptuInterface.csproj
  6. +2 −2 ImpromptuInterface/Properties/AssemblyInfo.cs
  7. +290 −0 ImpromptuInterface/src/Dynamic/ExtensionToInstanceProxy.cs
  8. +38 −7 ImpromptuInterface/src/Dynamic/ImpromptuForwarder.cs
  9. +7 −1 ImpromptuInterface/src/Dynamic/ImpromptuObject.cs
  10. +36 −243 ImpromptuInterface/src/Dynamic/{DynamicLinq.cs → LinqInstanceProxy.cs}
  11. +13 −3 ImpromptuInterface/src/Impromptu.cs
  12. +1 −1 NuGetBuild/Core/ImpromptuInterface.MetaData.xml
  13. +1 −1 NuGetBuild/Core/ImpromptuInterface.Symbol.nuspec
  14. +2 −2 NuGetBuild/Core/ImpromptuInterface.Symbol.tt
  15. +2 −2 NuGetBuild/Core/ImpromptuInterface.nuspec
  16. +2 −2 NuGetBuild/Core/ImpromptuInterface.tt
  17. +2 −2 NuGetBuild/FSharp/ImpromptuInterface.FSharp.MetaData.xml
  18. +2 −2 NuGetBuild/FSharp/ImpromptuInterface.FSharp.Symbol.nuspec
  19. +1 −1 NuGetBuild/FSharp/ImpromptuInterface.FSharp.Symbol.tt
  20. +2 −2 NuGetBuild/FSharp/ImpromptuInterface.FSharp.nuspec
  21. +1 −1 NuGetBuild/FSharp/ImpromptuInterface.FSharp.tt
  22. +2 −2 NuGetBuild/MVVM/ImpromptuInterface.MVVM.MetaData.xml
  23. +2 −2 NuGetBuild/MVVM/ImpromptuInterface.MVVM.Symbol.nuspec
  24. +1 −1 NuGetBuild/MVVM/ImpromptuInterface.MVVM.Symbol.tt
  25. +2 −2 NuGetBuild/MVVM/ImpromptuInterface.MVVM.nuspec
  26. +1 −1 NuGetBuild/MVVM/ImpromptuInterface.MVVM.tt
@@ -40,5 +40,5 @@ open System.Runtime.InteropServices;
// You can specify all the values or you can default the Build and Revision Numbers
// by using the ‘*’ as shown below:
// [assembly: AssemblyVersion("1.0.*")]
-[<assembly: AssemblyVersion("1.2.7.0")>]
+[<assembly: AssemblyVersion("1.2.8.0")>]
()
@@ -42,7 +42,7 @@
// by using the '*' as shown below:
// [assembly: AssemblyVersion("1.0.*")]
#if SILVERLIGHT
-[assembly: AssemblyVersion("4.0.6.0")]
+[assembly: AssemblyVersion("4.0.8.0")]
#else
-[assembly: AssemblyVersion("4.0.7.*")]
+[assembly: AssemblyVersion("4.0.8.*")]
#endif
@@ -100,8 +100,8 @@
<Compile Include="..\ImpromptuInterface\src\Dynamic\CacheableInvocation.cs">
<Link>src\Dynamic\CacheableInvocation.cs</Link>
</Compile>
- <Compile Include="..\ImpromptuInterface\src\Dynamic\DynamicLinq.cs">
- <Link>src\Dynamic\DynamicLinq.cs</Link>
+ <Compile Include="..\ImpromptuInterface\src\Dynamic\ExtensionToInstanceProxy.cs">
+ <Link>src\Dynamic\ExtensionToInstanceProxy.cs</Link>
</Compile>
<Compile Include="..\ImpromptuInterface\src\Dynamic\FluentRegex.cs">
<Link>src\Dynamic\FluentRegex.cs</Link>
@@ -163,6 +163,9 @@
<Compile Include="..\ImpromptuInterface\src\Dynamic\Invocation.cs">
<Link>src\Dynamic\Invocation.cs</Link>
</Compile>
+ <Compile Include="..\ImpromptuInterface\src\Dynamic\LinqInstanceProxy.cs">
+ <Link>src\Dynamic\LinqInstanceProxy.cs</Link>
+ </Compile>
<Compile Include="..\ImpromptuInterface\src\Dynamic\Mimic.cs">
<Link>src\Dynamic\Mimic.cs</Link>
</Compile>
@@ -80,8 +80,8 @@
<Compile Include="..\ImpromptuInterface\src\Dynamic\CacheableInvocation.cs">
<Link>src\Dynamic\CacheableInvocation.cs</Link>
</Compile>
- <Compile Include="..\ImpromptuInterface\src\Dynamic\DynamicLinq.cs">
- <Link>src\Dynamic\DynamicLinq.cs</Link>
+ <Compile Include="..\ImpromptuInterface\src\Dynamic\ExtensionToInstanceProxy.cs">
+ <Link>src\Dynamic\ExtensionToInstanceProxy.cs</Link>
</Compile>
<Compile Include="..\ImpromptuInterface\src\Dynamic\FluentRegex.cs">
<Link>src\Dynamic\FluentRegex.cs</Link>
@@ -143,6 +143,9 @@
<Compile Include="..\ImpromptuInterface\src\Dynamic\Invocation.cs">
<Link>src\Dynamic\Invocation.cs</Link>
</Compile>
+ <Compile Include="..\ImpromptuInterface\src\Dynamic\LinqInstanceProxy.cs">
+ <Link>src\Dynamic\LinqInstanceProxy.cs</Link>
+ </Compile>
<Compile Include="..\ImpromptuInterface\src\Dynamic\Mimic.cs">
<Link>src\Dynamic\Mimic.cs</Link>
</Compile>
@@ -109,7 +109,8 @@
<ItemGroup>
<Compile Include="Properties\AssemblyInfo.cs" />
<Compile Include="src\ActLikeCaster.cs" />
- <Compile Include="src\Dynamic\DynamicLinq.cs" />
+ <Compile Include="src\Dynamic\LinqInstanceProxy.cs" />
+ <Compile Include="src\Dynamic\ExtensionToInstanceProxy.cs" />
<Compile Include="src\Dynamic\FluentStringLookup.cs" />
<Compile Include="src\Dynamic\ImpromptuMatch.cs" />
<Compile Include="src\Dynamic\FluentRegex.cs" />
@@ -59,10 +59,10 @@
#if SILVERLIGHT
-[assembly: AssemblyVersion("6.0.6.0")]
+[assembly: AssemblyVersion("6.1.1.0")]
#else
-[assembly: AssemblyVersion("6.1.0.*")]
+[assembly: AssemblyVersion("6.1.1.*")]
#endif
@@ -0,0 +1,290 @@
+using System;
+using System.Collections;
+using System.Collections.Generic;
+using System.Dynamic;
+using System.Linq;
+using System.Reflection;
+using System.Runtime.Serialization;
+using System.Text;
+using ImpromptuInterface.Internal.Support;
+using ImpromptuInterface.Optimization;
+using Microsoft.CSharp.RuntimeBinder;
+
+namespace ImpromptuInterface.Dynamic
+{
+
+
+ [Serializable]
+ public class ExtensionToInstanceProxy: ImpromptuForwarder
+ {
+ private readonly Type _extendedType;
+ private readonly Type[] _staticTypes;
+ private readonly Type[] _instanceHints;
+
+ public IEnumerable<Type> InstanceHints
+ {
+ get { return _instanceHints ?? KnownInterfaces; }
+ }
+
+#if !SILVERLIGHT
+ /// <summary>
+ /// Initializes a new instance of the <see cref="ImpromptuObject"/> class. when deserializing
+ /// </summary>
+ /// <param name="info">The info.</param>
+ /// <param name="context">The context.</param>
+ protected ExtensionToInstanceProxy(SerializationInfo info,
+ StreamingContext context) : base(info, context)
+ {
+ _staticTypes = info.GetValue<Type[]>("_staticTypes");
+ _extendedType = info.GetValue<Type>("_extendedType");
+ _instanceHints = info.GetValue<Type[]>("_instanceHints");
+ }
+
+ /// <summary>
+ /// Populates a <see cref="T:System.Runtime.Serialization.SerializationInfo"/> with the data needed to serialize the target object.
+ /// </summary>
+ /// <param name="info">The <see cref="T:System.Runtime.Serialization.SerializationInfo"/> to populate with data.</param>
+ /// <param name="context">The destination (see <see cref="T:System.Runtime.Serialization.StreamingContext"/>) for this serialization.</param>
+ /// <exception cref="T:System.Security.SecurityException">The caller does not have the required permission. </exception>
+ public virtual void GetObjectData(SerializationInfo info, StreamingContext context)
+ {
+ base.GetObjectData(info, context);
+ info.AddValue("_staticType", _extendedType);
+ info.AddValue("_extendedType", _staticTypes);
+ info.AddValue("_instanceHints", _staticTypes);
+ }
+#endif
+
+ public ExtensionToInstanceProxy(dynamic target, Type extendedType, Type[] staticTypes, Type[] instanceHints = null):base((object)target)
+ {
+ _staticTypes = staticTypes;
+ _extendedType = extendedType;
+ _instanceHints = instanceHints;
+
+ if(target is ExtensionToInstanceProxy)
+ throw new ArgumentException("Don't Nest ExtensionToInstance Objects");
+
+ if (IsExtendedType(target))
+ {
+ return;
+ }
+
+ throw new ArgumentException(String.Format("Non a valid {0} to be wrapped.",_extendedType));
+
+ }
+
+ public override bool TryGetMember(GetMemberBinder binder, out object result)
+ {
+
+ if (!base.TryGetMember(binder, out result))
+ {
+
+ var tInterface = CallTarget.GetType().GetInterface(_extendedType.Name, false);
+ result = new Invoker(binder.Name,
+ tInterface.IsGenericType ? tInterface.GetGenericArguments() : new Type[] {}, this);
+ }
+ return true;
+ }
+
+ public class Invoker:ImpromptuObject
+ {
+ private string _name;
+ private ExtensionToInstanceProxy _parent;
+ private IDictionary<int,Type[]> _overloadTypes;
+ private Type[] _genericParams;
+
+ internal Invoker(string name, Type[] genericParameters, ExtensionToInstanceProxy parent, Type[] overloadTypes = null)
+ {
+ _name = name;
+ _parent = parent;
+ _genericParams = genericParameters;
+ _overloadTypes = new Dictionary<int,Type[]>();
+
+ if (overloadTypes == null)
+ {
+
+ foreach (var tGenInterface in parent.InstanceHints)
+ {
+ var tNewType = tGenInterface;
+
+ if (tNewType.IsGenericType)
+ {
+ tNewType = tNewType.MakeGenericType(_genericParams);
+ }
+
+ var members = tNewType.GetMethods(BindingFlags.Instance |
+ BindingFlags.Public).Where(
+ it => it.Name == _name).ToList();
+ foreach (var tMethodInfo in members)
+ {
+ var tParams = tMethodInfo.GetParameters().Select(it => it.ParameterType).ToArray();
+
+ if (_overloadTypes.ContainsKey(tParams.Length))
+ {
+ _overloadTypes[tParams.Length] = new Type[] {};
+ }
+ else
+ {
+ _overloadTypes[tParams.Length] = tParams.Select(ReplaceGenericTypes).ToArray();
+ }
+ }
+
+ foreach (var tOverloadType in _overloadTypes.ToList())
+ {
+ if (tOverloadType.Value.Length == 0)
+ {
+ _overloadTypes.Remove(tOverloadType);
+ }
+ }
+
+ }
+ }
+ else
+ {
+ _overloadTypes[overloadTypes.Length] = overloadTypes;
+ }
+ }
+
+ private Type ReplaceGenericTypes(Type type)
+ {
+ if (type.IsGenericType && type.ContainsGenericParameters)
+ {
+ var tArgs = type.GetGenericArguments();
+
+ tArgs = tArgs.Select(ReplaceGenericTypes).ToArray();
+
+ return type.GetGenericTypeDefinition().MakeGenericType(tArgs);
+ }
+
+ if (type.ContainsGenericParameters)
+ {
+ return typeof (object);
+ }
+
+ return type;
+ }
+
+ public override bool TryGetMember(GetMemberBinder binder, out object result)
+ {
+ if (binder.Name == "Overloads")
+ {
+ result = this;
+ return true;
+ }
+ return base.TryGetMember(binder, out result);
+ }
+
+ public override bool TryGetIndex(GetIndexBinder binder, object[] indexes, out object result)
+ {
+ result = new Invoker(_name, _genericParams, _parent, indexes.Select(it=>Impromptu.InvokeConvert(it,typeof(Type),@explicit:true)).Cast<Type>().ToArray());
+ return true;
+ }
+
+ public override bool TryInvoke(InvokeBinder binder, object[] args, out object result)
+ {
+ object[] tArgs = args;
+ if (_overloadTypes.ContainsKey(args.Length))
+ {
+ tArgs = _overloadTypes[args.Length].Zip(args, Tuple.Create)
+ .Select(it => it.Item2 != null ? Impromptu.InvokeConvert(it.Item2, it.Item1, @explicit: true) : null).ToArray();
+
+ }
+ result = _parent.InvokeStaticMethod(_name, tArgs);
+ return true;
+ }
+ }
+
+
+
+ public override bool TryInvokeMember(System.Dynamic.InvokeMemberBinder binder, object[] args, out object result)
+ {
+ if (!base.TryInvokeMember(binder, args, out result))
+ {
+ result = InvokeStaticMethod(binder.Name, args);
+ }
+ return true;
+ }
+
+ protected object InvokeStaticMethod(string name, object[] args)
+ {
+ var staticType = InvokeContext.CreateStatic;
+
+
+ var tList = new List<object> { CallTarget };
+ tList.AddRange(args);
+
+ object result =null;
+ var sucess = false;
+ var exceptionList = new List<Exception>();
+ foreach (var sType in _staticTypes)
+ {
+ try
+ {
+ result = Impromptu.InvokeMember(staticType(sType), name, tList.ToArray());
+ sucess = true;
+ break;
+ }
+ catch (RuntimeBinderException ex)
+ {
+ exceptionList.Add(ex);
+ }
+ }
+
+ if (!sucess)
+ {
+
+#if SILVERLIGHT && !SILVERLIGHT5
+ throw exceptionList.First();
+#else
+ throw new AggregateException(exceptionList);
+#endif
+ }
+
+
+ Type tOutType;
+ if (TryTypeForName(name, out tOutType))
+ {
+ if (tOutType.IsInterface)
+ {
+ var tIsGeneric = tOutType.IsGenericType;
+ if (tOutType.IsGenericType)
+ {
+ tOutType = tOutType.GetGenericTypeDefinition();
+ }
+
+ if (InstanceHints.Select(it => tIsGeneric && it.IsGenericType ? it.GetGenericTypeDefinition() : it)
+ .Contains(tOutType))
+ {
+ result = new ExtensionToInstanceProxy(result,_extendedType, _staticTypes, _instanceHints);
+ }
+ }
+ }
+ else
+ {
+ if (IsExtendedType(result))
+ {
+ result = new ExtensionToInstanceProxy(result, _extendedType, _staticTypes, _instanceHints);
+ }
+ }
+
+ return result;
+ }
+
+ private bool IsExtendedType(object target)
+ {
+
+ if (target is ExtensionToInstanceProxy)
+ {
+ return false;
+ }
+
+ bool genericDef = _extendedType.IsGenericTypeDefinition;
+
+ return target.GetType().GetInterfaces().Any(
+ it => ((genericDef && it.IsGenericType) ? it.GetGenericTypeDefinition() : it) == _extendedType);
+
+ }
+
+
+ }
+}
Oops, something went wrong.

0 comments on commit 5b743c6

Please sign in to comment.