Esempio n. 1
0
        /// <summary>
        ///     Used to get the event out of the node.
        /// </summary>
        /// <param name="actionNode">The action node to process.</param>
        /// <returns></returns>
        public bool Next(out EventActionNodePersist <TKey, TState, TEvent, TParam, TCtx, TUserId> actionNode)
        {
            if (Interlocked.CompareExchange(
                    ref this.currentRunningState,
                    RUNNING,
                    IDLE) == IDLE)
            {
                if (this.skipQueue.Next(out actionNode))
                {
                    this.currentEventNode = actionNode;
                    return(true);
                }
                Volatile.Write(ref this.currentRunningState, IDLE);
                return(false);
            }
            else if (Interlocked.CompareExchange(
                         ref this.currentRunningState,
                         RUNNING,
                         RETRY) == RETRY)
            {
                actionNode            = this.retryEvent;
                this.currentEventNode = this.retryEvent;
                this.retryEvent       = null;
                return(true);
            }

            actionNode = null;
            return(false);
        }
Esempio n. 2
0
        /// <summary>
        ///     Called when you are done with the event.
        /// </summary>
        /// <returns>The task that performs the update.</returns>
        public async Task DoneWithEvent()
        {
            while (true)
            {
                try
                {
                    if (this.currentEventNode == null)
                    {
                        log.Warn($"The current event node is null.  This should never happen.");
                    }
                    else
                    {
                        if (!this.currentEventNode.RunOnThread)
                        {
                            await this.eventPersistedStore.SaveResult(
                                this.currentEventNode.Id,
                                EventResultType.Completed);
                        }

                        this.currentEventNode = null;
                    }

                    Volatile.Write(ref this.currentRunningState, IDLE);
                    break;
                }
                catch (Exception ex)
                {
                    log.Error(ex, ex.Message);
                    Thread.Sleep(5);
                }
            }
        }
Esempio n. 3
0
 public void RetryEvent(
     EventActionNodePersist <TKey, TState, TEvent, TParam, TCtx, TUserId> eventActionNodePersist)
 {
     Interlocked.Increment(ref this.retryCount);
     Volatile.Write(ref this.retryEvent, eventActionNodePersist);
     this.currentEventNode = null;
     // TODO add a delay.  Will need to use either a retry data structure or just use a timer but there is a limit to the amount of timers.
     this.retryService.Retry(new TimeSpan(0, 0, this.CalculateDelay()), () => { this.newEventSubject.Next(); });
 }
Esempio n. 4
0
        public bool Skip(EventActionNodePersist <TKey, TState, TEvent, TParam, TCtx, TUserId> actionNode)
        {
            var added = this.skipQueue.AddDefer(actionNode);

            // Need to do this here since skip is a special event.
            Volatile.Write(ref this.currentRunningState, IDLE);
            if (!added)
            {
                this.eventPersistedStore.SaveResult(actionNode.Id, EventResultType.Full);
                log.Warn($"Skip queue is full. State machine id {actionNode.StateMachineKey} {actionNode.Id}");
            }

            return(added);
        }
Esempio n. 5
0
        public async Task <bool> Add(EventActionNodePersist <TKey, TState, TEvent, TParam, TCtx, TUserId> actionNode)
        {
            try
            {
                if (actionNode.RunOnThread)
                {
                    var result = this.skipQueue.Add(actionNode);
                    await this.newEventReceived.NewEvent((TCtx)this);

                    return(result);
                }
                else
                {
                    await this.eventPersistedStore.Save(actionNode);

                    var able = this.skipQueue.Add(actionNode);
                    if (able)
                    {
                        await this.newEventReceived.NewEvent((TCtx)this);

                        return(true);
                    }
                    else
                    {
                        await this.eventPersistedStore.SaveResult(actionNode.Id, EventResultType.Full);

                        return(false);
                    }
                }
            }
            catch (Exception ex)
            {
                log.Error(ex, ex.Message);
                // TODO Come up with a retry idea but ordering is important so this could be difficult.
                return(false);
            }
        }