예제 #1
0
        public void RegisterWebservice(string path, Webservice webservice)
        {
            lock (server)
            {
                if (server.IsListening)
                {
                    throw new InvalidOperationException("Can not add a prefix to a running server");
                }

                if (!path.EndsWith("/"))
                {
                    throw new ArgumentException("path should end with /");
                }

                // Register into route processing
                services.Add(path, webservice);
            }
        }
예제 #2
0
        internal void DispatchWebservice(HttpListenerContext context)
        {
            // Resolve to method
            Match      match   = routingRegex.Match(context.Request.Url.AbsolutePath);
            Webservice service = ResolveWebservice(match);
            MethodInfo method  = null;

            if (service != null)
            {
                method = service.ResolveMethod(match);
            }

            if (service == null || method == null)
            {
                context.Response.StatusCode        = 404;
                context.Response.StatusDescription = "Service not found";
            }
            else
            {
                // TODO: Parse POST then GET params?
                // TODO: Allow variables to be tagged with resolution order
                // void foo(@WebVar('POST') int x)

                object[] args = new object[method.GetParameters().Length];

                foreach (var param in method.GetParameters())
                {
                    if (param.ParameterType == typeof(HttpListenerContext))
                    {
                        args[param.Position] = context;
                    }
                    else if (param.ParameterType == typeof(HttpListenerRequest))
                    {
                        args[param.Position] = context.Request;
                    }
                    else if (param.ParameterType == typeof(HttpListenerResponse))
                    {
                        args[param.Position] = context.Response;
                    }
                    else
                    {
                        //
                        // Pull argument from URI
                        //

                        Group group = match.Groups[Webservice.WebArgumentGroupName(param.Name)];
                        // If the assertion below fails, check the routing regex.
                        Debug.Assert(group.Success &&
                                     Webservice.ValidParameterTypes.Keys.Contains(param.ParameterType));
                        string argString = group.Value;
                        object argValue  = null;
                        if (!group.Success)
                        {
                            throw new InvalidOperationException("Programmer Error: URL group match was not successful");
                        }
                        else if (param.ParameterType == typeof(string))
                        {
                            argValue = argString;
                        }
                        else if (Webservice.ValidParameterTypes.Keys.Contains(param.ParameterType))
                        {
                            object[] temp = { argString };
                            argValue = param.ParameterType.InvokeMember("Parse", BindingFlags.Public | BindingFlags.Static | BindingFlags.InvokeMethod, null, null, temp);
                        }
                        else
                        {
                            throw new InvalidOperationException(string.Format("Programmer Error: Type {0} is not a supported WebArgument type"));
                        }
                        args[param.Position] = argValue;
                    }
                }

                object returnValue = method.Invoke(service, args);

                if (context.Response.StatusCode == (int)HttpStatusCode.OK && returnValue != null)
                {
                    Encoding encoding = context.Response.ContentEncoding;
                    if (encoding == null)
                    {
                        context.Response.ContentEncoding = encoding = Encoding.UTF8;
                    }

                    byte[] buffer = null;
                    if (method.ReturnType == typeof(string))
                    {
                        buffer = encoding.GetBytes((string)returnValue);
                    }

                    if (buffer != null)
                    {
                        context.Response.OutputStream.Write(buffer, 0, buffer.Length);
                    }
                    else
                    {
                        context.Response.StatusCode        = (int)HttpStatusCode.InternalServerError;
                        context.Response.StatusDescription = "Invalid Return Type";
                    }
                }
            }
            context.Response.Close();
        }
예제 #3
0
 internal static string WebserviceGroupName(Webservice service)
 {
     return(String.Format("service_{0}", service.GetHashCode()));
 }
예제 #4
0
 internal static string WebserviceGroupName(Webservice service)
 {
     return String.Format("service_{0}", service.GetHashCode());
 }