Example #1
0
        /// <summary>
        /// Adds a method. It will be callable by the name of the type of <paramref name="obj"/> and it's own name.
        /// Either can be substituted through <paramref name="interfaceName"/> and <paramref name="methodName"/>.
        /// </summary>
        /// <typeparam name="T">The type of <paramref name="obj"/></typeparam>
        /// <param name="obj">The object which can be called later.</param>
        /// <param name="method">The method which should later be called.</param>
        /// <param name="interfaceName">The optional interfaceName if you don't want to use the name of the class.</param>
        /// <param name="methodName">The optional methodName if you don't want to use the name of the method.</param>
        public void Add <T>(T obj, MethodInfo method, string interfaceName = "", string methodName = "")
        {
            var compiler = new ExpressionCompiler <Func <ISerializer, object> >();

            var serializer = compiler.Parameter <ISerializer>("serializer");

            var target    = compiler.Constant(obj);
            var toObject  = typeof(ISerializer).GetMethod("Get");
            var arguments = new List <int>();

            foreach (var parameter in method.GetParameters())
            {
                var correctToObject = toObject.MakeGenericMethod(parameter.ParameterType);
                var position        = compiler.Constant(parameter.Position);
                arguments.Add(compiler.Call(serializer, correctToObject, position));
            }

            var call = compiler.Call(target, method, arguments.ToArray());

            compiler.Emit(call);

            if (method.ReturnType.IsValueType)
            {
                var convert = compiler.Convert(call, typeof(object));

                compiler.Emit(convert);
            }

            if (string.IsNullOrWhiteSpace(interfaceName))
            {
                interfaceName = obj.GetType().Name;
            }

            if (string.IsNullOrWhiteSpace(methodName))
            {
                methodName = method.Name;
            }

            _dict.Add(interfaceName + "::" + methodName, compiler.Compile());
        }
        public void Compile_ShouldCreateDelegate()
        {
            var comp      = new ExpressionCompiler <Func <string, int> >();
            var lengthPi  = typeof(string).GetProperty("Length");
            var str       = comp.Parameter <string>("str");
            var strLength = comp.Property(str, lengthPi);

            comp.Emit(strLength);

            var dlg = comp.Compile();

            Assert.NotNull(dlg);
            Assert.Equal(4, dlg("four"));
        }