Skip to content

Commit f25446e

Browse files
authored
Merge pull request #323 from kitwtnb/add-async-await
Add async await into AsyncStorage
2 parents 41525b4 + 62374db commit f25446e

File tree

4 files changed

+140
-0
lines changed

4 files changed

+140
-0
lines changed

README.md

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -288,6 +288,45 @@ storage.async.removeExpiredObjects() { result in
288288
}
289289
```
290290

291+
#### Swift Concurrency
292+
293+
```swift
294+
do {
295+
try await storage.async.setObject("Oslo", forKey: "my favorite city")
296+
print("saved successfully")
297+
} catch {
298+
print(error)
299+
}
300+
301+
do {
302+
let city = try await storage.async.object(forKey: "my favorite city")
303+
print("my favorite city is \(city)")
304+
} catch {
305+
print(error)
306+
}
307+
308+
do {
309+
let exists = try await storage.async.objectExists(forKey: "my favorite city")
310+
if exists {
311+
print("I have a favorite city")
312+
}
313+
} catch {}
314+
315+
do {
316+
try await storage.async.remoeAll()
317+
print("removal completes")
318+
} catch {
319+
print(error)
320+
}
321+
322+
do {
323+
try await storage.async.removeExpiredObjects()
324+
print("removal completes")
325+
} catch {
326+
print(error)
327+
}
328+
```
329+
291330
### Expiry date
292331

293332
By default, all saved objects have the same expiry as the expiry you specify in `DiskConfig` or `MemoryConfig`. You can overwrite this for a specific object by specifying `expiry` for `setObject`

Source/Shared/Storage/AsyncStorage.swift

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -138,3 +138,65 @@ public extension AsyncStorage {
138138
return storage
139139
}
140140
}
141+
142+
@available(macOS 10.15, iOS 13.0, watchOS 6.0, tvOS 13.0, *)
143+
public extension AsyncStorage {
144+
func entry(forKey key: Key) async throws -> Entry<Value> {
145+
try await withCheckedThrowingContinuation { continuation in
146+
entry(forKey: key) {
147+
continuation.resume(with: $0)
148+
}
149+
}
150+
}
151+
152+
func removeObject(forKey key: Key) async throws {
153+
try await withCheckedThrowingContinuation { continuation in
154+
removeObject(forKey: key) {
155+
continuation.resume(with: $0)
156+
}
157+
}
158+
}
159+
160+
func setObject(
161+
_ object: Value,
162+
forKey key: Key,
163+
expiry: Expiry? = nil) async throws {
164+
try await withCheckedThrowingContinuation { continuation in
165+
setObject(object, forKey: key, expiry: expiry) {
166+
continuation.resume(with: $0)
167+
}
168+
}
169+
}
170+
171+
func removeAll() async throws {
172+
try await withCheckedThrowingContinuation { continuation in
173+
removeAll {
174+
continuation.resume(with: $0)
175+
}
176+
}
177+
}
178+
179+
func removeExpiredObjects() async throws {
180+
try await withCheckedThrowingContinuation { continuation in
181+
removeExpiredObjects {
182+
continuation.resume(with: $0)
183+
}
184+
}
185+
}
186+
187+
func object(forKey key: Key) async throws -> Value {
188+
try await withCheckedThrowingContinuation { continuation in
189+
object(forKey: key) {
190+
continuation.resume(with: $0)
191+
}
192+
}
193+
}
194+
195+
func objectExists(forKey key: Key) async throws -> Bool {
196+
try await withCheckedThrowingContinuation { continuation in
197+
objectExists(forKey: key) {
198+
continuation.resume(with: $0)
199+
}
200+
}
201+
}
202+
}

Tests/Shared/TestCase+Extensions.swift

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,11 +5,23 @@ extension XCTestCase {
55
try closure()
66
}
77

8+
func given(_ description: String, closure: () async throws -> Void) async rethrows {
9+
try await closure()
10+
}
11+
812
func when(_ description: String, closure: () throws -> Void) rethrows {
913
try closure()
1014
}
1115

16+
func when(_ description: String, closure: () async throws -> Void) async rethrows {
17+
try await closure()
18+
}
19+
1220
func then(_ description: String, closure: () throws -> Void) rethrows {
1321
try closure()
1422
}
23+
24+
func then(_ description: String, closure: () async throws -> Void) async rethrows {
25+
try await closure()
26+
}
1527
}

Tests/iOS/Tests/Storage/AsyncStorageTests.swift

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,13 @@ final class AsyncStorageTests: XCTestCase {
3636
wait(for: [expectation], timeout: 1)
3737
}
3838

39+
func testSetObject() async throws {
40+
try await storage.setObject(user, forKey: "user")
41+
let cachedUser = try await storage.object(forKey: "user")
42+
43+
XCTAssertEqual(cachedUser, self.user)
44+
}
45+
3946
func testRemoveAll() {
4047
let intStorage = storage.transform(transformer: TransformerFactory.forCodable(ofType: Int.self))
4148
let expectation = self.expectation(description: #function)
@@ -62,4 +69,24 @@ final class AsyncStorageTests: XCTestCase {
6269

6370
wait(for: [expectation], timeout: 1)
6471
}
72+
73+
func testRemoveAll() async throws {
74+
let intStorage = storage.transform(transformer: TransformerFactory.forCodable(ofType: Int.self))
75+
try await given("add a lot of objects") {
76+
for i in 0 ..< 100 {
77+
try await intStorage.setObject(i, forKey: "key-\(i)")
78+
}
79+
}
80+
81+
try await when("remove all") {
82+
try await intStorage.removeAll()
83+
}
84+
85+
await then("all are removed") {
86+
do {
87+
_ = try await intStorage.objectExists(forKey: "key-99")
88+
XCTFail()
89+
} catch {}
90+
}
91+
}
6592
}

0 commit comments

Comments
 (0)