Uploaded image for project: 'Qt'
  1. Qt
  2. QTBUG-86526

QHttpServer: response pending if behing a proxy server

    XMLWordPrintable

    Details

    • Type: Bug
    • Status: Reported
    • Priority: P3: Somewhat important
    • Resolution: Unresolved
    • Affects Version/s: 5.12.10
    • Fix Version/s: None
    • Component/s: Network: HTTP
    • Labels:
      None
    • Environment:
      Ubuntu 20.04 and embedded Linux (buildroot compiled)
      lighthhtpd server as frontend
    • Platform/s:
      Linux/X11, Linux/Other display system

      Description

      When a request comes through a forward-proxy (lighttpd mod_proxy), the request is handled and the correct route is called but the response never comes back to the client until the Server is closed or disconnectFromHost is called on the socket

       

      example:

      With a proxy redirecting all call behind a /API url on port 80 or 443 to the QhttpServer (on port 9000),

      With a very simple server running on host 172.16.16.120 port 9000

       

      QCoreApplication app(argc, argv);
      QHttpServer httpServer;
      httpServer.route("/proxyTest", [] () {
              return QJsonObject({{"success", true}});;
          });
      httpServer.listen(QHostAddress::Any, 9000);
      return app.exec();
      

       

      And the lighttpd proxy running on 172.16.16.115

       

      #direct call
      bet@laptop:/home/bet$ curl "http://172.16.16.120:9000/proxyTest" {"success":true}
      
      #call through the proxy
      bet@laptop:/home/bet$ curl "http://172.16.16.115/API/proxyTest" ...
      #hang forever till the server application (QHttpServer) is closed
      {"success":true}
      

      Modifying the sendResponse function to close the socket if it's a forward request make it works but it's not a good solution for websocket and the likes, the Forwarded header is not really a standard (lighttpd still use X-Forwarded-Host in my version (1.4.54)) and it doesn't solve the root cause of the problem

       

       

      void QHttpServer::sendResponse(QHttpServerResponse &&response,
                                     const QHttpServerRequest &request,
                                     QTcpSocket *socket)
      {
          Q_D(QHttpServer);
          for (auto afterRequestHandler : d->afterRequestHandlers)
              response = std::move(afterRequestHandler(std::move(response), request));
          response.write(makeResponder(request, socket));
          if (request.headers().contains(QLatin1String("X-Forwarded-Host")))
              socket->disconnectFromHost();
      }
      

       

      The parsed url is rather strange when the request has been forwarded (see forwarded_parsed_url.txt) but I don't think that it has any impact on the socket side.

      I haven't found any cleaner way to get the responses so far.

      Don't hesitate if I can provide anything else useful,

      Bertrand

        Attachments

        1. direct_request_content.txt
          3 kB
        2. forwarded_parsed_url.txt
          1 kB
        3. forwarded_request_content.txt
          6 kB
        4. lighttpd.conf
          0.4 kB
        No reviews matched the request. Check your Options in the drop-down menu of this sections header.

          Activity

            People

            Assignee:
            mikhailsvetkin Mikhail Svetkin
            Reporter:
            thelenbertrand Bertrand Thelen
            Votes:
            0 Vote for this issue
            Watchers:
            1 Start watching this issue

              Dates

              Created:
              Updated:

                Gerrit Reviews

                There are no open Gerrit changes