本文介绍了Kestrel 服务器在“错误的请求数据"上运行缓慢的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个 IOT 设备(黑匣子,无法重新编程),它通过有线以太网将 http POST 请求(136 字节的 JSON,一个字符串)发送到我的 .NET core 2.2 非常简单的服务器控制台应用程序.我只是将字符串输出到控制台.

I have an IOT device (black box, can't reprogram it) that sends http POST requests (136 bytes of JSON, a string) over wired ethernet to my .NET core 2.2 very simple server console application.I just output the string to the console.

    [HttpPost]
    public void Post([FromBody] RootObject root)
    {
        string adv = root.prt;
        Console.WriteLine(adv);
    }

我每秒只能显示不到 1 行,有时是 2 行.

I get to display less than 1 line per second, sometimes 2.

使用 Fiddler 作为反向代理,我每秒收到 5 到 10 个 http req,这是设备的正确行为.

Using Fiddler as a reverse proxy, instead I receive between 5 and 10 http req per second, that is the correct behavior of the device.

所以我启用了信息日志,并且每秒钟都会收到这个无效请求行"错误:

So I enabled Information logs, and get this, every second, with that "Invalid request line" error:

info: Microsoft.AspNetCore.Hosting.Internal.WebHost[1]
      Request starting HTTP/1.1 POST http://192.168.0.92/api/values application/json 136
info: Microsoft.AspNetCore.Routing.EndpointMiddleware[0]
      Executing endpoint 'BluepycWeb.Controllers.ValuesController.Post (BluepycWeb)'
info: Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker[1]
      Route matched with {action = "Post", controller = "Values"}. Executing action BluepycWeb.Controllers.ValuesController.Post (BluepycWeb)
02003F002293831000010033FF0006EFAA256B6D1A001E010201061AFF4C000215476C6F62616C2D54616700000000000000000000CD0101CC0001FF001FCC
info: Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker[1]
      Executing action method BluepycWeb.Controllers.ValuesController.Post (BluepycWeb) with arguments (BluepycWeb.Controllers.RootObject) - Validation state: Valid
info: Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker[2]
      Executed action method BluepycWeb.Controllers.ValuesController.Post (BluepycWeb), returned result Microsoft.AspNetCore.Mvc.EmptyResult in 0.2158ms.
info: Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker[2]
      Executed action BluepycWeb.Controllers.ValuesController.Post (BluepycWeb) in 9.4032ms
info: Microsoft.AspNetCore.Routing.EndpointMiddleware[1]
      Executed endpoint 'BluepycWeb.Controllers.ValuesController.Post (BluepycWeb)'
info: Microsoft.AspNetCore.Hosting.Internal.WebHost[2]
      Request finished in 24.5625ms 200
info: Microsoft.AspNetCore.Server.Kestrel[17]
      Connection id "0HLMO99UNQBGM" bad request data: "Invalid request line: 'x0Dx0A'"
Microsoft.AspNetCore.Server.Kestrel.Core.BadHttpRequestException: Invalid request line: 'x0Dx0A'
   at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.HttpParser`1.RejectRequestLine(Byte* requestLine, Int32 length)
   at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.HttpParser`1.GetUnknownMethod(Byte* data, Int32 length, Int32& methodLength)
   at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.HttpParser`1.ParseRequestLine(TRequestHandler handler, Byte* data, Int32 length)
   at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.HttpParser`1.ParseRequestLine(TRequestHandler handler, ReadOnlySequence`1& buffer, SequencePosition& consumed, SequencePosition& examined)
   at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.HttpParser`1.Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.IHttpParser<TRequestHandler>.ParseRequestLine(TRequestHandler handler, ReadOnlySequence`1& buffer, SequencePosition& consumed, SequencePosition& examined)
   at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.Http1Connection.TakeStartLine(ReadOnlySequence`1 buffer, SequencePosition& consumed, SequencePosition& examined)
   at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.Http1Connection.ParseRequest(ReadOnlySequence`1 buffer, SequencePosition& consumed, SequencePosition& examined)
   at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.Http1Connection.TryParseRequest(ReadResult result, Boolean& endConnection)
   at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.HttpProtocol.ProcessRequests[TContext](IHttpApplication`1 application)
   at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.HttpProtocol.ProcessRequestsAsync[TContext](IHttpApplication`1 application)

如果我通过 Postman 连续发送相同的 JSON paylod,没有错误,没有延迟.那个错误,我不知道如何避免,也不知道是由什么产生的(但它似乎没有打扰 Fiddler)似乎让我的服务器挂了一秒钟.

If I send the same JSON paylod through Postman continuosly, no errors, no delays.That error, that I don't know how to avoid nor by what is originated (but it seems it doesn't distub Fiddler) seems to hang my server for a second.

有关如何解决此问题的任何建议?丢弃/纠正错误?保持错误但不减慢数据接收?

Any suggestion on how can I solve this problem?Discard/correct the error?Keep the error but not slowing down the data receive?

更新:使用 IISExpress 托管,没问题,没有无效请求行:'x0Dx0A'"错误,非常快.问题仅在于使用 Kestrel.

UPDATE:Hosting with IISExpress, no problem, no "Invalid request line: 'x0Dx0A'" error, very fast.Problem is only using Kestrel.

谢谢!

推荐答案

昨天我的 ASP .NETCore 服务遇到了同样的问题.然后意识到我正在向 Kestrel 服务器发送 HTTPS 请求,而它没有配置为侦听 HTTPS 协议,这就是 Kestrel 抱怨的原因.

Yesterday I had same issue with my ASP .NETCore service.Then realized I was sending HTTPS requests to my Kestrel server while it isn't configured to listen at HTTPS protocol, that's why Kestrel complaining.

如果你想在你的 kestrel 中使用 HTTPS,你有多个选项来配置它,例如:

If you want to use HTTPS in your kestrel you have multiple options to configure it, for example :

使用分配的服务器证书:

With assigned server certificate :

var host = new WebHostBuilder().UseKestrel(选项=>options.Listen(IPAddress.Any, 443, listenOptions =>listenOptions.UseHttps("MyCert.pfx")))

有多个主机名和证书:

public static IWebHostBuilder CreateWebHostBuilder(string[] args) =>
WebHost.CreateDefaultBuilder(args)
    .UseStartup<Startup>()
    .ConfigureKestrel((context, options) =>
    {
        options.ListenAnyIP(5005, listenOptions =>
        {
            listenOptions.UseHttps(httpsOptions =>
            {
                var localhostCert = CertificateLoader.LoadFromStoreCert(
                    "localhost", "My", StoreLocation.CurrentUser,
                    allowInvalid: true);
                var exampleCert = CertificateLoader.LoadFromStoreCert(
                    "example.com", "My", StoreLocation.CurrentUser,
                    allowInvalid: true);
                var subExampleCert = CertificateLoader.LoadFromStoreCert(
                    "sub.example.com", "My", StoreLocation.CurrentUser,
                    allowInvalid: true);
                var certs = new Dictionary<string, X509Certificate2>(
                    StringComparer.OrdinalIgnoreCase);
                certs["localhost"] = localhostCert;
                certs["example.com"] = exampleCert;
                certs["sub.example.com"] = subExampleCert;

                httpsOptions.ServerCertificateSelector = (connectionContext, name) =>
                {
                    if (name != null && certs.TryGetValue(name, out var cert))
                    {
                        return cert;
                    }

                    return exampleCert;
                };
            });
        });
    });

这篇关于Kestrel 服务器在“错误的请求数据"上运行缓慢的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

07-19 04:49