Beispiel #1
0
        public async Task DispatchEffectsAsync(PropagationEffects effects)
        {
            await StatsHelper.RegisterMsg("EffectsDispatcherGrain::DispatchEffects", this.GrainFactory);

            Logger.LogInfoForDebug(this.GetLogger(), "@@[Dispatcher {0}] Dequeuing effects", this.GetPrimaryKey());

            this.lastProcessingTime   = DateTime.UtcNow;
            this.isDispatchingEffects = true;

            if (this.status != EffectsDispatcherStatus.Busy)
            {
                Logger.LogForRelease(this.GetLogger(), "@@[Dispatcher {0}] Becoming busy (before was {1})", this.GetPrimaryKey(), this.status);

                var oldStatus = this.status;
                this.status = EffectsDispatcherStatus.Busy;

                if (oldStatus == EffectsDispatcherStatus.Idle)
                {
                    // Notify that the dispatcher is busy
                    this.subscriptionManager.Notify(s => s.OnEffectsDispatcherStatusChanged(this, this.status));
                }
            }

            await this.effectsDispatcher.DispatchEffectsAsync(effects);

            this.lastProcessingTime   = DateTime.UtcNow;
            this.isDispatchingEffects = false;
        }
Beispiel #2
0
        private Task OnTimerTick(object state)
        {
            var idleTime = DateTime.UtcNow - lastProcessingTime;

            if (!this.isDispatchingEffects && this.status == EffectsDispatcherStatus.Inactive &&
                idleTime.TotalMilliseconds > AnalysisConstants.DispatcherInactiveThreshold)
            {
                Logger.LogForRelease(this.GetLogger(), "@@[Dispatcher {0}] Was inactive for too long", this.GetPrimaryKey());

                // Notify that this dispatcher was inactive for too long.
                this.subscriptionManager.Notify(s => s.OnEffectsDispatcherStatusChanged(this, this.status));
                // This is to avoid notifying inactive status every time the timer ticks after the first notification.
                this.lastProcessingTime = DateTime.UtcNow;
            }

            if (!this.isDispatchingEffects && this.status == EffectsDispatcherStatus.Busy &&
                idleTime.TotalMilliseconds > AnalysisConstants.DispatcherIdleThreshold)
            {
                Logger.LogForRelease(this.GetLogger(), "@@[Dispatcher {0}] Becoming idle (before was {1})", this.GetPrimaryKey(), this.status);

                // Notify that this dispatcher is idle.
                this.status = EffectsDispatcherStatus.Idle;
                this.subscriptionManager.Notify(s => s.OnEffectsDispatcherStatusChanged(this, this.status));
            }

            return(Task.CompletedTask);
        }
Beispiel #3
0
        public override async Task OnActivateAsync()
        {
            await StatsHelper.RegisterActivation("EffectsDispatcherGrain", this.GrainFactory);

            this.isDispatchingEffects = false;
            this.status             = EffectsDispatcherStatus.Inactive;
            this.lastProcessingTime = DateTime.UtcNow;             // DateTime.MinValue; // DateTime.MaxValue;
            this.solutionGrain      = OrleansSolutionManager.GetSolutionGrain(this.GrainFactory);
            this.effectsDispatcher  = new OrleansEffectsDispatcherManager(this.GrainFactory, this.solutionGrain);

            this.subscriptionManager = new ObserverSubscriptionManager <IAnalysisObserver>();

            var streamProvider = this.GetStreamProvider(AnalysisConstants.StreamProvider);
            var stream         = streamProvider.GetStream <PropagationEffects>(this.GetPrimaryKey(), AnalysisConstants.StreamNamespace);
            //await stream.SubscribeAsync(this);

            // Explicit subscription code
            var subscriptionHandles = await stream.GetAllSubscriptionHandles();

            if (subscriptionHandles != null && subscriptionHandles.Count > 0)
            {
                var tasks = new List <Task>();

                foreach (var subscriptionHandle in subscriptionHandles)
                {
                    var task = subscriptionHandle.ResumeAsync(this);
                    //await task;
                    tasks.Add(task);
                }

                await Task.WhenAll(tasks);
            }
            else
            {
                await stream.SubscribeAsync(this);
            }

            var period = TimeSpan.FromMilliseconds(AnalysisConstants.DispatcherTimerPeriod);

            this.timer = this.RegisterTimer(this.OnTimerTick, null, period, period);

            await base.OnActivateAsync();
        }
Beispiel #4
0
        void IAnalysisObserver.OnEffectsDispatcherStatusChanged(IEffectsDispatcherGrain sender, EffectsDispatcherStatus newStatus)
        {
            var dispatcherGuid = sender.GetPrimaryKey();
            var oldStatus      = this.dispatchersStatus[dispatcherGuid];

            this.dispatchersStatus[dispatcherGuid] = newStatus;

            Logger.LogForRelease(GrainClient.Logger, "@@[Client] Dispatcher {0} is {1} (before was {2})", dispatcherGuid, newStatus, oldStatus);
        }