Beispiel #1
0
        public static string ExecuteCallbackMethod(Control control, Dictionary <string, object> callInfo)
        {
            string methodName = (string)callInfo["name"];

            object[] args        = (object[])callInfo["args"];
            string   clientState = (string)callInfo["state"];

            // Attempt to load the client state
            IClientStateManager csm = control as IClientStateManager;

            if (csm != null && csm.SupportsClientState)
            {
                csm.LoadClientState(clientState);
            }

            // call the method
            object result = null;
            Dictionary <string, object> error = null;

            Type controlType = control.GetType();

            try
            {
                // Find a matching static or instance method.  Only public methods can be invoked
                MethodInfo mi = controlType.GetMethod(methodName, BindingFlags.Public | BindingFlags.Static | BindingFlags.Instance);
                if (mi == null)
                {
                    throw new MissingMethodException(controlType.FullName, methodName);
                }

                // Verify that the method has the corrent number of parameters as well as the ScriptControlMethodAttribute
                ParameterInfo[] methodParams          = mi.GetParameters();
                ScriptControlMethodAttribute methAttr = (ScriptControlMethodAttribute)Attribute.GetCustomAttribute(mi, typeof(ScriptControlMethodAttribute));

                if (methAttr == null || !methAttr.IsScriptMethod || args.Length != methodParams.Length)
                {
                    throw new MissingMethodException(controlType.FullName, methodName);
                }

                // Convert each argument to the parameter type if possible
                // NOTE: I'd rather have the ObjectConverter from within Microsoft.Web.Script.Serialization namespace for this
                object[] targetArgs = new object[args.Length];
                for (int i = 0; i < targetArgs.Length; i++)
                {
                    if (args[i] == null)
                    {
                        continue;
                    }

                    targetArgs[i] = JSONSerializerExecute.DeserializeObject(args[i], methodParams[i].ParameterType);
                }

                result = mi.Invoke(control, targetArgs);
            }
            catch (Exception ex)
            {
                // Catch the exception information to relay back to the client
                if (ex is TargetInvocationException)
                {
                    ex = ex.InnerException;
                }
                error            = new Dictionary <string, object>();
                error["name"]    = ex.GetType().FullName;
                error["message"] = ex.Message;

                if (WebUtility.AllowResponseExceptionStackTrace())
                {
                    error["stackTrace"] = ex.StackTrace;
                }
                else
                {
                    error["stackTrace"] = string.Empty;
                }

                TryWriteLog(ex, control);
            }

            // return the result
            Dictionary <string, object> resultInfo = new Dictionary <string, object>();

            if (error == null)
            {
                resultInfo["result"] = result;
                if (csm != null && csm.SupportsClientState)
                {
                    resultInfo["state"] = csm.SaveClientState();
                }
            }
            else
            {
                resultInfo["error"] = error;
            }

            // Serialize the result info into JSON
            return(JSONSerializerExecute.Serialize(resultInfo));
        }