升级 WebSocket 🌐
Feat 支持通过通过 HttpRequest.upgrade 方法将 HTTP 请求升级为 WebSocket。
操作示例如下:
public class WebSocketDemo { public static void main(String[] args) { Feat.httpServer().httpHandler(request -> { request.upgrade(new WebSocketUpgrade() { @Override public void handleTextMessage(WebSocketRequest request, WebSocketResponse response, String message) { response.sendTextMessage("接受到客户端消息:" + message); } }); }).listen(); }}
启动程序后,可访问:WebSocket 在线测试 验证运行效果。

构造方法
WebSocketUpgrade 提供了两个构造方法,分别如下:
public WebSocketUpgrade() { this(120000);}
public WebSocketUpgrade(long idleTimeout) { this.idleTimeout = idleTimeout;}
用户可在进行 WebSocket 升级时,通过构造方法传入 idleTimeout 参数,设置 WebSocket 连接的空闲超时时间。 其中无参构造方法默认设置空闲超时时间为 120000 毫秒,即:2 分钟。
当 WebSocket 连接空闲时间超过 idleTimeout 时,Feat 会主动关闭该连接。
消息处理
WebSocketUpgrade 提供了两个消息处理方法,分别如下:
public void handle(WebSocketRequest request, WebSocketResponse response, CompletableFuture<Object> completableFuture) throws Throwable { try { handle(request, response); } finally { completableFuture.complete(null); }}
public void handle(WebSocketRequest request, WebSocketResponse response) throws Throwable { ...}
如果用户需要采用异步方式处理 WebSocket 消息,可重写带 CompletableFuture<Object>
入参的 handle 方法,并在异步处理完成后,调用 completableFuture.complete(null)
方法。
若需要同步处理 WebSocket 消息,可重写 handle(WebSocketRequest request, WebSocketResponse response)
方法。
为便于开发人员使用,WebSocketUpgrade 已经默认实现了 handle(WebSocketRequest request, WebSocketResponse response)
方法,用户可按需重写相应的方法。
public void handle(WebSocketRequest request, WebSocketResponse response) throws Throwable { try { switch (request.getFrameOpcode()) { case WebSocketUtil.OPCODE_TEXT: handleTextMessage(request, response, new String(request.getPayload(), StandardCharsets.UTF_8)); break; case WebSocketUtil.OPCODE_BINARY: handleBinaryMessage(request, response, request.getPayload()); break; case WebSocketUtil.OPCODE_CLOSE: try { onClose(request, response, new CloseReason(request.getPayload())); } finally { response.close(); } break; case WebSocketUtil.OPCODE_PING: handlePing(request, response); break; case WebSocketUtil.OPCODE_PONG: handlePong(request, response); break; case WebSocketUtil.OPCODE_CONTINUE: handleContinueMessage(request, response, request.getPayload()); break; default: throw new UnsupportedOperationException(); } } catch (Throwable throwable) { onError(request, throwable); }}
请求路由
在实际场景下,用户可能需要将不同的 WebSocket 消息路由到不同的处理方法, 以及存在 Http 请求和 WebSocket 请求共存的情况。
此时可以采用 Router
来实现请求路由,示例如下:
public class WebSocketRouterDemo { public static void main(String[] args) { Router router = new Router(); router.route("/ws1", request -> { request.upgrade(new WebSocketUpgrade() { @Override public void handleTextMessage(WebSocketRequest request, WebSocketResponse response, String message) { response.sendTextMessage("ws1接受到客户端消息:" + message); } }); }).route("/ws2", request -> { request.upgrade(new WebSocketUpgrade() { @Override public void handleTextMessage(WebSocketRequest request, WebSocketResponse response, String message) { response.sendTextMessage("ws2接受到客户端消息:" + message); } }); }).route("/http", request -> { request.getResponse().write("http".getBytes()); }); Feat.httpServer().httpHandler(router).listen(); }}