/// <summary>
        /// Overridable method that can be used to implement a custom hnandler
        /// </summary>
        /// <param name="httpReq">The HTTP req.</param>
        /// <param name="url">The URL.</param>
        /// <returns>Task.</returns>
        protected Task RequestHandler(IHttpRequest httpReq, Uri url)
        {
            var date = DateTime.Now;

            var httpRes = httpReq.Response;

            var operationName = httpReq.OperationName;
            var localPath     = url.LocalPath;

            if (string.Equals(localPath, "/mediabrowser/", StringComparison.OrdinalIgnoreCase) ||
                string.Equals(localPath, "/emby/", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl(DefaultRedirectPath);
                return(Task.FromResult(true));
            }
            if (string.Equals(localPath, "/mediabrowser", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl("mediabrowser/" + DefaultRedirectPath);
                return(Task.FromResult(true));
            }
            if (string.Equals(localPath, "/emby", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl("emby/" + DefaultRedirectPath);
                return(Task.FromResult(true));
            }
            if (string.Equals(localPath, "/", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl(DefaultRedirectPath);
                return(Task.FromResult(true));
            }
            if (string.IsNullOrEmpty(localPath))
            {
                httpRes.RedirectToUrl("/" + DefaultRedirectPath);
                return(Task.FromResult(true));
            }

            var handler = HttpHandlerFactory.GetHandler(httpReq);

            var remoteIp = httpReq.RemoteIp;

            var serviceStackHandler = handler as IServiceStackHandler;

            if (serviceStackHandler != null)
            {
                var restHandler = serviceStackHandler as RestHandler;
                if (restHandler != null)
                {
                    httpReq.OperationName = operationName = restHandler.RestPath.RequestType.GetOperationName();
                }

                var task = serviceStackHandler.ProcessRequestAsync(httpReq, httpRes, operationName);

                task.ContinueWith(x => httpRes.Close(), TaskContinuationOptions.OnlyOnRanToCompletion | TaskContinuationOptions.AttachedToParent);
                //Matches Exceptions handled in HttpListenerBase.InitTask()

                var urlString = url.ToString();

                task.ContinueWith(x =>
                {
                    var statusCode = httpRes.StatusCode;

                    var duration = DateTime.Now - date;

                    LoggerUtils.LogResponse(_logger, statusCode, urlString, remoteIp, duration);
                }, TaskContinuationOptions.None);
                return(task);
            }

            return(new NotImplementedException("Cannot execute handler: " + handler + " at PathInfo: " + httpReq.PathInfo)
                   .AsTaskException());
        }
Beispiel #2
0
        /// <summary>
        /// Overridable method that can be used to implement a custom hnandler
        /// </summary>
        /// <param name="httpReq">The HTTP req.</param>
        /// <param name="url">The URL.</param>
        /// <returns>Task.</returns>
        protected Task RequestHandler(IHttpRequest httpReq, Uri url)
        {
            var date = DateTime.Now;

            var httpRes = httpReq.Response;

            var operationName = httpReq.OperationName;
            var localPath     = url.LocalPath;

            var urlString = url.OriginalString;
            var enableLog = EnableLogging(urlString, localPath);
            var urlToLog  = urlString;

            if (enableLog)
            {
                urlToLog = GetUrlToLog(urlString);
                LoggerUtils.LogRequest(_logger, urlToLog, httpReq.HttpMethod, httpReq.UserAgent);
            }

            if (string.Equals(localPath, "/emby/", StringComparison.OrdinalIgnoreCase) ||
                string.Equals(localPath, "/mediabrowser/", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl(DefaultRedirectPath);
                return(Task.FromResult(true));
            }
            if (string.Equals(localPath, "/emby", StringComparison.OrdinalIgnoreCase) ||
                string.Equals(localPath, "/mediabrowser", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl("emby/" + DefaultRedirectPath);
                return(Task.FromResult(true));
            }

            if (string.Equals(localPath, "/mediabrowser/", StringComparison.OrdinalIgnoreCase) ||
                string.Equals(localPath, "/mediabrowser", StringComparison.OrdinalIgnoreCase) ||
                localPath.IndexOf("mediabrowser/web", StringComparison.OrdinalIgnoreCase) != -1 ||
                localPath.IndexOf("dashboard/", StringComparison.OrdinalIgnoreCase) != -1)
            {
                httpRes.StatusCode  = 200;
                httpRes.ContentType = "text/html";
                var newUrl = urlString.Replace("mediabrowser", "emby", StringComparison.OrdinalIgnoreCase)
                             .Replace("/dashboard/", "/web/", StringComparison.OrdinalIgnoreCase);

                if (!string.Equals(newUrl, urlString, StringComparison.OrdinalIgnoreCase))
                {
                    httpRes.Write("<!doctype html><html><head><title>Emby</title></head><body>Please update your Emby bookmark to <a href=\"" + newUrl + "\">" + newUrl + "</a></body></html>");

                    httpRes.Close();
                    return(Task.FromResult(true));
                }
            }

            if (string.Equals(localPath, "/web", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl(DefaultRedirectPath);
                return(Task.FromResult(true));
            }
            if (string.Equals(localPath, "/web/", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl("../" + DefaultRedirectPath);
                return(Task.FromResult(true));
            }
            if (string.Equals(localPath, "/", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl(DefaultRedirectPath);
                return(Task.FromResult(true));
            }
            if (string.IsNullOrEmpty(localPath))
            {
                httpRes.RedirectToUrl("/" + DefaultRedirectPath);
                return(Task.FromResult(true));
            }

            if (string.Equals(localPath, "/emby/pin", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl("web/pin.html");
                return(Task.FromResult(true));
            }

            if (!string.IsNullOrWhiteSpace(GlobalResponse))
            {
                httpRes.StatusCode  = 503;
                httpRes.ContentType = "text/html";
                httpRes.Write(GlobalResponse);

                httpRes.Close();
                return(Task.FromResult(true));
            }

            var handler = HttpHandlerFactory.GetHandler(httpReq);

            var remoteIp = httpReq.RemoteIp;

            var serviceStackHandler = handler as IServiceStackHandler;

            if (serviceStackHandler != null)
            {
                var restHandler = serviceStackHandler as RestHandler;
                if (restHandler != null)
                {
                    httpReq.OperationName = operationName = restHandler.RestPath.RequestType.GetOperationName();
                }

                var task = serviceStackHandler.ProcessRequestAsync(httpReq, httpRes, operationName);

                task.ContinueWith(x => httpRes.Close(), TaskContinuationOptions.OnlyOnRanToCompletion | TaskContinuationOptions.AttachedToParent);
                //Matches Exceptions handled in HttpListenerBase.InitTask()

                task.ContinueWith(x =>
                {
                    var statusCode = httpRes.StatusCode;

                    var duration = DateTime.Now - date;

                    if (enableLog)
                    {
                        LoggerUtils.LogResponse(_logger, statusCode, urlToLog, remoteIp, duration);
                    }
                }, TaskContinuationOptions.None);
                return(task);
            }

            return(new NotImplementedException("Cannot execute handler: " + handler + " at PathInfo: " + httpReq.PathInfo)
                   .AsTaskException());
        }
Beispiel #3
0
        // Handle the processing of a request in here.
        private void ListenerCallback(IAsyncResult asyncResult, int index)
        {
            var listener = asyncResult.AsyncState as HttpListener;
            HttpListenerContext context = null;

            if (listener == null)
            {
                return;
            }

            try
            {
                if (!IsListening)
                {
                    _logger.Debug("Ignoring ListenerCallback() as HttpListener is no longer listening");
                    return;
                }
                // The EndGetContext() method, as with all Begin/End asynchronous methods in the .NET Framework,
                // blocks until there is a request to be processed or some type of data is available.
                context = listener.EndGetContext(asyncResult);
            }
            catch (Exception ex)
            {
                // You will get an exception when httpListener.Stop() is called
                // because there will be a thread stopped waiting on the .EndGetContext()
                // method, and again, that is just the way most Begin/End asynchronous
                // methods of the .NET Framework work.
                var errMsg = ex + ": " + IsListening;
                _logger.Warn(errMsg);
                return;
            }
            finally
            {
                // Once we know we have a request (or exception), we signal the other thread
                // so that it calls the BeginGetContext() (or possibly exits if we're not
                // listening any more) method to start handling the next incoming request
                // while we continue to process this request on a different thread.
                _autoResetEvents[index].Set();
            }

            if (context == null)
            {
                return;
            }

            var date = DateTime.Now;

            Task.Factory.StartNew(async() =>
            {
                try
                {
                    var request = context.Request;

                    LogHttpRequest(request, index);

                    if (request.IsWebSocketRequest)
                    {
                        await ProcessWebSocketRequest(context).ConfigureAwait(false);
                        return;
                    }

                    var localPath = request.Url.LocalPath;

                    if (string.Equals(localPath, "/mediabrowser/", StringComparison.OrdinalIgnoreCase))
                    {
                        context.Response.Redirect(DefaultRedirectPath);
                        context.Response.Close();
                        return;
                    }
                    if (string.Equals(localPath, "/mediabrowser", StringComparison.OrdinalIgnoreCase))
                    {
                        context.Response.Redirect("mediabrowser/" + DefaultRedirectPath);
                        context.Response.Close();
                        return;
                    }
                    if (string.Equals(localPath, "/", StringComparison.OrdinalIgnoreCase))
                    {
                        context.Response.Redirect("mediabrowser/" + DefaultRedirectPath);
                        context.Response.Close();
                        return;
                    }
                    if (string.IsNullOrEmpty(localPath))
                    {
                        context.Response.Redirect("/mediabrowser/" + DefaultRedirectPath);
                        context.Response.Close();
                        return;
                    }

                    var url      = request.Url.ToString();
                    var endPoint = request.RemoteEndPoint;

                    await ProcessRequestAsync(context).ConfigureAwait(false);

                    var duration = DateTime.Now - date;

                    if (EnableHttpRequestLogging)
                    {
                        LoggerUtils.LogResponse(_logger, context.Response, url, endPoint, duration);
                    }
                }
                catch (Exception ex)
                {
                    _logger.ErrorException("ProcessRequest failure", ex);

                    HandleError(ex, context, _logger);
                }
            });
        }
Beispiel #4
0
        /// <summary>
        /// Overridable method that can be used to implement a custom hnandler
        /// </summary>
        /// <param name="httpReq">The HTTP req.</param>
        /// <param name="url">The URL.</param>
        /// <returns>Task.</returns>
        protected async Task RequestHandler(IHttpRequest httpReq, Uri url)
        {
            var date = DateTime.Now;

            var httpRes = httpReq.Response;

            if (_disposed)
            {
                httpRes.StatusCode = 503;
                httpRes.Close();
                return;
            }

            if (!ValidateHost(url))
            {
                httpRes.StatusCode  = 400;
                httpRes.ContentType = "text/plain";
                httpRes.Write("Invalid host");

                httpRes.Close();
                return;
            }

            if (string.Equals(httpReq.Verb, "OPTIONS", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.StatusCode = 200;
                httpRes.AddHeader("Access-Control-Allow-Origin", "*");
                httpRes.AddHeader("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, PATCH, OPTIONS");
                httpRes.AddHeader("Access-Control-Allow-Headers", "Content-Type, Authorization, Range, X-MediaBrowser-Token, X-Emby-Authorization");
                httpRes.ContentType = "text/html";

                httpRes.Close();
            }

            var operationName = httpReq.OperationName;
            var localPath     = url.LocalPath;

            var urlString = url.OriginalString;
            var enableLog = EnableLogging(urlString, localPath);
            var urlToLog  = urlString;

            if (enableLog)
            {
                urlToLog = GetUrlToLog(urlString);
                LoggerUtils.LogRequest(_logger, urlToLog, httpReq.HttpMethod, httpReq.UserAgent);
            }

            if (string.Equals(localPath, "/emby/", StringComparison.OrdinalIgnoreCase) ||
                string.Equals(localPath, "/mediabrowser/", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl(DefaultRedirectPath);
                return;
            }
            if (string.Equals(localPath, "/emby", StringComparison.OrdinalIgnoreCase) ||
                string.Equals(localPath, "/mediabrowser", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl("emby/" + DefaultRedirectPath);
                return;
            }

            if (string.Equals(localPath, "/mediabrowser/", StringComparison.OrdinalIgnoreCase) ||
                string.Equals(localPath, "/mediabrowser", StringComparison.OrdinalIgnoreCase) ||
                localPath.IndexOf("mediabrowser/web", StringComparison.OrdinalIgnoreCase) != -1)
            {
                httpRes.StatusCode  = 200;
                httpRes.ContentType = "text/html";
                var newUrl = urlString.Replace("mediabrowser", "emby", StringComparison.OrdinalIgnoreCase)
                             .Replace("/dashboard/", "/web/", StringComparison.OrdinalIgnoreCase);

                if (!string.Equals(newUrl, urlString, StringComparison.OrdinalIgnoreCase))
                {
                    httpRes.Write("<!doctype html><html><head><title>Emby</title></head><body>Please update your Emby bookmark to <a href=\"" + newUrl + "\">" + newUrl + "</a></body></html>");

                    httpRes.Close();
                    return;
                }
            }

            if (localPath.IndexOf("dashboard/", StringComparison.OrdinalIgnoreCase) != -1 &&
                localPath.IndexOf("web/dashboard", StringComparison.OrdinalIgnoreCase) == -1)
            {
                httpRes.StatusCode  = 200;
                httpRes.ContentType = "text/html";
                var newUrl = urlString.Replace("mediabrowser", "emby", StringComparison.OrdinalIgnoreCase)
                             .Replace("/dashboard/", "/web/", StringComparison.OrdinalIgnoreCase);

                if (!string.Equals(newUrl, urlString, StringComparison.OrdinalIgnoreCase))
                {
                    httpRes.Write("<!doctype html><html><head><title>Emby</title></head><body>Please update your Emby bookmark to <a href=\"" + newUrl + "\">" + newUrl + "</a></body></html>");

                    httpRes.Close();
                    return;
                }
            }

            if (string.Equals(localPath, "/web", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl(DefaultRedirectPath);
                return;
            }
            if (string.Equals(localPath, "/web/", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl("../" + DefaultRedirectPath);
                return;
            }
            if (string.Equals(localPath, "/", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl(DefaultRedirectPath);
                return;
            }
            if (string.IsNullOrEmpty(localPath))
            {
                httpRes.RedirectToUrl("/" + DefaultRedirectPath);
                return;
            }

            if (string.Equals(localPath, "/emby/pin", StringComparison.OrdinalIgnoreCase))
            {
                httpRes.RedirectToUrl("web/pin.html");
                return;
            }

            if (!string.IsNullOrWhiteSpace(GlobalResponse))
            {
                httpRes.StatusCode  = 503;
                httpRes.ContentType = "text/html";
                httpRes.Write(GlobalResponse);

                httpRes.Close();
                return;
            }

            var handler = HttpHandlerFactory.GetHandler(httpReq);

            var remoteIp = httpReq.RemoteIp;

            var serviceStackHandler = handler as IServiceStackHandler;

            if (serviceStackHandler != null)
            {
                var restHandler = serviceStackHandler as RestHandler;
                if (restHandler != null)
                {
                    httpReq.OperationName = operationName = restHandler.RestPath.RequestType.GetOperationName();
                }

                try
                {
                    await serviceStackHandler.ProcessRequestAsync(httpReq, httpRes, operationName).ConfigureAwait(false);
                }
                finally
                {
                    httpRes.Close();
                    var statusCode = httpRes.StatusCode;

                    var duration = DateTime.Now - date;

                    if (enableLog)
                    {
                        LoggerUtils.LogResponse(_logger, statusCode, urlToLog, remoteIp, duration);
                    }
                }
            }

            throw new NotImplementedException("Cannot execute handler: " + handler + " at PathInfo: " + httpReq.PathInfo);
        }