29
29
import io .rsocket .frame .ResumeOkFrameCodec ;
30
30
import io .rsocket .keepalive .KeepAliveSupport ;
31
31
import java .time .Duration ;
32
- import java .util .concurrent .TimeoutException ;
33
32
import java .util .concurrent .atomic .AtomicReferenceFieldUpdater ;
34
33
import java .util .function .Function ;
35
34
import org .reactivestreams .Subscription ;
@@ -79,31 +78,49 @@ public ClientRSocketSession(
79
78
this .resumeToken = resumeToken ;
80
79
this .session = resumeToken .toString (CharsetUtil .UTF_8 );
81
80
this .connectionFactory =
82
- connectionFactory .flatMap (
83
- dc -> {
84
- final long impliedPosition = resumableFramesStore .frameImpliedPosition ();
85
- final long position = resumableFramesStore .framePosition ();
86
- dc .sendFrame (
87
- 0 ,
88
- ResumeFrameCodec .encode (
89
- dc .alloc (),
90
- resumeToken .retain (),
91
- // server uses this to release its cache
92
- impliedPosition , // observed on the client side
93
- // server uses this to check whether there is no mismatch
94
- position // sent from the client sent
95
- ));
96
-
97
- if (logger .isDebugEnabled ()) {
98
- logger .debug (
99
- "Side[client]|Session[{}]. ResumeFrame[impliedPosition[{}], position[{}]] has been sent." ,
100
- session ,
101
- impliedPosition ,
102
- position );
103
- }
104
-
105
- return connectionTransformer .apply (dc );
106
- });
81
+ connectionFactory
82
+ .doOnDiscard (
83
+ DuplexConnection .class ,
84
+ c -> {
85
+ final ConnectionErrorException connectionErrorException =
86
+ new ConnectionErrorException ("resumption_server=[Session Expired]" );
87
+ c .sendErrorAndClose (connectionErrorException );
88
+ c .receive ().subscribe ();
89
+ })
90
+ .flatMap (
91
+ dc -> {
92
+ final long impliedPosition = resumableFramesStore .frameImpliedPosition ();
93
+ final long position = resumableFramesStore .framePosition ();
94
+ dc .sendFrame (
95
+ 0 ,
96
+ ResumeFrameCodec .encode (
97
+ dc .alloc (),
98
+ resumeToken .retain (),
99
+ // server uses this to release its cache
100
+ impliedPosition , // observed on the client side
101
+ // server uses this to check whether there is no mismatch
102
+ position // sent from the client sent
103
+ ));
104
+
105
+ if (logger .isDebugEnabled ()) {
106
+ logger .debug (
107
+ "Side[client]|Session[{}]. ResumeFrame[impliedPosition[{}], position[{}]] has been sent." ,
108
+ session ,
109
+ impliedPosition ,
110
+ position );
111
+ }
112
+
113
+ return connectionTransformer
114
+ .apply (dc )
115
+ .doOnDiscard (
116
+ Tuple2 .class ,
117
+ tuple2 -> {
118
+ if (logger .isDebugEnabled ()) {
119
+ logger .debug ("try to reestablish from discard" );
120
+ }
121
+ tryReestablishSession (tuple2 );
122
+ });
123
+ });
107
124
this .resumableFramesStore = resumableFramesStore ;
108
125
this .allocator = resumableDuplexConnection .alloc ();
109
126
this .resumeSessionDuration = resumeSessionDuration ;
@@ -160,11 +177,20 @@ public void onImpliedPosition(long remoteImpliedPos) {
160
177
161
178
@ Override
162
179
public void dispose () {
163
- Operators .terminate (S , this );
180
+ if (logger .isDebugEnabled ()) {
181
+ logger .debug ("Side[client]|Session[{}]. Disposing" , session );
182
+ }
183
+
184
+ boolean result = Operators .terminate (S , this );
185
+
186
+ if (logger .isDebugEnabled ()) {
187
+ logger .debug ("Side[client]|Session[{}]. Sessions[isDisposed={}]" , session , result );
188
+ }
164
189
165
190
reconnectDisposable .dispose ();
166
191
resumableConnection .dispose ();
167
- resumableFramesStore .dispose ();
192
+ // frame store is disposed by resumable connection
193
+ // resumableFramesStore.dispose();
168
194
169
195
if (resumeToken .refCnt () > 0 ) {
170
196
resumeToken .release ();
@@ -177,6 +203,9 @@ public boolean isDisposed() {
177
203
}
178
204
179
205
void tryReestablishSession (Tuple2 <ByteBuf , DuplexConnection > tuple2 ) {
206
+ if (logger .isDebugEnabled ()) {
207
+ logger .debug ("Active subscription is canceled {}" , s == Operators .cancelledSubscription ());
208
+ }
180
209
ByteBuf shouldBeResumeOKFrame = tuple2 .getT1 ();
181
210
DuplexConnection nextDuplexConnection = tuple2 .getT2 ();
182
211
@@ -189,9 +218,9 @@ void tryReestablishSession(Tuple2<ByteBuf, DuplexConnection> tuple2) {
189
218
}
190
219
final ConnectionErrorException connectionErrorException =
191
220
new ConnectionErrorException ("RESUME_OK frame must be received before any others" );
192
- resumableConnection .dispose (connectionErrorException );
221
+ resumableConnection .dispose (nextDuplexConnection , connectionErrorException );
193
222
nextDuplexConnection .sendErrorAndClose (connectionErrorException );
194
- nextDuplexConnection .receive ().subscribe (). dispose () ;
223
+ nextDuplexConnection .receive ().subscribe ();
195
224
196
225
throw connectionErrorException ; // throw to retry connection again
197
226
}
@@ -227,10 +256,10 @@ void tryReestablishSession(Tuple2<ByteBuf, DuplexConnection> tuple2) {
227
256
}
228
257
final ConnectionErrorException t = new ConnectionErrorException (e .getMessage (), e );
229
258
230
- resumableConnection .dispose (t );
259
+ resumableConnection .dispose (nextDuplexConnection , t );
231
260
232
261
nextDuplexConnection .sendErrorAndClose (t );
233
- nextDuplexConnection .receive ().subscribe (). dispose () ;
262
+ nextDuplexConnection .receive ().subscribe ();
234
263
235
264
return ;
236
265
}
@@ -244,7 +273,7 @@ void tryReestablishSession(Tuple2<ByteBuf, DuplexConnection> tuple2) {
244
273
final ConnectionErrorException connectionErrorException =
245
274
new ConnectionErrorException ("resumption_server=[Session Expired]" );
246
275
nextDuplexConnection .sendErrorAndClose (connectionErrorException );
247
- nextDuplexConnection .receive ().subscribe (). dispose () ;
276
+ nextDuplexConnection .receive ().subscribe ();
248
277
return ;
249
278
}
250
279
@@ -263,7 +292,7 @@ void tryReestablishSession(Tuple2<ByteBuf, DuplexConnection> tuple2) {
263
292
final ConnectionErrorException connectionErrorException =
264
293
new ConnectionErrorException ("resumption_server_pos=[Session Expired]" );
265
294
nextDuplexConnection .sendErrorAndClose (connectionErrorException );
266
- nextDuplexConnection .receive ().subscribe (). dispose () ;
295
+ nextDuplexConnection .receive ().subscribe ();
267
296
// no need to do anything since connection resumable connection is liklly to
268
297
// be disposed
269
298
}
@@ -278,10 +307,10 @@ void tryReestablishSession(Tuple2<ByteBuf, DuplexConnection> tuple2) {
278
307
final ConnectionErrorException connectionErrorException =
279
308
new ConnectionErrorException ("resumption_server_pos=[" + remoteImpliedPos + "]" );
280
309
281
- resumableConnection .dispose (connectionErrorException );
310
+ resumableConnection .dispose (nextDuplexConnection , connectionErrorException );
282
311
283
312
nextDuplexConnection .sendErrorAndClose (connectionErrorException );
284
- nextDuplexConnection .receive ().subscribe (). dispose () ;
313
+ nextDuplexConnection .receive ().subscribe ();
285
314
}
286
315
} else if (frameType == FrameType .ERROR ) {
287
316
final RuntimeException exception = Exceptions .from (0 , shouldBeResumeOKFrame );
@@ -292,13 +321,14 @@ void tryReestablishSession(Tuple2<ByteBuf, DuplexConnection> tuple2) {
292
321
exception );
293
322
}
294
323
if (exception instanceof RejectedResumeException ) {
295
- resumableConnection .dispose (exception );
324
+ resumableConnection .dispose (nextDuplexConnection , exception );
296
325
nextDuplexConnection .dispose ();
297
- nextDuplexConnection .receive ().subscribe (). dispose () ;
326
+ nextDuplexConnection .receive ().subscribe ();
298
327
return ;
299
328
}
300
329
301
330
nextDuplexConnection .dispose ();
331
+ nextDuplexConnection .receive ().subscribe ();
302
332
throw exception ; // assume retryable exception
303
333
} else {
304
334
if (logger .isDebugEnabled ()) {
@@ -309,10 +339,10 @@ void tryReestablishSession(Tuple2<ByteBuf, DuplexConnection> tuple2) {
309
339
final ConnectionErrorException connectionErrorException =
310
340
new ConnectionErrorException ("RESUME_OK frame must be received before any others" );
311
341
312
- resumableConnection .dispose (connectionErrorException );
342
+ resumableConnection .dispose (nextDuplexConnection , connectionErrorException );
313
343
314
344
nextDuplexConnection .sendErrorAndClose (connectionErrorException );
315
- nextDuplexConnection .receive ().subscribe (). dispose () ;
345
+ nextDuplexConnection .receive ().subscribe ();
316
346
317
347
// no need to do anything since remote server rejected our connection completely
318
348
}
@@ -349,11 +379,7 @@ public void onError(Throwable t) {
349
379
Operators .onErrorDropped (t , currentContext ());
350
380
}
351
381
352
- if (t instanceof TimeoutException ) {
353
- resumableConnection .dispose ();
354
- } else {
355
- resumableConnection .dispose (t );
356
- }
382
+ resumableConnection .dispose ();
357
383
}
358
384
359
385
@ Override
0 commit comments