{"record":{"id":"db5b85fe5b9b95dd","repo":"eclipse-vertx/vert.x","slug":"invalid-connection-header","errorCode":null,"errorMessage":"Invalid connection header","messagePattern":"Invalid connection header","errorType":"http","errorClass":"WebSocketHandshakeException","httpStatus":400,"severity":"error","filePath":"vertx-core/src/main/java/io/vertx/core/http/impl/http1/Http1ServerConnection.java","lineNumber":375,"sourceCode":"        } catch (WebSocketHandshakeException e) {\n          promise.fail(e);\n          return;\n        }\n        promise.complete(new ServerWebSocketHandshaker(request, handshaker, webSocketConfig, registerWebSocketWriteHandlers));\n      }\n    });\n  }\n\n  public WebSocketServerHandshaker createHandshaker(Http1ServerRequest request) throws WebSocketHandshakeException {\n    // As a fun part, Firefox 6.0.2 supports Websockets protocol '7'. But,\n    // it doesn't send a normal 'Connection: Upgrade' header. Instead it\n    // sends: 'Connection: keep-alive, Upgrade'. Brilliant.\n    String connectionHeader = request.getHeader(io.vertx.core.http.HttpHeaders.CONNECTION);\n    if (connectionHeader == null || !connectionHeader.toLowerCase().contains(\"upgrade\")) {\n      request.response()\n        .setStatusCode(BAD_REQUEST.code())\n        .end(\"\\\"Connection\\\" header must be \\\"Upgrade\\\".\");\n      throw new WebSocketHandshakeException(\"Invalid connection header\");\n    }\n    if (request.method() != io.vertx.core.http.HttpMethod.GET) {\n      request.response()\n        .setStatusCode(METHOD_NOT_ALLOWED.code())\n        .end();\n      throw new WebSocketHandshakeException(\"Invalid HTTP method\");\n    }\n    String wsURL;\n    try {\n      wsURL = HttpUtils.getWebSocketLocation(request, isSsl());\n    } catch (Exception e) {\n      request.response()\n        .setStatusCode(BAD_REQUEST.code())\n        .end(\"Invalid request URI\");\n      throw new WebSocketHandshakeException(\"Invalid WebSocket location\", e);\n    }\n    String subProtocols = null;\n    if (webSocketConfig.getSubProtocols() != null) {","sourceCodeStart":357,"sourceCodeEnd":393,"githubUrl":"https://github.com/eclipse-vertx/vert.x/blob/fb308bd8c3f12c79f4ae89bef67fadf6c80d036e/vertx-core/src/main/java/io/vertx/core/http/impl/http1/Http1ServerConnection.java#L357-L393","documentation":"This WebSocketHandshakeException is thrown in createHandshaker when a WebSocket upgrade request lacks a \"Connection\" header containing \"Upgrade\". The HTTP/1.1 upgrade handshake requires both \"Connection: Upgrade\" and \"Upgrade: websocket\" headers. Vert.x rejects the request with a 400 response before the handshaker is created.","triggerScenarios":"Calling server upgrade methods (upgrade/createWebSocket path) with an incoming request whose Connection header is missing or does not contain \"upgrade\" (case-insensitive check), e.g. \"Connection: keep-alive\" only.","commonSituations":"Hand-rolled WebSocket clients forgetting the Connection header; proxies or intermediaries stripping or rewriting the Connection header; testing the upgrade endpoint with curl or a plain GET that lacks proper upgrade headers.","solutions":["Ensure the client sends \"Connection: Upgrade\" and \"Upgrade: websocket\" headers with the GET request.","If a proxy sits in front, configure it to forward the Connection and Upgrade headers (e.g. nginx proxy_set_header Connection $connection_upgrade).","Inspect the actual incoming headers (request.headers()) to confirm what the client sent before upgrading.","Return a clear 400 to the client when the handshake fails so the client-side code can surface the misconfiguration."],"exampleFix":"// before (client-side)\nrequest.putHeader(\"Upgrade\", \"websocket\");\n\n// after\nrequest.putHeader(\"Upgrade\", \"websocket\");\nrequest.putHeader(\"Connection\", \"Upgrade\");","handlingStrategy":"validation","validationCode":"String conn = request.getHeader(HttpHeaders.CONNECTION);\nif (conn == null || !conn.toLowerCase().contains(\"upgrade\")) {\n  // reject before upgrade\n}","typeGuard":null,"tryCatchPattern":"try {\n  serverRequest.toWebSocket();\n} catch (WebSocketHandshakeException e) {\n  log.warn(\"Bad upgrade request: \" + e.getMessage());\n}","preventionTips":["Always send \"Connection: Upgrade\" and \"Upgrade: websocket\" on handshake","Verify proxies forward hop-by-hop upgrade headers","Test handshake endpoints with a real WebSocket client, not plain curl"],"tags":["websocket","http1","handshake","headers"],"backgroundTag":"http-error-response","analyzedSha":"fb308bd8c3f12c79f4ae89bef67fadf6c80d036e","analyzedAt":"2026-09-06T11:37:12.241Z","contentChangedAt":"2026-09-06T11:37:12.241Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}