@@ -2,20 +2,20 @@ import Foundation
22
33extension ScalarDatabaseFunction {
44 public func install( _ db: OpaquePointer ) {
5- let body = Unmanaged . passRetained ( ScalarDatabaseFunctionContext ( self ) ) . toOpaque ( )
5+ let box = Unmanaged . passRetained ( ScalarDatabaseFunctionBox ( self ) ) . toOpaque ( )
66 sqlite3_create_function_v2 (
77 db,
88 name,
99 Int32 ( argumentCount ?? - 1 ) ,
1010 SQLITE_UTF8 | ( isDeterministic ? SQLITE_DETERMINISTIC : 0 ) ,
11- body ,
11+ box ,
1212 { context, argumentCount, arguments in
1313 do {
14- let body = Unmanaged < ScalarDatabaseFunctionContext >
14+ let box = Unmanaged < ScalarDatabaseFunctionBox >
1515 . fromOpaque ( sqlite3_user_data ( context) )
1616 . takeUnretainedValue ( )
1717 let arguments = try [ QueryBinding] ( argumentCount: argumentCount, arguments: arguments)
18- let output = body ( arguments)
18+ let output = box . function . invoke ( arguments)
1919 try output. result ( db: context)
2020 } catch {
2121 sqlite3_result_error ( context, error. localizedDescription, - 1 )
@@ -25,19 +25,16 @@ extension ScalarDatabaseFunction {
2525 nil ,
2626 { context in
2727 guard let context else { return }
28- Unmanaged < ScalarDatabaseFunctionContext > . fromOpaque ( context) . release ( )
28+ Unmanaged < ScalarDatabaseFunctionBox > . fromOpaque ( context) . release ( )
2929 }
3030 )
3131 }
3232}
3333
34- private final class ScalarDatabaseFunctionContext {
35- let body : ( [ QueryBinding ] ) -> QueryBinding
34+ private final class ScalarDatabaseFunctionBox {
35+ let function : any ScalarDatabaseFunction
3636 init ( _ function: some ScalarDatabaseFunction ) {
37- body = function. invoke
38- }
39- func callAsFunction( _ arguments: [ QueryBinding ] ) -> QueryBinding {
40- body ( arguments)
37+ self . function = function
4138 }
4239}
4340
@@ -93,3 +90,38 @@ extension QueryBinding {
9390 }
9491 }
9592}
93+
94+ private final class Stream < Element> : Sequence {
95+ private let condition = NSCondition ( )
96+ private var buffer : [ Element ] = [ ]
97+ private var isFinished = false
98+
99+ func send( _ element: Element ) {
100+ condition. withLock {
101+ buffer. append ( element)
102+ condition. signal ( )
103+ }
104+ }
105+
106+ func finish( ) {
107+ condition. withLock {
108+ isFinished = true
109+ condition. broadcast ( )
110+ }
111+ }
112+
113+ func makeIterator( ) -> Iterator { Iterator ( base: self ) }
114+
115+ struct Iterator : IteratorProtocol {
116+ fileprivate let base : Stream
117+ mutating func next( ) -> Element ? {
118+ base. condition. withLock {
119+ while base. buffer. isEmpty && !base. isFinished {
120+ base. condition. wait ( )
121+ }
122+ guard !base. buffer. isEmpty else { return nil }
123+ return base. buffer. removeFirst ( )
124+ }
125+ }
126+ }
127+ }
0 commit comments