简体   繁体   English

C#和HttpListener在后台运行

[英]C# and running of HttpListener in background

I created simple HttpListener that listens to port 9090 and depending on a request's URL writes some info to the console. 我创建了一个简单的HttpListener ,它侦听端口9090,并根据请求的URL向控制台写入一些信息。

But I'm stuck :( I thought of multithreading, event based system, but I dind't manage to do anything with it. 但是我被困住了:(我想到了基于事件的多线程系统,但是我没有做任何事情。

Here is the code of my listener that I launched as a separate console app: 这是我作为单独的控制台应用程序启动的侦听器的代码:

string urlTemplate = String.Format("/prefix/{0}/suffix", id);
string prefix = String.Format("http://localhost:9090/");

HttpListener listener = new HttpListener();
listener.Prefixes.Add(prefix);

listener.Start();

Console.WriteLine("Listening to {0}...", prefix);

while (true)
{
    HttpListenerContext context = listener.GetContext();
    HttpListenerRequest request = context.Request;

    //Response object
    HttpListenerResponse response = context.Response;

    //Construct response
    if (request.RawUrl.Contains(urlTemplate) && request.HttpMethod == "POST")
    {
         string requestBody;
         Stream iStream = request.InputStream;
         Encoding encoding = request.ContentEncoding;
         StreamReader reader = new StreamReader(iStream, encoding);
         requestBody = reader.ReadToEnd();

         Console.WriteLine("POST request on {0} with body = [{1}]", request.RawUrl, requestBody);

         response.StatusCode = (int)HttpStatusCode.OK;

         //Return a response
         using (Stream stream = response.OutputStream) { }
     }
     else
     {
         response.StatusCode = (int)HttpStatusCode.BadRequest;
         Console.WriteLine("Invalid HTTP request: [{0}] {1}", request.HttpMethod, request.Url);
         using (Stream stream = response.OutputStream) { }
     }
}

I decided to use it as an utility for unit tests (maybe somewhere else). 我决定将其用作单元测试的实用程序(也许在其他地方)。 So when test starts I need to configure the listener, run it, then make some requests and receive the info (which listener wrote earlier to Console), and at the end of the test stop the listener. 因此,当测试开始时,我需要配置侦听器,运行它,然后发出一些请求并接收信息(该侦听器先前已写入控制台),然后在测试结束时停止侦听器。

My main idea was to incapsulate this listener to separate class MyHttpListener which has methods: StartListener() , StopListener() . 我的主要想法是将该侦听器封装到单独的类MyHttpListener ,该类具有以下方法: StartListener()StopListener()

But when I call StartListener() my test freezes because of infinite while loop. 但是当我调用StartListener()由于无限的while循环,我的测试冻结了。 I tried to create separate background thread or event based system, but my lack of experience with them, prevents me from doing it. 我试图创建单独的后台线程或基于事件的系统,但是由于缺乏经验,我无法这样做。 I've already spent a lot of time trying to find the solution, but all for nothing. 我已经花了很多时间试图找到解决方案,但是一切都没有。

Hope you can help me finding the solution for such trivial task. 希望您能帮助我找到此类琐碎任务的解决方案。

Thanks in advance. 提前致谢。

One of the responder's variant (it seems he deleted his post) looked good, but it didn't work for me. 响应者的一种变体(似乎他删除了自己的帖子)看起来不错,但对我而言不起作用。 I tried to fix things in order it started working, but at the end that variant gave me an idea how to solve the problem - with multithreading and events :) 我试图修复一些问题以使其开始起作用,但是最后,该变体使我有了一个解决问题的想法-多线程和事件:)

Here's what I have now and it works: 这是我现在拥有的并且可以正常工作:

public delegate void HttpListenerRequestHandler(object sender, HttpListenerEventArgs e);
public event HttpListenerRequestHandler OnCorrectRequest;

... ...

if(OnCorrectRequest != null)
    OnCorrectRequest(this, new HttpListenerEventArgs(response));
lock (threadLock)
{
    Console.WriteLine("POST request on {0} with body = [{1}]", request.RawUrl, requestBody);
}

... ...

public class HttpListenerEventArgs : EventArgs
{
    public readonly HttpListenerResponse response;
    public HttpListenerEventArgs(HttpListenerResponse httpResponse)
    {
        response = httpResponse;
    }
}

In order to receive detailed responses from HttpListener in main thread, I use the following: 为了从主线程中的HttpListener接收详细的响应,我使用以下命令:

private HttpListenerResponse response;

public void HttpCallbackRequestCorrect(object sender, HttpListenerEventArgs e)
{
    response = e.response;
    Console.WriteLine("{0} sent: {1}", sender, e.response.StatusCode);
}

Unfortunately I have the following exception which I don't know how to handle: 不幸的是,我有以下不知道如何处理的异常:

System.Net.HttpListenerException: The I/O operation has been aborted because of either a thread exit or an application request at System.Net.HttpListener.GetContext() System.Net.HttpListenerException:由于线程退出或System.Net.HttpListener.GetContext()上的应用程序请求,I / O操作已被中止

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM