@@ -76,9 +76,9 @@ extension EffectProducer {
76
76
}
77
77
}
78
78
79
- _cancellationCancellables [ id, default: [ ] ] . insert (
79
+ _cancellationCancellables [ id, default: [ ] ] . insert (
80
80
cancellationDisposable
81
- )
81
+ )
82
82
83
83
return SignalProducer ( values. value)
84
84
. concat ( subject. output. producer)
@@ -165,55 +165,55 @@ extension EffectProducer {
165
165
}
166
166
167
167
#if swift(>=5.7)
168
- /// Execute an operation with a cancellation identifier.
169
- ///
170
- /// If the operation is in-flight when `Task.cancel(id:)` is called with the same identifier, the
171
- /// operation will be cancelled.
172
- ///
173
- /// ```
174
- /// enum CancelID.self {}
175
- ///
176
- /// await withTaskCancellation(id: CancelID.self) {
177
- /// // ...
178
- /// }
179
- /// ```
180
- ///
181
- /// ### Debouncing tasks
182
- ///
183
- /// When paired with a clock, this function can be used to debounce a unit of async work by
184
- /// specifying the `cancelInFlight`, which will automatically cancel any in-flight work with the
185
- /// same identifier:
186
- ///
187
- /// ```swift
188
- /// @Dependency(\.continuousClock) var clock
189
- /// enum CancelID {}
190
- ///
191
- /// // ...
192
- ///
193
- /// return .task {
194
- /// await withTaskCancellation(id: CancelID.self, cancelInFlight: true) {
195
- /// try await self.clock.sleep(for: .seconds(0.3))
196
- /// return await .debouncedResponse(
197
- /// TaskResult { try await environment.request() }
198
- /// )
199
- /// }
200
- /// }
201
- /// ```
202
- ///
203
- /// - Parameters:
204
- /// - id: A unique identifier for the operation.
205
- /// - cancelInFlight: Determines if any in-flight operation with the same identifier should be
206
- /// canceled before starting this new one.
207
- /// - operation: An async operation.
208
- /// - Throws: An error thrown by the operation.
209
- /// - Returns: A value produced by operation.
168
+ /// Execute an operation with a cancellation identifier.
169
+ ///
170
+ /// If the operation is in-flight when `Task.cancel(id:)` is called with the same identifier, the
171
+ /// operation will be cancelled.
172
+ ///
173
+ /// ```
174
+ /// enum CancelID.self {}
175
+ ///
176
+ /// await withTaskCancellation(id: CancelID.self) {
177
+ /// // ...
178
+ /// }
179
+ /// ```
180
+ ///
181
+ /// ### Debouncing tasks
182
+ ///
183
+ /// When paired with a clock, this function can be used to debounce a unit of async work by
184
+ /// specifying the `cancelInFlight`, which will automatically cancel any in-flight work with the
185
+ /// same identifier:
186
+ ///
187
+ /// ```swift
188
+ /// @Dependency(\.continuousClock) var clock
189
+ /// enum CancelID {}
190
+ ///
191
+ /// // ...
192
+ ///
193
+ /// return .task {
194
+ /// await withTaskCancellation(id: CancelID.self, cancelInFlight: true) {
195
+ /// try await self.clock.sleep(for: .seconds(0.3))
196
+ /// return await .debouncedResponse(
197
+ /// TaskResult { try await environment.request() }
198
+ /// )
199
+ /// }
200
+ /// }
201
+ /// ```
202
+ ///
203
+ /// - Parameters:
204
+ /// - id: A unique identifier for the operation.
205
+ /// - cancelInFlight: Determines if any in-flight operation with the same identifier should be
206
+ /// canceled before starting this new one.
207
+ /// - operation: An async operation.
208
+ /// - Throws: An error thrown by the operation.
209
+ /// - Returns: A value produced by operation.
210
210
@_unsafeInheritExecutor
211
- public func withTaskCancellation< T: Sendable > (
212
- id: AnyHashable ,
213
- cancelInFlight: Bool = false ,
214
- operation: @Sendable @escaping ( ) async throws -> T
215
- ) async rethrows -> T {
216
- let id = _CancelToken ( id: id)
211
+ public func withTaskCancellation< T: Sendable > (
212
+ id: AnyHashable ,
213
+ cancelInFlight: Bool = false ,
214
+ operation: @Sendable @escaping ( ) async throws -> T
215
+ ) async rethrows -> T {
216
+ let id = _CancelToken ( id: id)
217
217
let ( cancellable, task) = _cancellablesLock. sync { ( ) -> ( AnyDisposable , Task < T , Error > ) in
218
218
if cancelInFlight {
219
219
_cancellationCancellables [ id] ? . forEach { $0. dispose ( ) }
@@ -245,55 +245,55 @@ public func withTaskCancellation<T: Sendable>(
245
245
) async rethrows -> T {
246
246
let id = _CancelToken ( id: id)
247
247
let ( cancellable, task) = _cancellablesLock. sync { ( ) -> ( AnyDisposable , Task < T , Error > ) in
248
- if cancelInFlight {
249
- _cancellationCancellables [ id] ? . forEach { $0. dispose ( ) }
248
+ if cancelInFlight {
249
+ _cancellationCancellables [ id] ? . forEach { $0. dispose ( ) }
250
+ }
251
+ let task = Task { try await operation ( ) }
252
+ let cancellable = AnyDisposable { task. cancel ( ) }
253
+ _cancellationCancellables [ id, default: [ ] ] . insert ( cancellable)
254
+ return ( cancellable, task)
250
255
}
251
- let task = Task { try await operation ( ) }
252
- let cancellable = AnyDisposable { task. cancel ( ) }
253
- _cancellationCancellables [ id, default: [ ] ] . insert ( cancellable)
254
- return ( cancellable, task)
255
- }
256
- defer {
257
- _cancellablesLock. sync {
258
- _cancellationCancellables [ id] ? . remove ( cancellable)
259
- if _cancellationCancellables [ id] ? . isEmpty == . some( true ) {
260
- _cancellationCancellables [ id] = nil
256
+ defer {
257
+ _cancellablesLock. sync {
258
+ _cancellationCancellables [ id] ? . remove ( cancellable)
259
+ if _cancellationCancellables [ id] ? . isEmpty == . some( true ) {
260
+ _cancellationCancellables [ id] = nil
261
+ }
261
262
}
262
263
}
264
+ do {
265
+ return try await task. cancellableValue
266
+ } catch {
267
+ return try Result < T , Error > . failure ( error) . _rethrowGet ( )
268
+ }
263
269
}
264
- do {
265
- return try await task. cancellableValue
266
- } catch {
267
- return try Result < T , Error > . failure ( error) . _rethrowGet ( )
268
- }
269
- }
270
270
#endif
271
271
272
272
#if swift(>=5.7)
273
- /// Execute an operation with a cancellation identifier.
274
- ///
275
- /// A convenience for calling ``withTaskCancellation(id:cancelInFlight:operation:)-4dtr6`` with a
276
- /// static type as the operation's unique identifier.
277
- ///
278
- /// - Parameters:
279
- /// - id: A unique type identifying the operation.
280
- /// - cancelInFlight: Determines if any in-flight operation with the same identifier should be
281
- /// canceled before starting this new one.
282
- /// - operation: An async operation.
283
- /// - Throws: An error thrown by the operation.
284
- /// - Returns: A value produced by operation.
273
+ /// Execute an operation with a cancellation identifier.
274
+ ///
275
+ /// A convenience for calling ``withTaskCancellation(id:cancelInFlight:operation:)-4dtr6`` with a
276
+ /// static type as the operation's unique identifier.
277
+ ///
278
+ /// - Parameters:
279
+ /// - id: A unique type identifying the operation.
280
+ /// - cancelInFlight: Determines if any in-flight operation with the same identifier should be
281
+ /// canceled before starting this new one.
282
+ /// - operation: An async operation.
283
+ /// - Throws: An error thrown by the operation.
284
+ /// - Returns: A value produced by operation.
285
285
@_unsafeInheritExecutor
286
- public func withTaskCancellation< T: Sendable > (
287
- id: Any . Type ,
288
- cancelInFlight: Bool = false ,
289
- operation: @Sendable @escaping ( ) async throws -> T
290
- ) async rethrows -> T {
291
- try await withTaskCancellation (
292
- id: ObjectIdentifier ( id) ,
293
- cancelInFlight: cancelInFlight,
294
- operation: operation
295
- )
296
- }
286
+ public func withTaskCancellation< T: Sendable > (
287
+ id: Any . Type ,
288
+ cancelInFlight: Bool = false ,
289
+ operation: @Sendable @escaping ( ) async throws -> T
290
+ ) async rethrows -> T {
291
+ try await withTaskCancellation (
292
+ id: ObjectIdentifier ( id) ,
293
+ cancelInFlight: cancelInFlight,
294
+ operation: operation
295
+ )
296
+ }
297
297
#else
298
298
public func withTaskCancellation< T: Sendable > (
299
299
id: Any . Type ,
0 commit comments