Merge branch '6.2.x'
This commit is contained in:
@@ -19,6 +19,6 @@ from where they are handled according to their destination prefix. As the channe
|
|||||||
a `ThreadPoolExecutor`, messages are processed in different threads, and the resulting sequence
|
a `ThreadPoolExecutor`, messages are processed in different threads, and the resulting sequence
|
||||||
of handling may not match the exact order in which they were received.
|
of handling may not match the exact order in which they were received.
|
||||||
|
|
||||||
To enable ordered publishing, set the `setPreserveReceiveOrder` flag as follows:
|
To enable ordered receiving, set the `setPreserveReceiveOrder` flag as follows:
|
||||||
|
|
||||||
include-code::./ReceiveOrderWebSocketConfiguration[tag=snippet,indent=0]
|
include-code::./ReceiveOrderWebSocketConfiguration[tag=snippet,indent=0]
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2002-2018 the original author or authors.
|
* Copyright 2002-2015 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -50,19 +50,38 @@ public class ServerResponseResultHandler implements HandlerResultHandler, Initia
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Configure HTTP message writers to serialize the request body with.
|
* Configure HTTP message writers to serialize the request body with.
|
||||||
* <p>By default this is set to {@link ServerCodecConfigurer}'s default writers.
|
* <p>By default, this is set to {@link ServerCodecConfigurer}'s default writers.
|
||||||
*/
|
*/
|
||||||
public void setMessageWriters(List<HttpMessageWriter<?>> configurer) {
|
public void setMessageWriters(List<HttpMessageWriter<?>> configurer) {
|
||||||
this.messageWriters = configurer;
|
this.messageWriters = configurer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return the configured {@link HttpMessageWriter}'s.
|
||||||
|
* @since 6.2.3
|
||||||
|
*/
|
||||||
|
public List<HttpMessageWriter<?>> getMessageWriters() {
|
||||||
|
return this.messageWriters;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set the current view resolvers.
|
||||||
|
*/
|
||||||
public void setViewResolvers(List<ViewResolver> viewResolvers) {
|
public void setViewResolvers(List<ViewResolver> viewResolvers) {
|
||||||
this.viewResolvers = viewResolvers;
|
this.viewResolvers = viewResolvers;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return the configured {@link ViewResolver}'s.
|
||||||
|
* @since 6.2.3
|
||||||
|
*/
|
||||||
|
public List<ViewResolver> getViewResolvers() {
|
||||||
|
return this.viewResolvers;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the order for this result handler relative to others.
|
* Set the order for this result handler relative to others.
|
||||||
* <p>By default set to 0. It is generally safe to place it early in the
|
* <p>By default, set to 0. It is generally safe to place it early in the
|
||||||
* order as it looks for a concrete return type.
|
* order as it looks for a concrete return type.
|
||||||
*/
|
*/
|
||||||
public void setOrder(int order) {
|
public void setOrder(int order) {
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2002-2024 the original author or authors.
|
* Copyright 2002-2025 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -22,6 +22,7 @@ import java.security.Principal;
|
|||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
import java.util.Set;
|
||||||
import java.util.function.Predicate;
|
import java.util.function.Predicate;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
@@ -65,6 +66,9 @@ import org.springframework.web.server.ServerWebInputException;
|
|||||||
*/
|
*/
|
||||||
public class HandshakeWebSocketService implements WebSocketService, Lifecycle {
|
public class HandshakeWebSocketService implements WebSocketService, Lifecycle {
|
||||||
|
|
||||||
|
// For WebSocket upgrades in HTTP/2 (see RFC 8441)
|
||||||
|
private static final HttpMethod CONNECT_METHOD = HttpMethod.valueOf("CONNECT");
|
||||||
|
|
||||||
private static final String SEC_WEBSOCKET_KEY = "Sec-WebSocket-Key";
|
private static final String SEC_WEBSOCKET_KEY = "Sec-WebSocket-Key";
|
||||||
|
|
||||||
private static final String SEC_WEBSOCKET_PROTOCOL = "Sec-WebSocket-Protocol";
|
private static final String SEC_WEBSOCKET_PROTOCOL = "Sec-WebSocket-Protocol";
|
||||||
@@ -194,9 +198,9 @@ public class HandshakeWebSocketService implements WebSocketService, Lifecycle {
|
|||||||
HttpMethod method = request.getMethod();
|
HttpMethod method = request.getMethod();
|
||||||
HttpHeaders headers = request.getHeaders();
|
HttpHeaders headers = request.getHeaders();
|
||||||
|
|
||||||
if (HttpMethod.GET != method) {
|
if (HttpMethod.GET != method && CONNECT_METHOD != method) {
|
||||||
return Mono.error(new MethodNotAllowedException(
|
return Mono.error(new MethodNotAllowedException(
|
||||||
request.getMethod(), Collections.singleton(HttpMethod.GET)));
|
request.getMethod(), Set.of(HttpMethod.GET, CONNECT_METHOD)));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!"WebSocket".equalsIgnoreCase(headers.getUpgrade())) {
|
if (!"WebSocket".equalsIgnoreCase(headers.getUpgrade())) {
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2002-2024 the original author or authors.
|
* Copyright 2002-2025 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -25,6 +25,7 @@ import java.util.Collections;
|
|||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Locale;
|
import java.util.Locale;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
import org.apache.commons.logging.Log;
|
import org.apache.commons.logging.Log;
|
||||||
import org.apache.commons.logging.LogFactory;
|
import org.apache.commons.logging.LogFactory;
|
||||||
@@ -67,6 +68,10 @@ import org.springframework.web.socket.server.standard.StandardWebSocketUpgradeSt
|
|||||||
*/
|
*/
|
||||||
public abstract class AbstractHandshakeHandler implements HandshakeHandler, Lifecycle {
|
public abstract class AbstractHandshakeHandler implements HandshakeHandler, Lifecycle {
|
||||||
|
|
||||||
|
// For WebSocket upgrades in HTTP/2 (see RFC 8441)
|
||||||
|
private static final HttpMethod CONNECT_METHOD = HttpMethod.valueOf("CONNECT");
|
||||||
|
|
||||||
|
|
||||||
protected final Log logger = LogFactory.getLog(getClass());
|
protected final Log logger = LogFactory.getLog(getClass());
|
||||||
|
|
||||||
private final RequestUpgradeStrategy requestUpgradeStrategy;
|
private final RequestUpgradeStrategy requestUpgradeStrategy;
|
||||||
@@ -169,11 +174,12 @@ public abstract class AbstractHandshakeHandler implements HandshakeHandler, Life
|
|||||||
logger.trace("Processing request " + request.getURI() + " with headers=" + headers);
|
logger.trace("Processing request " + request.getURI() + " with headers=" + headers);
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
if (HttpMethod.GET != request.getMethod()) {
|
HttpMethod httpMethod = request.getMethod();
|
||||||
|
if (HttpMethod.GET != httpMethod && CONNECT_METHOD != httpMethod) {
|
||||||
response.setStatusCode(HttpStatus.METHOD_NOT_ALLOWED);
|
response.setStatusCode(HttpStatus.METHOD_NOT_ALLOWED);
|
||||||
response.getHeaders().setAllow(Collections.singleton(HttpMethod.GET));
|
response.getHeaders().setAllow(Set.of(HttpMethod.GET, CONNECT_METHOD));
|
||||||
if (logger.isErrorEnabled()) {
|
if (logger.isErrorEnabled()) {
|
||||||
logger.error("Handshake failed due to unexpected HTTP method: " + request.getMethod());
|
logger.error("Handshake failed due to unexpected HTTP method: " + httpMethod);
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@@ -255,7 +261,7 @@ public abstract class AbstractHandshakeHandler implements HandshakeHandler, Life
|
|||||||
|
|
||||||
protected void handleWebSocketVersionNotSupported(ServerHttpRequest request, ServerHttpResponse response) {
|
protected void handleWebSocketVersionNotSupported(ServerHttpRequest request, ServerHttpResponse response) {
|
||||||
if (logger.isErrorEnabled()) {
|
if (logger.isErrorEnabled()) {
|
||||||
String version = request.getHeaders().getFirst("Sec-WebSocket-Version");
|
String version = request.getHeaders().getFirst(WebSocketHttpHeaders.SEC_WEBSOCKET_VERSION);
|
||||||
logger.error(LogFormatUtils.formatValue(
|
logger.error(LogFormatUtils.formatValue(
|
||||||
"Handshake failed due to unsupported WebSocket version: " + version +
|
"Handshake failed due to unsupported WebSocket version: " + version +
|
||||||
". Supported versions: " + Arrays.toString(getSupportedVersions()), -1, true));
|
". Supported versions: " + Arrays.toString(getSupportedVersions()), -1, true));
|
||||||
|
|||||||
Reference in New Issue
Block a user