public void ReliableMultiSubjectProxy_AsReliableObservable_Dispose()
        {
            Run(client =>
            {
                var env = new TestReliableExecutionEnvironment();
                var ctx = client.CreateContext(env);

                var uri     = new Uri("test://stream");
                var subject = new ReliableSubject <int>();
                env.AddArtifact(uri, subject);

                var proxy    = new ReliableMultiSubjectProxy <int, int>(uri);
                var observer = new MockObserver <int>(client);
                var sub      = proxy.ToSubscribable().Subscribe(observer);
                new SubscriptionInitializeVisitor(sub).Initialize(ctx);
                sub.Dispose();

                // Reliable subscriptions must be ack'd before they can be disposed
                // Unfortunately, this acking must be done on the implicit interface.
                SubscriptionVisitor.Do <ReliableSubscriptionBase>(s => ((IReliableSubscription)s).AcknowledgeRange(0)).Apply(sub);
                sub.Dispose();

                var isDisposed = false;
                SubscriptionVisitor.Do <ReliableSubcription <int> >(s => isDisposed |= s.IsDisposed).Apply(sub);

                Assert.IsTrue(isDisposed);
            });
        }
Пример #2
0
        public void SubscriptionVisitor_Null()
        {
            var visitor = new SubscriptionVisitor <MyOperator>(o =>
            {
                Assert.Fail();
            });

            visitor.Visit(null);
        }
Пример #3
0
        public void Window_Environment_Time_Dependencies()
        {
            Run(client =>
            {
                var env = new TestExecutionEnvironment();

                var ctx = client.CreateContext(env);

                var xs = client.CreateHotObservable <int>(
                    OnNext(210, 1),
                    OnNext(220, 2),
                    OnNext(230, 3),
                    OnNext(240, 4),
                    OnNext(250, 5),
                    OnNext(260, 6),
                    OnNext(270, 7),
                    OnNext(280, 8),
                    OnNext(290, 9),
                    OnCompleted <int>(300)
                    );

                var s = default(ISubscription);

                client.ScheduleAbsolute(200, () =>
                {
                    s = xs.Window(TimeSpan.FromTicks(30)).Subscribe(Observer.Nop <ISubscribable <int> >());
                    new SubscriptionInitializeVisitor(s).Initialize(ctx);
                });

                foreach (var t in new[] { 215, 245, 275 })
                {
                    client.ScheduleAbsolute(t, () =>
                    {
                        var ds = default(IEnumerable <Uri>);

                        SubscriptionVisitor.Do <IDependencyOperator>(op =>
                        {
                            ds = op.Dependencies;
                        }).Apply(s);

                        Assert.IsNotNull(ds);
                        Assert.AreEqual(1, ds.Count(d => d.OriginalString.StartsWith("rx://tollbooth")));
                        Assert.AreEqual(1, ds.Count(d => d.OriginalString.StartsWith("rx://collector")));
                        Assert.AreEqual(1, ds.Count(d => d.OriginalString.StartsWith("rx://tunnel/window")));
                    });
                }

                client.Start();
            });
        }
Пример #4
0
        public void AverageInt32_Overflow2()
        {
            Run(client =>
            {
                var xs = client.CreateColdObservable(
                    OnNext <int>(10, -2),
                    OnNext <int>(20, -3),
                    OnNext <int>(30, -5),
                    OnNext <int>(40, -7),
                    OnCompleted <int>(50)
                    );

                var res = client.CreateObserver <Double>();

                client.ScheduleAbsolute(default(object), 200, (s, _) =>
                {
                    var ys  = xs.Average();
                    var sub = ys.Subscribe(res);

                    InitializeSubscription(sub, client);

                    // Yes, dirty. No, I don't care.
                    SubscriptionVisitor.Do <IOperator>(op =>
                    {
                        var top = op.GetType();
                        if (top.DeclaringType == ys.GetType())
                        {
                            var count = top.GetField("_sum", BindingFlags.Instance | BindingFlags.NonPublic);
                            count.SetValue(op, long.MinValue + 8);
                        }
                    }).Apply(sub);
                });

                client.Start();

                res.Messages.AssertEqual(
                    OnError <Double>(230, ex => ex is OverflowException)
                    );

                xs.Subscriptions.AssertEqual(
                    Subscribe(200, 230)
                    );
            });
        }
Пример #5
0
        public void SubscriptionVisitor_Simple()
        {
            var g1 = new MySpecialOperator("g1");
            var c1 = new MyOperator("c1", g1);
            var c2 = new MySpecialOperator("c2");
            var c3 = new MyOperator("c3");
            var p  = new MyOperator("p", c1, c2, c3);

            var log  = new List <int>();
            var lst1 = new List <string>();
            var lst2 = new List <string>();

            SubscriptionVisitor
            .Do <IMyOperator>(op => { log.Add(1); lst1.Add(op.Name); })
            .Do <IMySpecialOperator>(op => { log.Add(2); lst2.Add(op.Name); })
            .Apply(p);

            Assert.IsTrue(new[] { 1, 1, 1, 2, 1, 2, 1 }.SequenceEqual(log));
            Assert.IsTrue(new[] { "p", "c1", "g1", "c2", "c3" }.SequenceEqual(lst1));
            Assert.IsTrue(new[] { "g1", "c2" }.SequenceEqual(lst2));
        }
Пример #6
0
 private static void Start(ISubscription o)
 {
     SubscriptionVisitor.Do <IOperator>(op => op.Start()).Apply(o);
 }
                public void Collect()
                {
                    var trace = _queryEngine.TraceSource;

                    var enabled = _queryEngine.Options.GarbageCollectionEnabled;

                    if (!enabled)
                    {
                        trace.RegistryGarbageCollection_NotEnabled(_queryEngine.Uri);
                        return;
                    }

                    trace.RegistryGarbageCollection_Started(_queryEngine.Uri);

                    var sw = Stopwatch.StartNew();

                    var allDependenciesList = new List <Uri>();

                    var visitor = SubscriptionVisitor.Do <IDependencyOperator>(op => { allDependenciesList.AddRange(op.Dependencies); });

                    foreach (var sub in _queryEngine._registry.Subscriptions)
                    {
                        var value = sub.Value;
                        if (value != null)
                        {
                            var instance = value.Instance;
                            if (instance != null && value.IsInitialized)
                            {
                                visitor.Apply(instance);
                            }
                        }
                    }

                    foreach (var sub in _queryEngine._registry.Subjects)
                    {
                        var value = sub.Value;
                        if (value != null)
                        {
                            var instance = value.Instance;
                            if (instance != null && value.IsInitialized)
                            {
                                if (instance is IDependencyOperator op)
                                {
                                    allDependenciesList.AddRange(op.Dependencies);
                                }
                            }
                        }
                    }

                    var allDependencies = new HashSet <Uri>(allDependenciesList);

                    var markTime = sw.Elapsed;

                    trace.RegistryGarbageCollection_LiveDependencies(_queryEngine.Uri, allDependencies.Count, (int)markTime.TotalMilliseconds);

                    sw.Restart();

                    var observables            = _queryEngine._registry.Observables;
                    var unreachableObservables = 0;

                    foreach (var obs in observables)
                    {
                        var value = obs.Value;
                        if (value != null)
                        {
                            //
                            // NB: Right now, we take a narrow approach for known entities that cannot be top-level nodes (i.e.
                            //     they are always owned by a parent, and such a parent should be found for them to be alive).
                            //
                            //     A more complete implementation should have a mechanism to discover these, because they are
                            //     really dependent on the operator library used (with the exception of e.g. edges), and thus
                            //     this violates the layering map right now.
                            //

                            if (obs.Key.EndsWith("/upstream-observable", StringComparison.Ordinal))
                            {
                                if (!allDependencies.Contains(value.Uri))
                                {
                                    unreachableObservables++;
                                    _collectibleEntities.Enqueue(value);
                                }
                            }
                        }
                    }

                    //
                    // NB: Removed various internal-only identifiers from libraries other than Reaqtor for the OSS release.
                    //

                    var scanTime = sw.Elapsed;

                    trace.RegistryGarbageCollection_UnreachableObservables(_queryEngine.Uri, unreachableObservables, observables.Values.Count, (int)scanTime.TotalMilliseconds);

                    if (!_queryEngine.Options.GarbageCollectionSweepEnabled)
                    {
                        trace.RegistryGarbageCollection_SweepDisabled(_queryEngine.Uri);
                    }
                }