Skip to content

Commit b0029b2

Browse files
committed
Add AsyncThrowingFlatMapSequence.nextElement()
1 parent 1b6a18f commit b0029b2

File tree

2 files changed

+51
-0
lines changed

2 files changed

+51
-0
lines changed

stdlib/public/Concurrency/AsyncThrowingFlatMapSequence.swift

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -168,6 +168,56 @@ extension AsyncThrowingFlatMapSequence: AsyncSequence {
168168
}
169169
return nil
170170
}
171+
172+
/// Produces the next element in the flat map sequence.
173+
///
174+
/// This iterator calls `next()` on its base iterator; if this call returns
175+
/// `nil`, `next()` returns `nil`. Otherwise, `next()` calls the
176+
/// transforming closure on the received element, takes the resulting
177+
/// asynchronous sequence, and creates an asynchronous iterator from it.
178+
/// `next()` then consumes values from this iterator until it terminates.
179+
/// At this point, `next()` is ready to receive the next value from the base
180+
/// sequence. If `transform` throws an error, the sequence terminates.
181+
@available(SwiftStdlib 5.11, *)
182+
@inlinable
183+
public mutating func nextElement() async throws(Failure) -> SegmentOfResult.Element? {
184+
while !finished {
185+
if var iterator = currentIterator {
186+
do {
187+
guard let element = try await iterator.next() else {
188+
currentIterator = nil
189+
continue
190+
}
191+
// restore the iterator since we just mutated it with next
192+
currentIterator = iterator
193+
return element
194+
} catch {
195+
finished = true
196+
throw error
197+
}
198+
} else {
199+
guard let item = try await baseIterator.next() else {
200+
return nil
201+
}
202+
let segment: SegmentOfResult
203+
do {
204+
segment = try await transform(item)
205+
var iterator = segment.makeAsyncIterator()
206+
guard let element = try await iterator.next() else {
207+
currentIterator = nil
208+
continue
209+
}
210+
currentIterator = iterator
211+
return element
212+
} catch {
213+
finished = true
214+
currentIterator = nil
215+
throw error
216+
}
217+
}
218+
}
219+
return nil
220+
}
171221
}
172222

173223
@inlinable

test/api-digester/stability-concurrency-abi.test

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,7 @@
5252
// UNSUPPORTED: swift_evolve
5353

5454
// *** DO NOT DISABLE OR XFAIL THIS TEST. *** (See comment above.)
55+
Func AsyncSequence.flatMap(_:) has mangled name changing from '(extension in _Concurrency):Swift.AsyncSequence.flatMap<A where A1: Swift.AsyncSequence>((A.Element) async -> A1) -> _Concurrency.AsyncFlatMapSequence<A, A1>' to '(extension in _Concurrency):Swift.AsyncSequence.flatMap<A where A1: Swift.AsyncSequence>(@Sendable (A.Element) async -> A1) -> _Concurrency.AsyncFlatMapSequence<A, A1>'
5556
Func MainActor.run(resultType:body:) has generic signature change from <T where T : Swift.Sendable> to <T>
5657
Func MainActor.run(resultType:body:) has mangled name changing from 'static Swift.MainActor.run<A where A: Swift.Sendable>(resultType: A.Type, body: @Swift.MainActor @Sendable () throws -> A) async throws -> A' to 'static Swift.MainActor.run<A>(resultType: A.Type, body: @Swift.MainActor @Sendable () throws -> A) async throws -> A'
5758
Func _asyncLet_get(_:_:) has mangled name changing from '_Concurrency._asyncLet_get(Builtin.RawPointer, Builtin.RawPointer) async -> Builtin.RawPointer' to '_Concurrency._asyncLet_get(Builtin.RawPointer, Builtin.RawPointer) async -> ()'

0 commit comments

Comments
 (0)