Fix pagination with filter and offset #2

Merged
nabarun merged 2 commits from ng-paginate-filter-offset into zenith 2025-12-12 06:59:48 +00:00
2 changed files with 31 additions and 18 deletions

View File

@ -128,13 +128,10 @@ func collFilteredPaginateNoKey[K, V any, C Collection[K, V], T any](
return nil, nil, err
}
defer iterator.Close()
// we advance the iter equal to the provided offset
if !advanceIter(iterator, offset) {
return nil, nil, collections.ErrInvalidIterator
}
var (
count uint64
skipped uint64
nextKey []byte
results []T
)
@ -149,6 +146,11 @@ func collFilteredPaginateNoKey[K, V any, C Collection[K, V], T any](
}
// if no predicate function is specified then we just include the result
if predicateFunc == nil {
if skipped < offset {
skipped++
continue
}
transformed, err := transformFunc(kv.Key, kv.Value)
if err != nil {
return nil, nil, err
@ -163,6 +165,12 @@ func collFilteredPaginateNoKey[K, V any, C Collection[K, V], T any](
return nil, nil, err
}
if include {
// Item matches filter - check if we need to skip it for offset
if skipped < offset {
skipped++
continue
}
transformed, err := transformFunc(kv.Key, kv.Value)
if err != nil {
return nil, nil, err
@ -224,20 +232,6 @@ func collFilteredPaginateNoKey[K, V any, C Collection[K, V], T any](
return results, resp, nil
}
func advanceIter[I interface {
Next()
Valid() bool
}](iter I, offset uint64,
) bool {
for i := uint64(0); i < offset; i++ {
if !iter.Valid() {
return false
}
iter.Next()
}
return true
}
// collFilteredPaginateByKey paginates a collection when a starting key
// is provided in the PageRequest. Predicate is applied only if not nil.
func collFilteredPaginateByKey[K, V any, C Collection[K, V], T any](

View File

@ -154,6 +154,25 @@ func TestCollectionPagination(t *testing.T) {
{Key: 295, Value: 295},
},
},
"filtered with offset": {
req: &PageRequest{
Offset: 3,
Limit: 3,
CountTotal: true,
},
expResp: &PageResponse{
NextKey: encodeKey(12),
Total: 150,
},
filter: func(key, value uint64) (bool, error) {
return key%2 == 0, nil
},
expResults: []collections.KeyValue[uint64, uint64]{
{Key: 6, Value: 6},
{Key: 8, Value: 8},
{Key: 10, Value: 10},
},
},
"filtered no key with error": {
req: &PageRequest{
Limit: 3,