Skip to content

feat(storage): add listPaginated for cursor-based file listing#1579

Merged
spydon merged 3 commits into
mainfrom
lukasklingsbo/storage-list-v2
Jul 11, 2026
Merged

feat(storage): add listPaginated for cursor-based file listing#1579
spydon merged 3 commits into
mainfrom
lukasklingsbo/storage-list-v2

Conversation

@spydon

@spydon spydon commented Jul 10, 2026

Copy link
Copy Markdown
Contributor

Summary

Adds StorageFileApi.listPaginated, backed by the storage object/list-v2/{bucketId} endpoint, supporting cursor-based pagination and hierarchical (delimiter) listing.

New API, using descriptive Dart names rather than the supabase-js listV2/SearchV2* naming:

  • listPaginated({PaginatedSearchOptions options}) returns PaginatedListResult
  • PaginatedSearchOptions (limit, prefix, cursor, withDelimiter, sortBy)
  • PaginatedListResult (hasNext, folders, objects, nextCursor)
  • PaginatedFile, PaginatedFolder
  • FileSort (column, order), where column and order are the enums FileSortColumn and FileSortOrder

Outcome: implemented
Reference: supabase-js StorageFileApi.listV2 (object/list-v2)
Compliance matrix: storage.file_buckets.list_files_paginated -> implemented

Notes

  • Idiomatic Dart rather than a transliteration of the JS shape: descriptive type names (Paginated*) instead of the V2 suffix, and enhanced enums FileSortColumn and FileSortOrder for the sort options instead of raw strings, matching the existing BucketSortColumn/BucketSortOrder pattern.
  • withDelimiter is camelCase on the Dart side and mapped to the with_delimiter wire key; FileSortColumn is serialized via snakeCase (for example createdAt becomes created_at) and FileSortOrder via its asc/desc value.
  • Unit tests cover the paginated result parsing (options body, folders and objects, cursor) and the empty-body default.
  • All new public symbols are registered under the capability.

Stacking

Second of three stacked PRs. Base: #1578 (cacheNonce). Review and merge #1578 first.

Adds an optional cacheNonce parameter to getPublicUrl, createSignedUrl,
createSignedUrls and download, appending a cacheNonce query parameter to
the generated URL to bypass CDN caching for a specific file version.

Ref: SDK-875
@spydon spydon requested a review from a team as a code owner July 10, 2026 12:13
@github-actions github-actions Bot added the storage This issue or pull request is related to storage label Jul 10, 2026
Adds StorageFileApi.listPaginated, backed by the storage list-v2 endpoint,
supporting cursor-based pagination and hierarchical (delimiter) listing via
PaginatedSearchOptions and returning a PaginatedListResult of PaginatedFile
and PaginatedFolder entries.

Implements storage.file_buckets.list_files_paginated.
@spydon spydon force-pushed the lukasklingsbo/storage-list-v2 branch from dc28e71 to 5653c6a Compare July 10, 2026 12:23
Base automatically changed from lukasklingsbo/sdk-875-storage-cache-nonce to main July 10, 2026 14:15
@spydon spydon merged commit a6428c6 into main Jul 11, 2026
27 checks passed
@spydon spydon deleted the lukasklingsbo/storage-list-v2 branch July 11, 2026 14:54
spydon added a commit that referenced this pull request Jul 11, 2026
## Summary

Adds `StorageFileApi.downloadStream`, which returns the response body as
a lazy `Stream<Uint8List>` for memory-efficient handling of large files
instead of buffering the whole body into a `Uint8List` (as `download`
does). The request is sent when the stream is listened to, and a
non-success status surfaces as a `StorageException` on the stream before
any bytes are emitted, matching how `File.openRead` behaves.

- `downloadStream(path, {transform, queryParams, cacheNonce})` returns
`Stream<Uint8List>`
- Internal `Fetch.getStream` streaming GET, an `async*` generator marked
`@internal`
- `download` and `downloadStream` share a new private `_downloadUri`
builder (DRY)

**Outcome:** implemented
**Reference:** supabase-js `download(...).asStream()`
(`StreamDownloadBuilder`)
**Compliance matrix:** `storage.file_buckets.download_as_stream` ->
implemented

## Notes
- Idiomatic Dart choices rather than a transliteration of the JS
builder: a bare lazy `Stream<Uint8List>` (not
`Future<Stream<List<int>>>` and not a chained `asStream()` builder),
with errors delivered on the stream. `Uint8List` is used for the byte
chunks, consistent with `download`; because `Stream` is covariant it is
still usable anywhere a `Stream<List<int>>` is expected.
- Unit tests cover the streamed happy path, the transform plus
cacheNonce query, and an error status surfacing on the stream.

## Stacking
Third of three stacked PRs. Base: #1579 (listPaginated). Review and
merge #1578 then #1579 first.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

storage This issue or pull request is related to storage

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants