问候!
我一直在玩C#(再次),现在我已经坚持使用简单的HTTP Web服务器实现了。老实说,我不想与HTTP规范相处 - 我只需要编写一个非常 tiny (读作简单)HTTP Web服务器。我鼓励这个问题:客户端向服务器发送请求,然后服务器解析它,运行一些操作,构建响应并将其发送回客户端。这似乎是显而易见的(至少对我而言)。
这是我到目前为止所得到的:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Net;
using System.Net.Sockets;
using System.IO;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
TcpListener listener = new TcpListener(IPAddress.Any, 80);
listener.Start();
Socket sock = listener.AcceptSocket();
try
{
Stream s = new NetworkStream(sock);
s.ReadTimeout = 300;
StreamReader reader = new StreamReader(s);
StreamWriter writer = new StreamWriter(s);
writer.AutoFlush = true;
Console.WriteLine("Client stream read:\r\n");
string str = "none";
while (sock.Connected && !reader.EndOfStream && str.Length > 0) // here's where i'm stuck
{
str = reader.ReadLine();
Console.WriteLine("{0} ({1})", str, str.Length);
}
Console.WriteLine("Sending response...\r\n");
{
string response = "<h1>404: Page Not Found</h1>";
writer.WriteLine("HTTP / 1.1 404 Not Found");
writer.WriteLine("Content-Type: text/html; charset=utf-8");
writer.WriteLine("Content-Length: {0}", response.Length);
writer.WriteLine("\r\n{0}", response);
}
Console.WriteLine("Client: over\r\n");
s.Close();
sock.Close();
}
catch (Exception e)
{
Console.WriteLine("Exception: {0}\r\nTrace: \r\n{1}", e.Message, e.StackTrace);
}
Console.ReadKey();
}
}
}
但是我遇到了一个“水下石头”:我正在通过输入流读取请求,因此当他的浏览器中的客户端关闭页面时,输入数据流将被终止(让我们谈谈最明显的动作,不包括curl,w3和其他“怪人的东西”)。
所以,问题是:如何确定请求'结束?例如。我何时应该停止阅读请求数据并开始发送响应?
答案 0 :(得分:2)
为什么不使用HttpListener?您可以在5行代码中拥有一个简单的HTTP服务器。
答案 1 :(得分:1)
This Wikipedia article非常简洁地解释了请求消息格式。
请求行和标题必须以&lt; CR&gt;&lt; LF&gt;结尾(即回车后跟换行)。空行必须仅包含&lt; CR&gt;&lt; LF&gt;而且没有其他的空白。在HTTP / 1.1协议中,除Host之外的所有头都是可选的。
基本上,请在标题和/或潜在邮件正文后面留一个空行。
根据HTTP specification,您可以使用某些标头来确定是否有邮件正文:
通过在请求的消息头中包含Content-Length或Transfer-Encoding头字段来表示请求中是否存在消息正文。
答案 2 :(得分:0)
另一个选择是这个: http://webserver.codeplex.com/ 即使你不想使用它,你也可以偷走想法,因为它实现了完整的请求生命周期。