Skip to content

Commit 177e082

Browse files
committed
Refactor SockJS and WebSocket layer configuration
Add HandlerProvider<T> class Modify HandshakeHandler to accept + adapt WebSocketHandler at runtime Modify SockJsService to accept + adapt SockJsHandler at runtime
1 parent 71e8206 commit 177e082

File tree

48 files changed

+913
-823
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

48 files changed

+913
-823
lines changed

spring-websocket/src/main/java/org/springframework/sockjs/SockJsSessionFactory.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,6 @@
2424
*/
2525
public interface SockJsSessionFactory<S extends SockJsSession>{
2626

27-
S createSession(String sessionId);
27+
S createSession(String sessionId, SockJsHandler sockJsHandler);
2828

2929
}

spring-websocket/src/main/java/org/springframework/sockjs/SockJsSessionSupport.java

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ public abstract class SockJsSessionSupport implements SockJsSession {
4949
*/
5050
public SockJsSessionSupport(String sessionId, SockJsHandler sockJsHandler) {
5151
Assert.notNull(sessionId, "sessionId is required");
52-
Assert.notNull(sockJsHandler, "SockJsHandler is required");
52+
Assert.notNull(sockJsHandler, "sockJsHandler is required");
5353
this.sessionId = sessionId;
5454
this.sockJsHandler = sockJsHandler;
5555
}
@@ -58,10 +58,6 @@ public String getId() {
5858
return this.sessionId;
5959
}
6060

61-
public SockJsHandler getSockJsHandler() {
62-
return this.sockJsHandler;
63-
}
64-
6561
public boolean isNew() {
6662
return State.NEW.equals(this.state);
6763
}

spring-websocket/src/main/java/org/springframework/sockjs/server/AbstractServerSession.java

Lines changed: 2 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -42,16 +42,11 @@ public abstract class AbstractServerSession extends SockJsSessionSupport {
4242
private ScheduledFuture<?> heartbeatTask;
4343

4444

45-
public AbstractServerSession(String sessionId, SockJsConfiguration sockJsConfig) {
46-
super(sessionId, getSockJsHandler(sockJsConfig));
45+
public AbstractServerSession(String sessionId, SockJsConfiguration sockJsConfig, SockJsHandler sockJsHandler) {
46+
super(sessionId, sockJsHandler);
4747
this.sockJsConfig = sockJsConfig;
4848
}
4949

50-
private static SockJsHandler getSockJsHandler(SockJsConfiguration sockJsConfig) {
51-
Assert.notNull(sockJsConfig, "sockJsConfig is required");
52-
return sockJsConfig.getSockJsHandler();
53-
}
54-
5550
protected SockJsConfiguration getSockJsConfig() {
5651
return this.sockJsConfig;
5752
}

spring-websocket/src/main/java/org/springframework/sockjs/server/AbstractSockJsService.java

Lines changed: 28 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -32,11 +32,13 @@
3232
import org.springframework.http.server.ServerHttpResponse;
3333
import org.springframework.scheduling.TaskScheduler;
3434
import org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler;
35+
import org.springframework.sockjs.SockJsHandler;
3536
import org.springframework.util.Assert;
3637
import org.springframework.util.CollectionUtils;
3738
import org.springframework.util.DigestUtils;
3839
import org.springframework.util.ObjectUtils;
3940
import org.springframework.util.StringUtils;
41+
import org.springframework.web.util.UriUtils;
4042

4143

4244
/**
@@ -45,7 +47,7 @@
4547
* @author Rossen Stoyanchev
4648
* @since 4.0
4749
*/
48-
public abstract class AbstractSockJsService implements SockJsConfiguration {
50+
public abstract class AbstractSockJsService implements SockJsService, SockJsConfiguration {
4951

5052
protected final Log logger = LogFactory.getLog(getClass());
5153

@@ -169,10 +171,20 @@ public void setHeartbeatScheduler(TaskScheduler heartbeatScheduler) {
169171
this.heartbeatScheduler = heartbeatScheduler;
170172
}
171173

174+
/**
175+
* The amount of time in milliseconds before a client is considered
176+
* disconnected after not having a receiving connection, i.e. an active
177+
* connection over which the server can send data to the client.
178+
* <p>
179+
* The default value is 5000.
180+
*/
172181
public void setDisconnectDelay(long disconnectDelay) {
173182
this.disconnectDelay = disconnectDelay;
174183
}
175184

185+
/**
186+
* Return the amount of time in milliseconds before a client is considered disconnected.
187+
*/
176188
public long getDisconnectDelay() {
177189
return this.disconnectDelay;
178190
}
@@ -191,7 +203,7 @@ public void setWebSocketsEnabled(boolean webSocketsEnabled) {
191203
* Whether WebSocket transport is enabled.
192204
* @see #setWebSocketsEnabled(boolean)
193205
*/
194-
public boolean isWebSocketsEnabled() {
206+
public boolean isWebSocketEnabled() {
195207
return this.webSocketsEnabled;
196208
}
197209

@@ -205,8 +217,8 @@ public boolean isWebSocketsEnabled() {
205217
*
206218
* @throws Exception
207219
*/
208-
public final void handleRequest(ServerHttpRequest request, ServerHttpResponse response, String sockJsPath)
209-
throws Exception {
220+
public final void handleRequest(ServerHttpRequest request, ServerHttpResponse response,
221+
String sockJsPath, SockJsHandler sockJsHandler) throws Exception {
210222

211223
logger.debug(request.getMethod() + " [" + sockJsPath + "]");
212224

@@ -217,6 +229,10 @@ public final void handleRequest(ServerHttpRequest request, ServerHttpResponse re
217229
// Ignore invalid Content-Type (TODO)
218230
}
219231

232+
String path = UriUtils.decode(request.getURI().getPath(), "URF-8");
233+
int index = path.indexOf(this.prefix);
234+
sockJsPath = path.substring(index + this.prefix.length());
235+
220236
try {
221237
if (sockJsPath.equals("") || sockJsPath.equals("/")) {
222238
response.getHeaders().setContentType(new MediaType("text", "plain", Charset.forName("UTF-8")));
@@ -232,7 +248,7 @@ else if (sockJsPath.matches("/iframe[0-9-.a-z_]*.html")) {
232248
return;
233249
}
234250
else if (sockJsPath.equals("/websocket")) {
235-
handleRawWebSocket(request, response);
251+
handleRawWebSocketRequest(request, response, sockJsHandler);
236252
return;
237253
}
238254

@@ -252,18 +268,19 @@ else if (sockJsPath.equals("/websocket")) {
252268
return;
253269
}
254270

255-
handleTransportRequest(request, response, sessionId, TransportType.fromValue(transport));
271+
handleTransportRequest(request, response, sessionId, TransportType.fromValue(transport), sockJsHandler);
256272
}
257273
finally {
258274
response.flush();
259275
}
260276
}
261277

262-
protected abstract void handleRawWebSocket(ServerHttpRequest request, ServerHttpResponse response)
263-
throws Exception;
278+
protected abstract void handleRawWebSocketRequest(ServerHttpRequest request, ServerHttpResponse response,
279+
SockJsHandler sockJsHandler) throws Exception;
264280

265281
protected abstract void handleTransportRequest(ServerHttpRequest request, ServerHttpResponse response,
266-
String sessionId, TransportType transportType) throws Exception;
282+
String sessionId, TransportType transportType, SockJsHandler sockJsHandler) throws Exception;
283+
267284

268285
protected boolean validateRequest(String serverId, String sessionId, String transport) {
269286

@@ -278,7 +295,7 @@ protected boolean validateRequest(String serverId, String sessionId, String tran
278295
return false;
279296
}
280297

281-
if (!isWebSocketsEnabled() && transport.equals(TransportType.WEBSOCKET.value())) {
298+
if (!isWebSocketEnabled() && transport.equals(TransportType.WEBSOCKET.value())) {
282299
logger.debug("Websocket transport is disabled");
283300
return false;
284301
}
@@ -344,7 +361,7 @@ public void handle(ServerHttpRequest request, ServerHttpResponse response) throw
344361
addCorsHeaders(request, response);
345362
addNoCacheHeaders(response);
346363

347-
String content = String.format(INFO_CONTENT, random.nextInt(), isJsessionIdCookieRequired(), isWebSocketsEnabled());
364+
String content = String.format(INFO_CONTENT, random.nextInt(), isJsessionIdCookieRequired(), isWebSocketEnabled());
348365
response.getBody().write(content.getBytes());
349366
}
350367
else if (HttpMethod.OPTIONS.equals(request.getMethod())) {

spring-websocket/src/main/java/org/springframework/sockjs/server/TransportHandlerRegistrar.java renamed to spring-websocket/src/main/java/org/springframework/sockjs/server/ConfigurableTransportHandler.java

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,24 +5,36 @@
55
* you may not use this file except in compliance with the License.
66
* You may obtain a copy of the License at
77
*
8-
* http://www.apache.org/licenses/LICENSE-2.0
8+
* http://www.apache.org/licenses/LICENSE-2.0
99
*
1010
* Unless required by applicable law or agreed to in writing, software
1111
* distributed under the License is distributed on an "AS IS" BASIS,
1212
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1313
* See the License for the specific language governing permissions and
1414
* limitations under the License.
1515
*/
16+
1617
package org.springframework.sockjs.server;
1718

19+
import java.util.Collection;
20+
21+
import org.springframework.sockjs.SockJsHandler;
22+
import org.springframework.websocket.WebSocketHandler;
23+
1824

1925
/**
2026
*
2127
* @author Rossen Stoyanchev
2228
* @since 4.0
2329
*/
24-
public interface TransportHandlerRegistrar {
30+
public interface ConfigurableTransportHandler extends TransportHandler {
31+
32+
void setSockJsConfiguration(SockJsConfiguration sockJsConfig);
2533

26-
void registerTransportHandlers(TransportHandlerRegistry registry, SockJsConfiguration config);
34+
/**
35+
* Pre-register {@link SockJsHandler} instances so they can be adapted to
36+
* {@link WebSocketHandler} and hence re-used at runtime.
37+
*/
38+
void registerSockJsHandlers(Collection<SockJsHandler> sockJsHandlers);
2739

2840
}

spring-websocket/src/main/java/org/springframework/sockjs/server/SockJsConfiguration.java

Lines changed: 0 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -17,18 +17,14 @@
1717

1818
import org.springframework.scheduling.TaskScheduler;
1919
import org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler;
20-
import org.springframework.sockjs.SockJsHandler;
21-
2220

2321
/**
24-
*
2522
*
2623
* @author Rossen Stoyanchev
2724
* @since 4.0
2825
*/
2926
public interface SockJsConfiguration {
3027

31-
3228
/**
3329
* Streaming transports save responses on the client side and don't free
3430
* memory used by delivered messages. Such transports need to recycle the
@@ -42,15 +38,6 @@ public interface SockJsConfiguration {
4238
*/
4339
public int getStreamBytesLimit();
4440

45-
/**
46-
* The amount of time in milliseconds before a client is considered
47-
* disconnected after not having a receiving connection, i.e. an active
48-
* connection over which the server can send data to the client.
49-
* <p>
50-
* The default value is 5000.
51-
*/
52-
public long getDisconnectDelay();
53-
5441
/**
5542
* The amount of time in milliseconds when the server has not sent any
5643
* messages and after which the server should send a heartbeat frame to the
@@ -67,11 +54,4 @@ public interface SockJsConfiguration {
6754
*/
6855
public TaskScheduler getHeartbeatScheduler();
6956

70-
/**
71-
* Provides access to the {@link SockJsHandler} that will handle the request. This
72-
* method should be called once per SockJS session. It may return the same or a
73-
* different instance every time it is called.
74-
*/
75-
SockJsHandler getSockJsHandler();
76-
7757
}
Lines changed: 14 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -14,29 +14,34 @@
1414
* limitations under the License.
1515
*/
1616

17-
package org.springframework.websocket.server.endpoint.handshake;
17+
package org.springframework.sockjs.server;
1818

19-
import javax.websocket.Endpoint;
19+
import java.util.Collection;
2020

2121
import org.springframework.http.server.ServerHttpRequest;
2222
import org.springframework.http.server.ServerHttpResponse;
23+
import org.springframework.sockjs.SockJsHandler;
24+
import org.springframework.websocket.WebSocketHandler;
2325

2426

2527
/**
26-
* A strategy for performing the container-specific steps for upgrading an HTTP request
27-
* as part of a WebSocket handshake.
2828
*
2929
* @author Rossen Stoyanchev
3030
* @since 4.0
3131
*/
32-
public interface RequestUpgradeStrategy {
32+
public interface SockJsService {
3333

34-
String[] getSupportedVersions();
34+
String getPrefix();
3535

3636
/**
37-
* Invoked after the handshake checks have been performed and succeeded.
37+
* Pre-register {@link SockJsHandler} instances so they can be adapted to
38+
* {@link WebSocketHandler} and hence re-used at runtime when
39+
* {@link #handleRequest(ServerHttpRequest, ServerHttpResponse, String, SockJsHandler) handleRequest}
40+
* is called.
3841
*/
39-
void upgrade(ServerHttpRequest request, ServerHttpResponse response, String protocol, Endpoint endpoint)
40-
throws Exception;
42+
void registerSockJsHandlers(Collection<SockJsHandler> sockJsHandlers);
43+
44+
void handleRequest(ServerHttpRequest request, ServerHttpResponse response, String sockJsPath,
45+
SockJsHandler handler) throws Exception;
4146

4247
}

spring-websocket/src/main/java/org/springframework/sockjs/server/TransportHandler.java

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2013 the toriginal author or authors.
2+
* Copyright 2002-2013 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -17,6 +17,7 @@
1717

1818
import org.springframework.http.server.ServerHttpRequest;
1919
import org.springframework.http.server.ServerHttpResponse;
20+
import org.springframework.sockjs.SockJsHandler;
2021
import org.springframework.sockjs.SockJsSessionSupport;
2122

2223

@@ -29,7 +30,7 @@ public interface TransportHandler {
2930

3031
TransportType getTransportType();
3132

32-
void handleRequest(ServerHttpRequest request, ServerHttpResponse response, SockJsSessionSupport session)
33-
throws Exception;
33+
void handleRequest(ServerHttpRequest request, ServerHttpResponse response,
34+
SockJsHandler sockJsHandler, SockJsSessionSupport session) throws Exception;
3435

3536
}

spring-websocket/src/main/java/org/springframework/sockjs/server/TransportHandlerRegistry.java

Lines changed: 0 additions & 28 deletions
This file was deleted.

0 commit comments

Comments
 (0)