From f95b6081cba084d1b067acea99c0effa2b3bf42c Mon Sep 17 00:00:00 2001
From: MW
Date: Thu, 24 May 2007 12:35:32 +0000
Subject: Renamed the new Directories. (removed the "-Source" from the end of
them)
---
Common/XmlRpcCS/XmlRpcSystemObject.cs | 252 ++++++++++++++++++++++++++++++++++
1 file changed, 252 insertions(+)
create mode 100644 Common/XmlRpcCS/XmlRpcSystemObject.cs
(limited to 'Common/XmlRpcCS/XmlRpcSystemObject.cs')
diff --git a/Common/XmlRpcCS/XmlRpcSystemObject.cs b/Common/XmlRpcCS/XmlRpcSystemObject.cs
new file mode 100644
index 0000000..5f79951
--- /dev/null
+++ b/Common/XmlRpcCS/XmlRpcSystemObject.cs
@@ -0,0 +1,252 @@
+namespace Nwc.XmlRpc
+{
+ using System;
+ using System.Collections;
+ using System.Reflection;
+
+ /// XML-RPC System object implementation of extended specifications.
+ [XmlRpcExposed]
+ public class XmlRpcSystemObject
+ {
+ private XmlRpcServer _server;
+ static private IDictionary _methodHelp = new Hashtable();
+
+ /// Static IDictionary to hold mappings of method name to associated documentation String
+ static public IDictionary MethodHelp
+ {
+ get { return _methodHelp; }
+ }
+
+ /// Constructor.
+ /// XmlRpcServer server to be the system object for.
+ public XmlRpcSystemObject(XmlRpcServer server)
+ {
+ _server = server;
+ server.Add("system", this);
+ _methodHelp.Add(this.GetType().FullName + ".methodHelp", "Return a string description.");
+ }
+
+ /// Invoke a method on a given object.
+ /// Using reflection, and respecting the XmlRpcExposed attribute,
+ /// invoke the methodName method on the target
+ /// instance with the parameters provided. All this packages other Invoke methods
+ /// end up calling this.
+ /// Object the value the invoked method returns.
+ /// If method does not exist, is not exposed, parameters invalid, or invocation
+ /// results in an exception. Note, the XmlRpcException.Code will indicate cause.
+ static public Object Invoke(Object target, String methodName, IList parameters)
+ {
+ if (target == null)
+ throw new XmlRpcException(XmlRpcErrorCodes.SERVER_ERROR_METHOD,
+ XmlRpcErrorCodes.SERVER_ERROR_METHOD_MSG + ": Invalid target object.");
+
+ Type type = target.GetType();
+ MethodInfo method = type.GetMethod(methodName);
+
+ try
+ {
+ if (!XmlRpcExposedAttribute.ExposedMethod(target, methodName))
+ throw new XmlRpcException(XmlRpcErrorCodes.SERVER_ERROR_METHOD,
+ XmlRpcErrorCodes.SERVER_ERROR_METHOD_MSG + ": Method " + methodName + " is not exposed.");
+ }
+ catch (MissingMethodException me)
+ {
+ throw new XmlRpcException(XmlRpcErrorCodes.SERVER_ERROR_METHOD,
+ XmlRpcErrorCodes.SERVER_ERROR_METHOD_MSG + ": " + me.Message);
+ }
+
+ Object[] args = new Object[parameters.Count];
+
+ int index = 0;
+ foreach (Object arg in parameters)
+ {
+ args[index] = arg;
+ index++;
+ }
+
+ try
+ {
+ Object retValue = method.Invoke(target, args);
+ if (retValue == null)
+ throw new XmlRpcException(XmlRpcErrorCodes.APPLICATION_ERROR,
+ XmlRpcErrorCodes.APPLICATION_ERROR_MSG + ": Method returned NULL.");
+ return retValue;
+ }
+ catch (XmlRpcException e)
+ {
+ throw e;
+ }
+ catch (ArgumentException ae)
+ {
+ Logger.WriteEntry(XmlRpcErrorCodes.SERVER_ERROR_PARAMS_MSG + ": " + ae.Message,
+ LogLevel.Information);
+ String call = methodName + "( ";
+ foreach (Object o in args)
+ {
+ call += o.GetType().Name;
+ call += " ";
+ }
+ call += ")";
+ throw new XmlRpcException(XmlRpcErrorCodes.SERVER_ERROR_PARAMS,
+ XmlRpcErrorCodes.SERVER_ERROR_PARAMS_MSG + ": Arguement type mismatch invoking " + call);
+ }
+ catch (TargetParameterCountException tpce)
+ {
+ Logger.WriteEntry(XmlRpcErrorCodes.SERVER_ERROR_PARAMS_MSG + ": " + tpce.Message,
+ LogLevel.Information);
+ throw new XmlRpcException(XmlRpcErrorCodes.SERVER_ERROR_PARAMS,
+ XmlRpcErrorCodes.SERVER_ERROR_PARAMS_MSG + ": Arguement count mismatch invoking " + methodName);
+ }
+ catch (TargetInvocationException tie)
+ {
+ throw new XmlRpcException(XmlRpcErrorCodes.APPLICATION_ERROR,
+ XmlRpcErrorCodes.APPLICATION_ERROR_MSG + " Invoked method " + methodName + ": " + tie.Message);
+ }
+ }
+
+ /// List methods available on all handlers of this server.
+ /// IList An array of Strings, each String will have form "object.method".
+ [XmlRpcExposed]
+ public IList listMethods()
+ {
+ IList methods = new ArrayList();
+ Boolean considerExposure;
+
+ foreach (DictionaryEntry handlerEntry in _server)
+ {
+ considerExposure = XmlRpcExposedAttribute.IsExposed(handlerEntry.Value.GetType());
+
+ foreach (MemberInfo mi in handlerEntry.Value.GetType().GetMembers())
+ {
+ if (mi.MemberType != MemberTypes.Method)
+ continue;
+
+ if (!((MethodInfo)mi).IsPublic)
+ continue;
+
+ if (considerExposure && !XmlRpcExposedAttribute.IsExposed(mi))
+ continue;
+
+ methods.Add(handlerEntry.Key + "." + mi.Name);
+ }
+ }
+
+ return methods;
+ }
+
+ /// Given a method name return the possible signatures for it.
+ /// String The object.method name to look up.
+ /// IList Of arrays of signatures.
+ [XmlRpcExposed]
+ public IList methodSignature(String name)
+ {
+ IList signatures = new ArrayList();
+ int index = name.IndexOf('.');
+
+ if (index < 0)
+ return signatures;
+
+ String oName = name.Substring(0, index);
+ Object obj = _server[oName];
+
+ if (obj == null)
+ return signatures;
+
+ MemberInfo[] mi = obj.GetType().GetMember(name.Substring(index + 1));
+
+ if (mi == null || mi.Length != 1) // for now we want a single signature
+ return signatures;
+
+ MethodInfo method;
+
+ try
+ {
+ method = (MethodInfo)mi[0];
+ }
+ catch (Exception e)
+ {
+ Logger.WriteEntry("Attempted methodSignature call on " + mi[0] + " caused: " + e,
+ LogLevel.Information);
+ return signatures;
+ }
+
+ if (!method.IsPublic)
+ return signatures;
+
+ IList signature = new ArrayList();
+ signature.Add(method.ReturnType.Name);
+
+ foreach (ParameterInfo param in method.GetParameters())
+ {
+ signature.Add(param.ParameterType.Name);
+ }
+
+
+ signatures.Add(signature);
+
+ return signatures;
+ }
+
+ /// Help for given method signature. Not implemented yet.
+ /// String The object.method name to look up.
+ /// String help text. Rich HTML text.
+ [XmlRpcExposed]
+ public String methodHelp(String name)
+ {
+ String help = null;
+
+ try
+ {
+ help = (String)_methodHelp[_server.MethodName(name)];
+ }
+ catch (XmlRpcException e)
+ {
+ throw e;
+ }
+ catch (Exception) { /* ignored */ };
+
+ if (help == null)
+ help = "No help available for: " + name;
+
+ return help;
+ }
+
+ /// Boxcarring support method.
+ /// IList of calls
+ /// ArrayList of results/faults.
+ [XmlRpcExposed]
+ public IList multiCall(IList calls)
+ {
+ IList responses = new ArrayList();
+ XmlRpcResponse fault = new XmlRpcResponse();
+
+ foreach (IDictionary call in calls)
+ {
+ try
+ {
+ XmlRpcRequest req = new XmlRpcRequest((String)call[XmlRpcXmlTokens.METHOD_NAME],
+ (ArrayList)call[XmlRpcXmlTokens.PARAMS]);
+ Object results = _server.Invoke(req);
+ IList response = new ArrayList();
+ response.Add(results);
+ responses.Add(response);
+ }
+ catch (XmlRpcException e)
+ {
+ fault.SetFault(e.FaultCode, e.FaultString);
+ responses.Add(fault.Value);
+ }
+ catch (Exception e2)
+ {
+ fault.SetFault(XmlRpcErrorCodes.APPLICATION_ERROR,
+ XmlRpcErrorCodes.APPLICATION_ERROR_MSG + ": " + e2.Message);
+ responses.Add(fault.Value);
+ }
+ }
+
+ return responses;
+ }
+
+ }
+}
+
--
cgit v1.1