From 8e67b7b2cf8e769ac56f779ea81fe8285e5f7020 Mon Sep 17 00:00:00 2001 From: Jacob Severson Date: Thu, 5 Dec 2019 21:09:38 -0600 Subject: [PATCH 1/2] Expose proxyPing Reactor Netty WebSocket See gh-24331 --- .../client/ReactorNettyWebSocketClient.java | 26 ++++++++++++++++++- .../ReactorNettyRequestUpgradeStrategy.java | 26 ++++++++++++++++++- 2 files changed, 50 insertions(+), 2 deletions(-) diff --git a/spring-webflux/src/main/java/org/springframework/web/reactive/socket/client/ReactorNettyWebSocketClient.java b/spring-webflux/src/main/java/org/springframework/web/reactive/socket/client/ReactorNettyWebSocketClient.java index d3e9f6f85e..c106b3a3c4 100644 --- a/spring-webflux/src/main/java/org/springframework/web/reactive/socket/client/ReactorNettyWebSocketClient.java +++ b/spring-webflux/src/main/java/org/springframework/web/reactive/socket/client/ReactorNettyWebSocketClient.java @@ -46,6 +46,8 @@ public class ReactorNettyWebSocketClient implements WebSocketClient { private int maxFramePayloadLength = NettyWebSocketSessionSupport.DEFAULT_FRAME_MAX_SIZE; + private boolean proxyPing = false; + private final HttpClient httpClient; @@ -95,6 +97,28 @@ public class ReactorNettyWebSocketClient implements WebSocketClient { return this.maxFramePayloadLength; } + /** + * Configure how the client handles incoming Websocket Ping frames. Setting this value to + * {@code true} causes the client to handle Ping frames as any other, allowing the + * Ping to be sent downstream if the client is used within a proxying application. Setting + * this value to {@code false} causes the client to respond automatically with a Pong frame. + * Default is {@code false}. + * + * @param proxyPing whether the client should proxy Ping frames or respond automatically + * @since 5.2 + */ + public void setProxyPing(boolean proxyPing) { + this.proxyPing = proxyPing; + } + + /** + * Return the configured {@link #setProxyPing(boolean)} + * + * @since 5.2 + */ + public boolean getProxyPing() { + return this.proxyPing; + } @Override public Mono execute(URI url, WebSocketHandler handler) { @@ -106,7 +130,7 @@ public class ReactorNettyWebSocketClient implements WebSocketClient { String protocols = StringUtils.collectionToCommaDelimitedString(handler.getSubProtocols()); return getHttpClient() .headers(nettyHeaders -> setNettyHeaders(requestHeaders, nettyHeaders)) - .websocket(protocols, getMaxFramePayloadLength()) + .websocket(protocols, getMaxFramePayloadLength(), this.proxyPing) .uri(url.toString()) .handle((inbound, outbound) -> { HttpHeaders responseHeaders = toHttpHeaders(inbound); diff --git a/spring-webflux/src/main/java/org/springframework/web/reactive/socket/server/upgrade/ReactorNettyRequestUpgradeStrategy.java b/spring-webflux/src/main/java/org/springframework/web/reactive/socket/server/upgrade/ReactorNettyRequestUpgradeStrategy.java index 85edc74852..db5ad508ad 100644 --- a/spring-webflux/src/main/java/org/springframework/web/reactive/socket/server/upgrade/ReactorNettyRequestUpgradeStrategy.java +++ b/spring-webflux/src/main/java/org/springframework/web/reactive/socket/server/upgrade/ReactorNettyRequestUpgradeStrategy.java @@ -44,6 +44,7 @@ public class ReactorNettyRequestUpgradeStrategy implements RequestUpgradeStrateg private int maxFramePayloadLength = NettyWebSocketSessionSupport.DEFAULT_FRAME_MAX_SIZE; + private boolean proxyPing = false; /** * Configure the maximum allowable frame payload length. Setting this value @@ -68,6 +69,29 @@ public class ReactorNettyRequestUpgradeStrategy implements RequestUpgradeStrateg return this.maxFramePayloadLength; } + /** + * Configure how the server handles incoming Websocket Ping frames. Setting this value to + * {@code true} causes the server to handle Ping frames as any other, allowing the + * Ping to be sent downstream if the server is used within a proxying application. Setting + * this value to {@code false} causes the server to respond automatically with a Pong frame. + * Default is {@code false}. + * + * @param proxyPing whether the server should proxy Ping frames or respond automatically + * @since 5.2 + */ + public void setProxyPing(boolean proxyPing) { + this.proxyPing = proxyPing; + } + + /** + * Return the configured {@link #setProxyPing(boolean)} + * + * @since 5.2 + */ + public boolean getProxyPing() { + return this.proxyPing; + } + @Override public Mono upgrade(ServerWebExchange exchange, WebSocketHandler handler, @@ -78,7 +102,7 @@ public class ReactorNettyRequestUpgradeStrategy implements RequestUpgradeStrateg HandshakeInfo handshakeInfo = handshakeInfoFactory.get(); NettyDataBufferFactory bufferFactory = (NettyDataBufferFactory) response.bufferFactory(); - return reactorResponse.sendWebsocket(subProtocol, this.maxFramePayloadLength, + return reactorResponse.sendWebsocket(subProtocol, this.maxFramePayloadLength, this.proxyPing, (in, out) -> { ReactorNettyWebSocketSession session = new ReactorNettyWebSocketSession( From b1d93bb307ed7ff1d63492251fe4f584bd716d7e Mon Sep 17 00:00:00 2001 From: Rossen Stoyanchev Date: Thu, 16 Jan 2020 14:16:56 +0000 Subject: [PATCH 2/2] Polishing contribution See gh-24367 --- .../client/ReactorNettyWebSocketClient.java | 42 ++++++++++--------- .../ReactorNettyRequestUpgradeStrategy.java | 37 ++++++++-------- 2 files changed, 41 insertions(+), 38 deletions(-) diff --git a/spring-webflux/src/main/java/org/springframework/web/reactive/socket/client/ReactorNettyWebSocketClient.java b/spring-webflux/src/main/java/org/springframework/web/reactive/socket/client/ReactorNettyWebSocketClient.java index c106b3a3c4..e530381632 100644 --- a/spring-webflux/src/main/java/org/springframework/web/reactive/socket/client/ReactorNettyWebSocketClient.java +++ b/spring-webflux/src/main/java/org/springframework/web/reactive/socket/client/ReactorNettyWebSocketClient.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2019 the original author or authors. + * Copyright 2002-2020 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -44,12 +44,13 @@ public class ReactorNettyWebSocketClient implements WebSocketClient { private static final Log logger = LogFactory.getLog(ReactorNettyWebSocketClient.class); - private int maxFramePayloadLength = NettyWebSocketSessionSupport.DEFAULT_FRAME_MAX_SIZE; - - private boolean proxyPing = false; private final HttpClient httpClient; + private int maxFramePayloadLength = NettyWebSocketSessionSupport.DEFAULT_FRAME_MAX_SIZE; + + private boolean handlePing; + /** * Default constructor. @@ -67,6 +68,7 @@ public class ReactorNettyWebSocketClient implements WebSocketClient { this.httpClient = httpClient; } + /** * Return the configured {@link HttpClient}. */ @@ -98,26 +100,26 @@ public class ReactorNettyWebSocketClient implements WebSocketClient { } /** - * Configure how the client handles incoming Websocket Ping frames. Setting this value to - * {@code true} causes the client to handle Ping frames as any other, allowing the - * Ping to be sent downstream if the client is used within a proxying application. Setting - * this value to {@code false} causes the client to respond automatically with a Pong frame. - * Default is {@code false}. - * - * @param proxyPing whether the client should proxy Ping frames or respond automatically - * @since 5.2 + * Configure whether to let ping frames through to be handled by the + * {@link WebSocketHandler} given to the execute method. By default, Reactor + * Netty automatically replies with pong frames in response to pings. This is + * useful in a proxy for allowing ping and pong frames through. + *

By default this is set to {@code false} in which case ping frames are + * handled automatically by Reactor Netty. If set to {@code true}, ping + * frames will be passed through to the {@link WebSocketHandler}. + * @param handlePing whether to let Ping frames through for handling + * @since 5.2.4 */ - public void setProxyPing(boolean proxyPing) { - this.proxyPing = proxyPing; + public void setHandlePing(boolean handlePing) { + this.handlePing = handlePing; } /** - * Return the configured {@link #setProxyPing(boolean)} - * - * @since 5.2 + * Return the configured {@link #setHandlePing(boolean)}. + * @since 5.2.4 */ - public boolean getProxyPing() { - return this.proxyPing; + public boolean getHandlePing() { + return this.handlePing; } @Override @@ -130,7 +132,7 @@ public class ReactorNettyWebSocketClient implements WebSocketClient { String protocols = StringUtils.collectionToCommaDelimitedString(handler.getSubProtocols()); return getHttpClient() .headers(nettyHeaders -> setNettyHeaders(requestHeaders, nettyHeaders)) - .websocket(protocols, getMaxFramePayloadLength(), this.proxyPing) + .websocket(protocols, getMaxFramePayloadLength(), this.handlePing) .uri(url.toString()) .handle((inbound, outbound) -> { HttpHeaders responseHeaders = toHttpHeaders(inbound); diff --git a/spring-webflux/src/main/java/org/springframework/web/reactive/socket/server/upgrade/ReactorNettyRequestUpgradeStrategy.java b/spring-webflux/src/main/java/org/springframework/web/reactive/socket/server/upgrade/ReactorNettyRequestUpgradeStrategy.java index db5ad508ad..afd8315f6c 100644 --- a/spring-webflux/src/main/java/org/springframework/web/reactive/socket/server/upgrade/ReactorNettyRequestUpgradeStrategy.java +++ b/spring-webflux/src/main/java/org/springframework/web/reactive/socket/server/upgrade/ReactorNettyRequestUpgradeStrategy.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2019 the original author or authors. + * Copyright 2002-2020 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -44,7 +44,8 @@ public class ReactorNettyRequestUpgradeStrategy implements RequestUpgradeStrateg private int maxFramePayloadLength = NettyWebSocketSessionSupport.DEFAULT_FRAME_MAX_SIZE; - private boolean proxyPing = false; + private boolean handlePing = false; + /** * Configure the maximum allowable frame payload length. Setting this value @@ -70,26 +71,26 @@ public class ReactorNettyRequestUpgradeStrategy implements RequestUpgradeStrateg } /** - * Configure how the server handles incoming Websocket Ping frames. Setting this value to - * {@code true} causes the server to handle Ping frames as any other, allowing the - * Ping to be sent downstream if the server is used within a proxying application. Setting - * this value to {@code false} causes the server to respond automatically with a Pong frame. - * Default is {@code false}. - * - * @param proxyPing whether the server should proxy Ping frames or respond automatically - * @since 5.2 + * Configure whether to let ping frames through to be handled by the + * {@link WebSocketHandler} given to the upgrade method. By default, Reactor + * Netty automatically replies with pong frames in response to pings. This is + * useful in a proxy for allowing ping and pong frames through. + *

By default this is set to {@code false} in which case ping frames are + * handled automatically by Reactor Netty. If set to {@code true}, ping + * frames will be passed through to the {@link WebSocketHandler}. + * @param handlePing whether to let Ping frames through for handling + * @since 5.2.4 */ - public void setProxyPing(boolean proxyPing) { - this.proxyPing = proxyPing; + public void setHandlePing(boolean handlePing) { + this.handlePing = handlePing; } /** - * Return the configured {@link #setProxyPing(boolean)} - * - * @since 5.2 + * Return the configured {@link #setHandlePing(boolean)}. + * @since 5.2.4 */ - public boolean getProxyPing() { - return this.proxyPing; + public boolean getHandlePing() { + return this.handlePing; } @@ -102,7 +103,7 @@ public class ReactorNettyRequestUpgradeStrategy implements RequestUpgradeStrateg HandshakeInfo handshakeInfo = handshakeInfoFactory.get(); NettyDataBufferFactory bufferFactory = (NettyDataBufferFactory) response.bufferFactory(); - return reactorResponse.sendWebsocket(subProtocol, this.maxFramePayloadLength, this.proxyPing, + return reactorResponse.sendWebsocket(subProtocol, this.maxFramePayloadLength, this.handlePing, (in, out) -> { ReactorNettyWebSocketSession session = new ReactorNettyWebSocketSession(