Skip to content

Commit 0863c08

Browse files
authored
feat(Swift): Adding SubpathStrategy documentation for Storage.List (#7831)
1 parent fa7c5e1 commit 0863c08

File tree

2 files changed

+293
-36
lines changed
  • src
    • fragments/lib/storage/ios
    • pages/[platform]/build-a-backend/storage/list-files

2 files changed

+293
-36
lines changed

src/fragments/lib/storage/ios/list.mdx

Lines changed: 167 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,15 @@
1-
You can list all of the objects uploaded under a given prefix by setting the `pageSize`. If the `pageSize` is set lower than the total file size available, A single `Storage.list` call only returns a subset of all the files. To list all the files with multiple calls, the user can use the `nextToken` from the previous call response.
1+
You can list files without having to download all the files. You can do this by using the list API from the Amplify Library for Storage.
22

3-
#### With StoragePath
3+
## With StoragePath
4+
5+
The following example lists all objects inside the `public/photos/` path:
46
<BlockSwitcher>
57

68
<Block name="Async/Await">
79

810
```swift
9-
let options = StorageListRequest.Options(pageSize: 1000)
1011
let listResult = try await Amplify.Storage.list(
11-
path: .fromString("public/example/path"),
12-
options: options
12+
path: .fromString("public/photos/")
1313
)
1414
listResult.items.forEach { item in
1515
print("Path: \(item.path)")
@@ -22,18 +22,15 @@ listResult.items.forEach { item in
2222

2323
```swift
2424
let sink = Amplify.Publisher.create {
25-
let options = StorageListRequest.Options(pageSize: 1000)
2625
try await Amplify.Storage.list(
27-
path: .fromString("public/example/path"),
28-
options: options
26+
path: .fromString("public/photos/")
2927
)
3028
}.sink {
3129
if case let .failure(error) = $0 {
3230
print("Failed: \(error)")
3331
}
3432
}
3533
receiveValue: { listResult in
36-
print("Completed")
3734
listResult.items.forEach { item in
3835
print("Path: \(item.path)")
3936
}
@@ -44,14 +41,135 @@ receiveValue: { listResult in
4441

4542
</BlockSwitcher>
4643

47-
#### With Key (Deprecated)
44+
<Callout>
45+
Note the trailing slash `/` in the given path.
46+
47+
If you had used `public/photos` as path, it would also match against files like `public/photos01.jpg`.
48+
</Callout>
49+
50+
### Exclude results from nested subpaths
51+
52+
By default, the `list` API will return all objects contained within the given path, including objects inside nested subpaths.
53+
54+
For example, the previous `public/photos/` path would include these objects:
55+
56+
```bash
57+
Path: public/photos/photo1.jpg
58+
Path: public/photos/vacation/photo1.jpg
59+
Path: public/photos/thumbnails/photo1.jpg
60+
```
61+
62+
In order to exclude objects within the `vacation` and `thumbnails` subpaths, you can set the `subpathStrategy` option to `.exclude`:
63+
64+
<BlockSwitcher>
65+
66+
<Block name="Async/Await">
67+
68+
```swift
69+
let listResult = try await Amplify.Storage.list(
70+
path: .fromString("public/photos/"),
71+
options: .init(
72+
subpathStrategy: .exclude
73+
)
74+
)
75+
listResult.items.forEach { item in
76+
print("Path: \(item.path)")
77+
}
78+
listResult.excludedSubpaths.forEach { subpath in
79+
print("Subpath: \(subpath)")
80+
}
81+
```
82+
83+
</Block>
84+
85+
<Block name="Combine">
86+
87+
```swift
88+
let sink = Amplify.Publisher.create {
89+
try await Amplify.Storage.list(
90+
path: .fromString("public/photos/"),
91+
options: .init(
92+
subpathStrategy: .exclude
93+
)
94+
)
95+
}.sink {
96+
if case let .failure(error) = $0 {
97+
print("Failed: \(error)")
98+
}
99+
}
100+
receiveValue: { listResult in
101+
listResult.items.forEach { item in
102+
print("Path: \(item.path)")
103+
}
104+
listResult.excludedSubpaths.forEach { subpath in
105+
print("Subpath: \(subpath)")
106+
}
107+
}
108+
```
109+
110+
</Block>
111+
112+
</BlockSwitcher>
113+
114+
The response will only include objects within the `public/photos/` path and will also provide a list of the excluded subpaths:
115+
116+
```bash
117+
Path: public/photos/photo01.jpg
118+
Subpath: public/photos/vacation/
119+
Subpath: public/photos/thumbnails/
120+
```
121+
122+
The default delimiter character is `"/"`, but this can be changed by supplying a custom delimiter:
123+
124+
<BlockSwitcher>
125+
126+
<Block name="Async/Await">
127+
128+
```swift
129+
let listResult = try await Amplify.Storage.list(
130+
path: .fromString("public/photos-"),
131+
options: .init(
132+
subpathStrategy: .exclude(delimitedBy: "-")
133+
)
134+
)
135+
```
136+
137+
</Block>
138+
139+
<Block name="Combine">
140+
141+
```swift
142+
let sink = Amplify.Publisher.create {
143+
try await Amplify.Storage.list(
144+
path: .fromString("public/photos-"),
145+
options: .init(
146+
subpathStrategy: .exclude(delimitedBy: "-")
147+
)
148+
)
149+
}.sink {
150+
if case let .failure(error) = $0 {
151+
print("Failed: \(error)")
152+
}
153+
}
154+
receiveValue: { listResult in
155+
// ...
156+
}
157+
```
158+
159+
</Block>
160+
161+
</BlockSwitcher>
162+
163+
164+
## With Key (Deprecated)
165+
The following example lists all public files:
166+
48167
<BlockSwitcher>
49168

50169
<Block name="Async/Await">
51170

52171
```swift
53-
let options = StorageListRequest.Options(pageSize: 1000)
54-
let listResult = try await Amplify.Storage.list(options: options)
172+
let listResult = try await Amplify.Storage.list()
55173
listResult.items.forEach { item in
56174
print("Key: \(item.key)")
57175
}
@@ -63,8 +181,7 @@ listResult.items.forEach { item in
63181

64182
```swift
65183
let sink = Amplify.Publisher.create {
66-
let options = StorageListRequest.Options(pageSize: 1000)
67-
try await Amplify.Storage.list(options: options)
184+
try await Amplify.Storage.list()
68185
}.sink {
69186
if case let .failure(error) = $0 {
70187
print("Failed: \(error)")
@@ -89,10 +206,14 @@ You can also list private or protected files by passing options. For example, to
89206
<Block name="Async/Await">
90207

91208
```swift
92-
let options = StorageListRequest.Options(accessLevel: .protected, targetIdentityId: "otherUserID", pageSize: 1000)
93-
let listResult = try await Amplify.Storage.list(options: options)
209+
let listResult = try await Amplify.Storage.list(
210+
options: .init(
211+
accessLevel: .protected,
212+
targetIdentityId: "otherUserID"
213+
)
214+
)
94215
listResult.items.forEach { item in
95-
print("Path: \(item.path)")
216+
print("Key: \(item.key)")
96217
}
97218
```
98219

@@ -102,17 +223,21 @@ listResult.items.forEach { item in
102223

103224
```swift
104225
let sink = Amplify.Publisher.create {
105-
let options = StorageListRequest.Options(accessLevel: .protected, targetIdentityId: "otherUserID", pageSize: 1000)
106-
try await Amplify.Storage.list(options: options)
226+
let options = StorageListRequest.Options)
227+
try await Amplify.Storage.list(
228+
options: .init(
229+
accessLevel: .protected,
230+
targetIdentityId: "otherUserID"
231+
)
232+
)
107233
}.sink {
108234
if case let .failure(error) = $0 {
109235
print("Failed: \(error)")
110236
}
111237
}
112238
receiveValue: { listResult in
113-
print("Completed")
114239
listResult.items.forEach { item in
115-
print("Path: \(item.path)")
240+
print("Key: \(item.path)")
116241
}
117242
}
118243
```
@@ -128,8 +253,11 @@ If you like limit the response to keys that begin with the specified path provid
128253
<Block name="Async/Await">
129254

130255
```swift
131-
let options = StorageListRequest.Options(path: "path")
132-
let listResult = try await Amplify.Storage.list(options: options)
256+
let listResult = try await Amplify.Storage.list(
257+
options: .init(
258+
path: "path"
259+
)
260+
)
133261
listResult.items.forEach { item in
134262
print("Key: \(item.key)")
135263
}
@@ -141,15 +269,17 @@ listResult.items.forEach { item in
141269

142270
```swift
143271
let sink = Amplify.Publisher.create {
144-
let options = StorageListRequest.Options(path: "path")
145-
try await Amplify.Storage.list(options: options)
272+
try await Amplify.Storage.list(
273+
options: .init(
274+
path: "path"
275+
)
276+
)
146277
}.sink {
147278
if case let .failure(error) = $0 {
148279
print("Failed: \(error)")
149280
}
150281
}
151282
receiveValue: { listResult in
152-
print("Completed")
153283
listResult.items.forEach { item in
154284
print("Key: \(item.key)")
155285
}
@@ -158,4 +288,14 @@ receiveValue: { listResult in
158288

159289
</Block>
160290

161-
</BlockSwitcher>
291+
</BlockSwitcher>
292+
293+
## More `list` options
294+
295+
| Option | Type | Description |
296+
| --- | --- | --- |
297+
| pageSize | UInt | Number between 1 and 1,000 that indicates the limit of how many entries to fetch when retrieving file lists from the server |
298+
| nextToken | String | String indicating the page offset at which to resume a listing. |
299+
300+
301+
If the `pageSize` is set lower than the total file size available, a single `list` call only returns a subset of all the files. To list all the files with multiple calls, the user can use the `nextToken` value from the previous response.

0 commit comments

Comments
 (0)