private async Task <bool> SeedSubscription(Event evt, EventSubscription sub, List <string> toQueue, CancellationToken cancellationToken)
        {
            foreach (var eventId in await _persistenceStore.GetEvents(sub.EventName, sub.EventKey, sub.SubscribeAsOf))
            {
                if (eventId == evt.Id)
                {
                    continue;
                }

                var siblingEvent = await _persistenceStore.GetEvent(eventId);

                if ((!siblingEvent.IsProcessed) && (siblingEvent.EventTime < evt.EventTime))
                {
                    await QueueProvider.QueueWork(eventId, QueueType.Event);

                    return(false);
                }

                if (!siblingEvent.IsProcessed)
                {
                    toQueue.Add(siblingEvent.Id);
                }
            }

            if (!await _lockProvider.AcquireLock(sub.WorkflowId, cancellationToken))
            {
                Logger.LogInformation("Workflow locked {0}", sub.WorkflowId);
                return(false);
            }

            try
            {
                var workflow = await _persistenceStore.GetWorkflowInstance(sub.WorkflowId);

                var pointers = workflow.ExecutionPointers.Where(p => p.EventName == sub.EventName && p.EventKey == sub.EventKey && !p.EventPublished && p.EndTime == null);
                foreach (var p in pointers)
                {
                    p.EventData      = evt.EventData;
                    p.EventPublished = true;
                    p.Active         = true;
                }
                workflow.NextExecution = 0;
                await _persistenceStore.PersistWorkflow(workflow);

                await _persistenceStore.TerminateSubscription(sub.Id);

                return(true);
            }
            catch (Exception ex)
            {
                Logger.LogError(ex, ex.Message);
                return(false);
            }
            finally
            {
                await _lockProvider.ReleaseLock(sub.WorkflowId);

                await QueueProvider.QueueWork(sub.WorkflowId, QueueType.Workflow);
            }
        }
Esempio n. 2
0
        private async Task SubscribeEvent(EventSubscription subscription, IPersistenceProvider persistenceStore, CancellationToken cancellationToken)
        {
            //TODO: move to own class
            Logger.LogDebug("Subscribing to event {0} {1} for workflow {2} step {3}", subscription.EventName, subscription.EventKey, subscription.WorkflowId, subscription.StepId);

            await persistenceStore.CreateEventSubscription(subscription, cancellationToken);

            if (subscription.EventName != Event.EventTypeActivity)
            {
                var events = await persistenceStore.GetEvents(subscription.EventName, subscription.EventKey, subscription.SubscribeAsOf, cancellationToken);

                foreach (var evt in events)
                {
                    var  eventKey     = $"evt:{evt}";
                    bool acquiredLock = false;
                    try
                    {
                        acquiredLock = await _lockProvider.AcquireLock(eventKey, cancellationToken);

                        int attempt = 0;
                        while (!acquiredLock && attempt < 10)
                        {
                            await Task.Delay(Options.IdleTime, cancellationToken);

                            acquiredLock = await _lockProvider.AcquireLock(eventKey, cancellationToken);

                            attempt++;
                        }

                        if (!acquiredLock)
                        {
                            Logger.LogWarning($"Failed to lock {evt}");
                        }
                        else
                        {
                            _greylist.Remove(eventKey);
                            await persistenceStore.MarkEventUnprocessed(evt, cancellationToken);

                            await QueueProvider.QueueWork(evt, QueueType.Event);
                        }
                    }
                    finally
                    {
                        if (acquiredLock)
                        {
                            await _lockProvider.ReleaseLock(eventKey);
                        }
                    }
                }
            }
        }
Esempio n. 3
0
        private async Task SubscribeEvent(EventSubscription subscription, IPersistenceProvider persistenceStore)
        {
            //TODO: move to own class
            Logger.LogDebug("Subscribing to event {0} {1} for workflow {2} step {3}", subscription.EventName, subscription.EventKey, subscription.WorkflowId, subscription.StepId);

            await persistenceStore.CreateEventSubscription(subscription);

            var events = await persistenceStore.GetEvents(subscription.EventName, subscription.EventKey, subscription.SubscribeAsOf);

            foreach (var evt in events)
            {
                await persistenceStore.MarkEventUnprocessed(evt);

                await QueueProvider.QueueWork(evt, QueueType.Event);
            }
        }