public void TestMultipleUnlisten() { StreamSink <int> s = Stream.CreateSink <int>(); List <int> @out = new List <int>(); ((Action)(() => { // ReSharper disable once UnusedVariable IStrongListener l = s.Listen(@out.Add); s.Send(1); l.Unlisten(); l.Unlisten(); s.Send(2); l.Unlisten(); }))(); s.Send(3); s.Send(4); Assert.AreEqual(1, @out.Count); }
internal IStrongListener ListenOnceImpl(Action <T> handler) { IStrongListener listener = null; bool unlistenEarly = false; listener = this.ListenImpl( a => { // ReSharper disable once AccessToModifiedClosure if (listener == null) { unlistenEarly = true; } else { // ReSharper disable once AccessToModifiedClosure listener.Unlisten(); listener = null; } handler(a); }); if (unlistenEarly) { listener.Unlisten(); listener = null; } return(listener); }
private static TResult ListenOnceAsyncInternal <T, TResult>( this Stream <T> s, Func <Task <T>, IStrongListener, TResult> generateResult, CancellationToken token) { TaskCompletionSource <T> tcs = new TaskCompletionSource <T>(); IStrongListener listener = null; bool unlistenEarly = false; listener = s.Listen( a => { // ReSharper disable once AccessToModifiedClosure if (listener == null) { unlistenEarly = true; } else { // ReSharper disable once AccessToModifiedClosure listener.Unlisten(); listener = null; } tcs.TrySetResult(a); }); if (unlistenEarly) { listener.Unlisten(); listener = null; } token.Register( () => { listener?.Unlisten(); tcs.TrySetCanceled(); }); return(generateResult(tcs.Task, listener)); }