HttpListener returns 错误请求 400
HttpListener returns bad request 400
我有下一个问题。我有一个使用 HttpListener 用 c# 编写的 windows 服务。我服务器的代码 class:
public class SoaphttpServer
{
private HttpListener _listener;
private readonly IniFile _settings;
public bool Terminated { get; private set; }
public void Terminate()
{
Terminated = true;
Common.Cts.Cancel();
}
public SoaphttpServer()
{
_settings = Common.ReadSettings();
Terminated = false;
ServicePointManager.DefaultConnectionLimit = 500;
ServicePointManager.Expect100Continue = false;
ServicePointManager.MaxServicePoints = 500;
}
public void StartServer()
{
try
{
Common.Cts = new CancellationTokenSource();
_listener = new HttpListener();
_listener.Prefixes.Add("http://*:8012/");
_listener.Start();
while (!Terminated)
{
IAsyncResult result = _listener.BeginGetContext(ListenerCallback, _listener);
while (!result.AsyncWaitHandle.WaitOne(1000))
{
if (Terminated) break;
}
}
}
catch (Exception ex)
{
Log.Write("StartServer: " + ex.Message);
}
}
public static async void ListenerCallback(IAsyncResult result)
{
Log.Write("new connection");
HttpListener listener = (HttpListener)result.AsyncState;
HttpListenerContext context = listener.EndGetContext(result);
SoapHttpClient client = new SoapHttpClient(context);
await client.SomeFuncAsync();
}
~SoaphttpServer()
{
if (_listener == null) return;
_listener.Stop();
_listener.Close();
}
}
在命令行中我执行了下一个命令:
netsh http add urlacl url="http://*:8012/" user="NETWORK SERVICE"
所有地方的一切都很好。我可以使用 IdHTTP 接受来自浏览器或来自 delphi 程序的连接。但是,当我尝试从一个程序(我没有来自该程序的代码)连接到我的服务时,该程序以 delphi 编写,我进入了该程序:"HTTP/1.1 400 Bad Request"。该程序的先前版本适用于我的服务。我知道这个程序中的通信协议没有变化。我发现使用 Wireshark GET 数据包到达我的计算机,但是,正如我认为 HttpListener 形成此响应(错误请求)并在没有我的情况下发回它。可能是什么问题?也许我可以覆盖 HttpListener 的一些方法并查看来自该程序的传入请求并找出哪里出了问题?
更新。我发现 HttpListener 是密封的 class。我怎样才能找到麻烦的地方?
谢谢大家!我找到了解决方案。
都是因为默认情况下HttpListener 无法解析长度超过255 个符号的GET 请求。
要解决此问题,您需要执行以下步骤:
添加到 HKEY_LOCAL_MACHINE/SYSTEM/CurrentControlSet/services/HTTP/Parameters DWORD(32 位)密钥并将其命名为 "UrlSegmentMaxLength" 并设置值 = 0。
接下来需要重启http服务:
网络启动http
净停止 http
仅此而已!一切正常!
我有下一个问题。我有一个使用 HttpListener 用 c# 编写的 windows 服务。我服务器的代码 class:
public class SoaphttpServer
{
private HttpListener _listener;
private readonly IniFile _settings;
public bool Terminated { get; private set; }
public void Terminate()
{
Terminated = true;
Common.Cts.Cancel();
}
public SoaphttpServer()
{
_settings = Common.ReadSettings();
Terminated = false;
ServicePointManager.DefaultConnectionLimit = 500;
ServicePointManager.Expect100Continue = false;
ServicePointManager.MaxServicePoints = 500;
}
public void StartServer()
{
try
{
Common.Cts = new CancellationTokenSource();
_listener = new HttpListener();
_listener.Prefixes.Add("http://*:8012/");
_listener.Start();
while (!Terminated)
{
IAsyncResult result = _listener.BeginGetContext(ListenerCallback, _listener);
while (!result.AsyncWaitHandle.WaitOne(1000))
{
if (Terminated) break;
}
}
}
catch (Exception ex)
{
Log.Write("StartServer: " + ex.Message);
}
}
public static async void ListenerCallback(IAsyncResult result)
{
Log.Write("new connection");
HttpListener listener = (HttpListener)result.AsyncState;
HttpListenerContext context = listener.EndGetContext(result);
SoapHttpClient client = new SoapHttpClient(context);
await client.SomeFuncAsync();
}
~SoaphttpServer()
{
if (_listener == null) return;
_listener.Stop();
_listener.Close();
}
}
在命令行中我执行了下一个命令:
netsh http add urlacl url="http://*:8012/" user="NETWORK SERVICE"
所有地方的一切都很好。我可以使用 IdHTTP 接受来自浏览器或来自 delphi 程序的连接。但是,当我尝试从一个程序(我没有来自该程序的代码)连接到我的服务时,该程序以 delphi 编写,我进入了该程序:"HTTP/1.1 400 Bad Request"。该程序的先前版本适用于我的服务。我知道这个程序中的通信协议没有变化。我发现使用 Wireshark GET 数据包到达我的计算机,但是,正如我认为 HttpListener 形成此响应(错误请求)并在没有我的情况下发回它。可能是什么问题?也许我可以覆盖 HttpListener 的一些方法并查看来自该程序的传入请求并找出哪里出了问题?
更新。我发现 HttpListener 是密封的 class。我怎样才能找到麻烦的地方?
谢谢大家!我找到了解决方案。
都是因为默认情况下HttpListener 无法解析长度超过255 个符号的GET 请求。 要解决此问题,您需要执行以下步骤:
添加到 HKEY_LOCAL_MACHINE/SYSTEM/CurrentControlSet/services/HTTP/Parameters DWORD(32 位)密钥并将其命名为 "UrlSegmentMaxLength" 并设置值 = 0。
接下来需要重启http服务:
网络启动http 净停止 http
仅此而已!一切正常!