You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
// Allow timeout (when the observable ends, caller will
358
-
// cancel the agent, so we need timeout to allow cancellation)
359
-
let!msg= mbox.TryReceive(200)
360
-
match msg with
361
-
| Some(Put _)| None ->
362
-
()// Ignore put or no message
363
-
| Some(Get repl)->
364
-
// Reader is blocked, so next will be Put
365
-
// (caller will not stop the agent at this point,
366
-
// so timeout is not necessary)
367
-
let!v= mbox.Receive()
368
-
match v with
369
-
| Put v -> repl.Reply(v)
370
-
|_-> failwith "Unexpected Get"})
371
-
372
-
[<System.Obsolete("Use AsyncSeq.ofObservableDiscarding. This function doesn't guarantee that the asynchronous sequence will return all values produced by the observable")>]
373
-
letofObservable(input :System.IObservable<_>)=
374
-
ofObservableDiscarding input
312
+
asyncSeq {
313
+
letcts=new CancellationTokenSource()
314
+
try
315
+
// The body of this agent returns immediately. It turns out this is a valid use of an F# agent, and it
316
+
// leaves the agent available as a queue that supports an asynchronous receive.
317
+
//
318
+
// This makes the cancellation token is somewhat meaningless since the body has already returned. However
319
+
// if we don't pass it in then the default cancellation token will be used, so we pass one in for completeness.
320
+
use agent = MailboxProcessor<_>.Start((fun inbox -> async.Return()), cancellationToken = cts.Token)
321
+
use d = input |> Observable.asUpdates |> Observable.subscribe agent.Post
322
+
letfin= ref false
323
+
whilenot fin.Value do
324
+
let!msg= agent.Receive()
325
+
match msg with
326
+
| Observable.ObservableUpdate.Error e -> raise e
327
+
| Observable.Completed -> fin := true
328
+
| Observable.Next v ->yield v
329
+
finally
330
+
// Cancel on early exit
331
+
cts.Cancel()}
332
+
333
+
[<System.Obsolete("Please use AsyncSeq.ofObservableBuffered. The original AsyncSeq.ofObservable doesn't guarantee that the asynchronous sequence will return all values produced by the observable",true) >]
334
+
letofObservable(input :System.IObservable<'T>):AsyncSeq<'T>= failwith "no longer supported"
375
335
376
336
lettoObservable(aseq:AsyncSeq<_>)=
377
337
letstart(obs:IObserver<_>)=
@@ -387,29 +347,28 @@ module AsyncSeq =
387
347
388
348
lettoBlockingSeq(input :AsyncSeq<'T>)=
389
349
seq{
390
-
// Write all elements to a blocking buffer and then add None to denote end
391
-
letbuf=newBlockingQueueAgent<_>(1)
350
+
// Write all elements to a blocking buffer
351
+
use buf =newSystem.Collections.Concurrent.BlockingCollection<_>()
392
352
393
353
use cts =new System.Threading.CancellationTokenSource()
394
354
use _cancel ={new IDisposable withmember__.Dispose()= cts.Cancel()}
Copy file name to clipboardExpand all lines: src/FSharp.Control.AsyncSeq/AsyncSeq.fsi
+1-4Lines changed: 1 addition & 4 deletions
Original file line number
Diff line number
Diff line change
@@ -181,10 +181,7 @@ module AsyncSeq =
181
181
/// an unbounded buffer and are returned as next elements of the async sequence.
182
182
val ofObservableBuffered : input:System.IObservable<'T>-> AsyncSeq<'T>
183
183
184
-
/// Converts observable to an asynchronous sequence. Values that are produced
185
-
/// by the observable while the asynchronous sequence is blocked are discarded
186
-
///(this function doesn't guarantee that asynchronou ssequence will return
187
-
/// all values produced by the observable)
184
+
[<System.Obsolete("Please use AsyncSeq.ofObservableBuffered. The original AsyncSeq.ofObservable doesn't guarantee that the asynchronous sequence will return all values produced by the observable",true)>]
188
185
val ofObservable : input:System.IObservable<'T>-> AsyncSeq<'T>
189
186
190
187
/// Converts asynchronous sequence to an IObservable<_>. When the client subscribes
0 commit comments