101
101
import org .glassfish .grizzly .websockets .DataFrame ;
102
102
import org .glassfish .grizzly .websockets .DefaultWebSocket ;
103
103
import org .glassfish .grizzly .websockets .HandShake ;
104
+ import org .glassfish .grizzly .websockets .HandshakeException ;
104
105
import org .glassfish .grizzly .websockets .ProtocolHandler ;
105
106
import org .glassfish .grizzly .websockets .Version ;
106
107
import org .glassfish .grizzly .websockets .WebSocketEngine ;
@@ -147,7 +148,7 @@ public class GrizzlyAsyncHttpProvider implements AsyncHttpProvider {
147
148
private final static Logger LOGGER = LoggerFactory .getLogger (GrizzlyAsyncHttpProvider .class );
148
149
private static final boolean SEND_FILE_SUPPORT ;
149
150
static {
150
- SEND_FILE_SUPPORT = configSendFileSupport ();
151
+ SEND_FILE_SUPPORT = /* configSendFileSupport()*/ false ;
151
152
}
152
153
private final Attribute <HttpTransactionContext > REQUEST_STATE_ATTR =
153
154
Grizzly .DEFAULT_ATTRIBUTE_BUILDER .createAttribute (HttpTransactionContext .class .getName ());
@@ -619,6 +620,7 @@ final class HttpTransactionContext {
619
620
HandShake handshake ;
620
621
ProtocolHandler protocolHandler ;
621
622
WebSocket webSocket ;
623
+ boolean establishingTunnel ;
622
624
623
625
624
626
// -------------------------------------------------------- Constructors
@@ -677,6 +679,15 @@ void result(Object result) {
677
679
}
678
680
}
679
681
682
+ boolean isTunnelEstablished (final Connection c ) {
683
+ return c .getAttributes ().getAttribute ("tunnel-established" ) != null ;
684
+ }
685
+
686
+
687
+ void tunnelEstablished (final Connection c ) {
688
+ c .getAttributes ().setAttribute ("tunnel-established" , Boolean .TRUE );
689
+ }
690
+
680
691
681
692
} // END HttpTransactionContext
682
693
@@ -844,7 +855,9 @@ private boolean sendAsGrizzlyRequest(final Request request,
844
855
final ProxyServer proxy = getProxyServer (request );
845
856
final boolean useProxy = (proxy != null );
846
857
if (useProxy ) {
847
- if (secure ) {
858
+ if ((secure || httpCtx .isWSRequest ) && !httpCtx .isTunnelEstablished (ctx .getConnection ())) {
859
+ secure = false ;
860
+ httpCtx .establishingTunnel = true ;
848
861
builder .method (Method .CONNECT );
849
862
builder .uri (AsyncHttpProviderUtils .getAuthority (uri ));
850
863
} else {
@@ -864,7 +877,7 @@ private boolean sendAsGrizzlyRequest(final Request request,
864
877
}
865
878
866
879
HttpRequestPacket requestPacket ;
867
- if (httpCtx .isWSRequest ) {
880
+ if (httpCtx .isWSRequest && ! httpCtx . establishingTunnel ) {
868
881
try {
869
882
final URI wsURI = new URI (httpCtx .wsRequestURI );
870
883
httpCtx .protocolHandler = Version .DRAFT17 .createHandler (true );
@@ -877,7 +890,10 @@ private boolean sendAsGrizzlyRequest(final Request request,
877
890
} else {
878
891
requestPacket = builder .build ();
879
892
}
880
- requestPacket .setSecure (true );
893
+ requestPacket .setSecure (secure );
894
+ if (secure ) {
895
+ ctx .notifyDownstream (new SwitchingSSLFilter .SSLSwitchingEvent (true , ctx .getConnection ()));
896
+ }
881
897
if (!useProxy && !httpCtx .isWSRequest ) {
882
898
addQueryString (request , requestPacket );
883
899
}
@@ -1139,14 +1155,19 @@ protected void onInitialLineParsed(HttpHeader httpHeader,
1139
1155
if (httpHeader .isSkipRemainder ()) {
1140
1156
return ;
1141
1157
}
1158
+ final Connection connection = ctx .getConnection ();
1142
1159
final HttpTransactionContext context =
1143
- provider .getHttpTransactionContext (ctx . getConnection () );
1160
+ provider .getHttpTransactionContext (connection );
1144
1161
final int status = ((HttpResponsePacket ) httpHeader ).getStatus ();
1162
+ if (context .establishingTunnel && HttpStatus .OK_200 .statusMatches (status )) {
1163
+ return ;
1164
+ }
1145
1165
if (HttpStatus .CONINTUE_100 .statusMatches (status )) {
1146
1166
ctx .notifyUpstream (new ContinueEvent (context ));
1147
1167
return ;
1148
1168
}
1149
1169
1170
+
1150
1171
if (context .statusHandler != null && !context .statusHandler .handlesStatus (status )) {
1151
1172
context .statusHandler = null ;
1152
1173
context .invocationStatus = StatusHandler .InvocationStatus .CONTINUE ;
@@ -1180,9 +1201,9 @@ protected void onInitialLineParsed(HttpHeader httpHeader,
1180
1201
}
1181
1202
}
1182
1203
final GrizzlyResponseStatus responseStatus =
1183
- new GrizzlyResponseStatus ((HttpResponsePacket ) httpHeader ,
1184
- getURI (context .requestUrl ),
1185
- provider );
1204
+ new GrizzlyResponseStatus ((HttpResponsePacket ) httpHeader ,
1205
+ getURI (context .requestUrl ),
1206
+ provider );
1186
1207
context .responseStatus = responseStatus ;
1187
1208
if (context .statusHandler != null ) {
1188
1209
return ;
@@ -1193,6 +1214,10 @@ protected void onInitialLineParsed(HttpHeader httpHeader,
1193
1214
final AsyncHandler handler = context .handler ;
1194
1215
if (handler != null ) {
1195
1216
context .currentState = handler .onStatusReceived (responseStatus );
1217
+ if (context .isWSRequest && context .currentState == AsyncHandler .STATE .ABORT ) {
1218
+ httpHeader .setSkipRemainder (true );
1219
+ context .abort (new HandshakeException ("Upgrade failed" ));
1220
+ }
1196
1221
}
1197
1222
} catch (Exception e ) {
1198
1223
httpHeader .setSkipRemainder (true );
@@ -1221,24 +1246,23 @@ protected void onHttpHeadersParsed(HttpHeader httpHeader,
1221
1246
FilterChainContext ctx ) {
1222
1247
1223
1248
super .onHttpHeadersParsed (httpHeader , ctx );
1224
- if (LOGGER .isDebugEnabled ()) {
1225
- LOGGER .debug ("RESPONSE: " + httpHeader .toString ());
1226
- }
1249
+ LOGGER .debug ("RESPONSE: {}" , httpHeader );
1227
1250
if (httpHeader .containsHeader (Header .Connection )) {
1228
1251
if ("close" .equals (httpHeader .getHeader (Header .Connection ))) {
1229
1252
ConnectionManager .markConnectionAsDoNotCache (ctx .getConnection ());
1230
1253
}
1231
1254
}
1232
- if (httpHeader .isSkipRemainder ()) {
1233
- return ;
1234
- }
1235
1255
final HttpTransactionContext context =
1236
1256
provider .getHttpTransactionContext (ctx .getConnection ());
1257
+ if (httpHeader .isSkipRemainder () || context .establishingTunnel ) {
1258
+ return ;
1259
+ }
1260
+
1237
1261
final AsyncHandler handler = context .handler ;
1238
1262
final List <ResponseFilter > filters = context .provider .clientConfig .getResponseFilters ();
1239
1263
final GrizzlyResponseHeaders responseHeaders = new GrizzlyResponseHeaders ((HttpResponsePacket ) httpHeader ,
1240
- null ,
1241
- provider );
1264
+ null ,
1265
+ provider );
1242
1266
if (!filters .isEmpty ()) {
1243
1267
FilterContext fc = new FilterContext .FilterContextBuilder ()
1244
1268
.asyncHandler (handler ).request (context .request )
@@ -1260,16 +1284,16 @@ protected void onHttpHeadersParsed(HttpHeader httpHeader,
1260
1284
context .provider .connectionManager ;
1261
1285
final Connection c =
1262
1286
m .obtainConnection (newRequest ,
1263
- context .future );
1287
+ context .future );
1264
1288
final HttpTransactionContext newContext =
1265
1289
context .copy ();
1266
1290
context .future = null ;
1267
1291
provider .setHttpTransactionContext (c , newContext );
1268
1292
try {
1269
1293
context .provider .execute (c ,
1270
- newRequest ,
1271
- newHandler ,
1272
- context .future );
1294
+ newRequest ,
1295
+ newHandler ,
1296
+ context .future );
1273
1297
} catch (IOException ioe ) {
1274
1298
newContext .abort (ioe );
1275
1299
}
@@ -1281,8 +1305,8 @@ protected void onHttpHeadersParsed(HttpHeader httpHeader,
1281
1305
}
1282
1306
if (context .statusHandler != null && context .invocationStatus == StatusHandler .InvocationStatus .CONTINUE ) {
1283
1307
final boolean result = context .statusHandler .handleStatus (((HttpResponsePacket ) httpHeader ),
1284
- context ,
1285
- ctx );
1308
+ context ,
1309
+ ctx );
1286
1310
if (!result ) {
1287
1311
httpHeader .setSkipRemainder (true );
1288
1312
return ;
@@ -1347,20 +1371,38 @@ protected boolean onHttpPacketParsed(HttpHeader httpHeader, FilterChainContext c
1347
1371
1348
1372
result = super .onHttpPacketParsed (httpHeader , ctx );
1349
1373
1350
- final HttpTransactionContext context = cleanup (ctx , provider );
1351
-
1352
- final AsyncHandler handler = context .handler ;
1353
- if (handler != null ) {
1374
+ final HttpTransactionContext context = provider .getHttpTransactionContext (ctx .getConnection ());
1375
+ if (context .establishingTunnel
1376
+ && HttpStatus .OK_200 .statusMatches (
1377
+ ((HttpResponsePacket ) httpHeader ).getStatus ())) {
1378
+ context .establishingTunnel = false ;
1379
+ final Connection c = ctx .getConnection ();
1380
+ context .tunnelEstablished (c );
1354
1381
try {
1355
- context .result (handler .onCompleted ());
1356
- } catch (Exception e ) {
1382
+ context .provider .execute (c ,
1383
+ context .request ,
1384
+ context .handler ,
1385
+ context .future );
1386
+ return result ;
1387
+ } catch (IOException e ) {
1357
1388
context .abort (e );
1389
+ return result ;
1358
1390
}
1359
1391
} else {
1360
- context .done (null );
1361
- }
1392
+ cleanup (ctx , provider );
1393
+ final AsyncHandler handler = context .handler ;
1394
+ if (handler != null ) {
1395
+ try {
1396
+ context .result (handler .onCompleted ());
1397
+ } catch (Exception e ) {
1398
+ context .abort (e );
1399
+ }
1400
+ } else {
1401
+ context .done (null );
1402
+ }
1362
1403
1363
- return result ;
1404
+ return result ;
1405
+ }
1364
1406
}
1365
1407
1366
1408
@@ -1389,7 +1431,7 @@ private static HttpTransactionContext cleanup(final FilterChainContext ctx,
1389
1431
context .abort (new IOException ("Maximum pooled connections exceeded" ));
1390
1432
} else {
1391
1433
if (!context .provider .connectionManager .returnConnection (context .requestUrl , c )) {
1392
- ctx .getConnection ().close (). markForRecycle ( true ) ;
1434
+ ctx .getConnection ().close ();
1393
1435
}
1394
1436
}
1395
1437
0 commit comments