@@ -43,7 +43,6 @@ public abstract class ScanCursor<T> implements Cursor<T> {
43
43
private Iterator <T > delegate ;
44
44
private final ScanOptions scanOptions ;
45
45
private long position ;
46
- private final long limit ;
47
46
48
47
/**
49
48
* Crates new {@link ScanCursor} with {@code id=0} and {@link ScanOptions#NONE}
@@ -82,23 +81,20 @@ public ScanCursor(long cursorId, @Nullable ScanOptions options) {
82
81
this .cursorId = cursorId ;
83
82
this .state = CursorState .READY ;
84
83
this .delegate = Collections .emptyIterator ();
85
- this .limit = -1 ;
86
84
}
87
85
88
86
/**
89
87
* Crates a new {@link ScanCursor}.
90
88
*
91
89
* @param source source cursor.
92
- * @param limit
93
90
* @since 2.5
94
91
*/
95
- private ScanCursor (ScanCursor <T > source , long limit ) {
92
+ private ScanCursor (ScanCursor <T > source ) {
96
93
97
94
this .scanOptions = source .scanOptions ;
98
95
this .cursorId = source .cursorId ;
99
96
this .state = source .state ;
100
97
this .delegate = source .delegate ;
101
- this .limit = limit ;
102
98
}
103
99
104
100
private void scan (long cursorId ) {
@@ -189,7 +185,7 @@ public boolean hasNext() {
189
185
190
186
assertCursorIsOpen ();
191
187
192
- if (limit != - 1 && getPosition () > limit - 1 ) {
188
+ if (limitReached ( getPosition ()) ) {
193
189
return false ;
194
190
}
195
191
@@ -204,6 +200,17 @@ public boolean hasNext() {
204
200
return cursorId > 0 ;
205
201
}
206
202
203
+ /**
204
+ * Evaluate if the current cursor position has reached a point where it should stop.
205
+ *
206
+ * @param currentPosition the current position.
207
+ * @return {@literal false} by default.
208
+ * @since 2.5
209
+ */
210
+ protected boolean limitReached (long currentPosition ) {
211
+ return false ;
212
+ }
213
+
207
214
private void assertCursorIsOpen () {
208
215
209
216
if (isReady () || isClosed ()) {
@@ -303,7 +310,7 @@ public ScanCursor<T> limit(long count) {
303
310
304
311
Assert .isTrue (count >= 0 , "Count must be greater or equal to zero" );
305
312
306
- return new ScanCursorWrapper <>(this , count );
313
+ return new LimitingCursor <>(this , count );
307
314
}
308
315
309
316
/**
@@ -318,30 +325,57 @@ enum CursorState {
318
325
* {@link #isClosed()}.
319
326
*
320
327
* @param <T>
328
+ * @author Mark Paluch
329
+ * @author Christoph Strobl
321
330
* @since 2.5
322
331
*/
323
- private static class ScanCursorWrapper <T > extends ScanCursor <T > {
332
+ private static class LimitingCursor <T > extends ScanCursor <T > {
324
333
325
334
private final ScanCursor <T > delegate ;
335
+ private final long limit ;
336
+
337
+ LimitingCursor (ScanCursor <T > delegate , long limit ) {
338
+
339
+ super (delegate );
326
340
327
- public ScanCursorWrapper (ScanCursor <T > delegate , long limit ) {
328
- super (delegate , limit );
329
341
this .delegate = delegate ;
342
+ this .limit = limit ;
330
343
}
331
344
345
+ /*
346
+ * (non-Javadoc)
347
+ * @see org.springframework.data.redis.core.ScanCursor#doScan(long, ScanOptions)
348
+ */
332
349
@ Override
333
350
protected ScanIteration <T > doScan (long cursorId , ScanOptions options ) {
334
351
return delegate .doScan (cursorId , options );
335
352
}
336
353
354
+ /*
355
+ * (non-Javadoc)
356
+ * @see org.springframework.data.redis.core.ScanCursor#doClose()
357
+ */
337
358
@ Override
338
359
protected void doClose () {
339
360
delegate .close ();
340
361
}
341
362
363
+ /*
364
+ * (non-Javadoc)
365
+ * @see org.springframework.data.redis.core.Cursor#isClosed()
366
+ */
342
367
@ Override
343
368
public boolean isClosed () {
344
369
return delegate .isClosed ();
345
370
}
371
+
372
+ /*
373
+ * (non-Javadoc)
374
+ * @see org.springframework.data.redis.core.ScanCursor#limitReached(long)
375
+ */
376
+ @ Override
377
+ protected boolean limitReached (long currentPosition ) {
378
+ return delegate .limitReached (currentPosition ) || (limit != -1 && currentPosition > limit - 1 );
379
+ }
346
380
}
347
381
}
0 commit comments