public async Task <ConditionalValue <TValue> > TryDequeueAsync(ITransaction tx, CancellationToken cancellationToken = default, TimeSpan?timeout = null)
        {
            if (reliableConcurrentQueue == null)
            {
                await InitializeReliableQueue();
            }

            return(await reliableConcurrentQueue.TryDequeueAsync(tx, cancellationToken, timeout));
        }
Exemple #2
0
        /// <inheritdoc />
        /// <summary>
        /// This is the main entry point for your service replica.
        /// This method executes when this replica of your service becomes primary and has write status.
        /// </summary>
        /// <param name="cancellationToken">Canceled when Service Fabric needs to shut down this service replica.</param>
        protected override async Task RunAsync(CancellationToken cancellationToken)
        {
            InitInflightQueue();
            while (true)
            {
                cancellationToken.ThrowIfCancellationRequested();

                try
                {
                    using (var tx = StateManager.CreateTransaction())
                    {
                        var message = await _inflightQueue.TryDequeueAsync(tx, cancellationToken);

                        if (message.HasValue)
                        {
                            await _clusterNotifier.DistributeToCluster(message.Value, cancellationToken,
                                                                       Context.CodePackageActivationContext.ApplicationName);
                        }

                        await tx.CommitAsync();
                    }
                }
                catch (OperationCanceledException) //cancellation requested
                {
                    throw;
                }
                catch (Exception e) //anything else
                {
                    _bigBrother.Publish(e.ToExceptionEvent());
                }

                await Task.Delay(WaitTimeBetweenLoop, cancellationToken);
            }
            // ReSharper disable once FunctionNeverReturns
        }
        public async Task <List <T> > GetPayments(int batchSize, CancellationToken cancellationToken)
        {
            var list = new List <T>();

            for (var i = 0; i < batchSize; i++)
            {
                var ret = await queue.TryDequeueAsync(transactionProvider.Current, cancellationToken);

                if (ret.HasValue)
                {
                    list.Add(ret.Value);
                    logger.LogDebug($"Object {Describe(ret.Value)} of type {typeof(T)} removed from cache. Transaction {transactionProvider.Current.TransactionId}.");
                }
                else
                {
                    break; //no more items
                }
            }

            if (list.Any())
            {
                logger.LogDebug($"Removing object: {string.Join(", ", list.Select(Describe))} Transaction: {transactionProvider.Current.TransactionId}");
            }
            return(list);
        }
Exemple #4
0
        protected override async Task <ConditionalValue <byte[]> > TryDequeueAsync(ServiceFabricTransaction tx, IReliableState collectionBase, CancellationToken cancellationToken)
        {
            IReliableConcurrentQueue <byte[]> collection = (IReliableConcurrentQueue <byte[]>)collectionBase;

            ConditionalValue <byte[]> message = await collection.TryDequeueAsync(tx.Tx, cancellationToken, TimeSpan.FromSeconds(4));

            return(message);
        }
        private static async Task <Trade> ExecuteDequeueAsync(ITransaction tx, IReliableConcurrentQueue <Trade> transactions, CancellationToken cancellationToken)
        {
            Trade trade  = null;
            var   result = await transactions.TryDequeueAsync(tx, cancellationToken);

            if (result.HasValue)
            {
                trade = result.Value;
            }
            return(trade);
        }
Exemple #6
0
        /// <summary>
        /// this method keeps on dequeuing the payload from the queue and processes it..
        /// </summary>
        /// <returns></returns>
        private async Task ProcessJobAsync(IReliableConcurrentQueue <string> processQueue)
        {
            using (var tx = StateManager.CreateTransaction())
            {
                var result = await processQueue.TryDequeueAsync(tx);

                if (result.HasValue)
                {
                    // Do the work
                }

                await tx.CommitAsync();
            }
        }
Exemple #7
0
        private async Task ProcessAsync()
        {
            if (_queue.Count == 0)
            {
                return;
            }

            ProcessingState = State.Processing;

            using (var tx = StateManager.CreateTransaction())
            {
                var message = await _queue.TryDequeueAsync(tx, _cancellationToken);

                if (!message.HasValue)
                {
                    tx.Abort();
                }

                if (await TryProcessMessageAsync(message.Value))
                {
                    await tx.CommitAsync();
                }
                else
                {
                    tx.Abort();
                }
            }

            //Synchronize message count in queue and semaphore
            var delta = Convert.ToInt32(_queue.Count - _signal.CurrentCount);

            if (delta > 0)
            {
                _signal.Release(delta);
            }
        }
Exemple #8
0
        private async Task ReceiveMessagesAsync(Func <IEnumerable <QueueMessage>, Task> onMessage, int maxBatchSize, CancellationToken cancellationToken)
        {
            var messages = new List <QueueMessage>();

            while (!cancellationToken.IsCancellationRequested && !_disposed)
            {
                try
                {
                    using (var tx = new ServiceFabricTransaction(_stateManager, null))
                    {
                        IReliableConcurrentQueue <byte[]> collection = await GetCollectionAsync();

                        while (messages.Count < maxBatchSize)
                        {
                            ConditionalValue <byte[]> message = await collection.TryDequeueAsync(tx.Tx, cancellationToken);

                            if (message.HasValue)
                            {
                                QueueMessage qm = QueueMessage.FromByteArray(message.Value);

                                messages.Add(qm);
                            }
                            else
                            {
                                break;
                            }
                        }

                        //make the call before committing the transaction
                        if (messages.Count > 0)
                        {
                            await onMessage(messages);

                            messages.Clear();
                        }

                        await tx.CommitAsync();
                    }
                }
                catch (Exception ex)
                {
                    Trace.Fail($"failed to listen to messages on queue '{_queueName}'", ex.ToString());
                }

                await Task.Delay(_scanInterval);
            }
        }
        public async static Task RunAsync(
            CancellationToken cancellationToken,
            IGitHubClient gitHubClient,
            IReliableStateManager stateManager,
            IUserRepoSearchActorProvider userRepoSearchActorProvider)
        {
            IReliableConcurrentQueue <ScrapingTask> firstTaskQueue =
                await GetFirstTaskQueue(stateManager);

            IReliableConcurrentQueue <ScrapingTask> secondTaskQueue =
                await GetSecondTaskQueue(stateManager);

            while (true)
            {
                cancellationToken.ThrowIfCancellationRequested();
                if (firstTaskQueue.Count > 0 || secondTaskQueue.Count > 0)
                {
                    using (var tx = stateManager.CreateTransaction())
                    {
                        var dequeued = await firstTaskQueue.TryDequeueAsync(tx, cancellationToken);

                        if (!dequeued.HasValue)
                        {
                            dequeued = await secondTaskQueue.TryDequeueAsync(tx, cancellationToken);
                        }

                        await ProcessScrapingTask(
                            scrapingTask : dequeued.Value,
                            gitHubClient : gitHubClient, tx : tx,
                            firstTaskQueue : firstTaskQueue,
                            secondTaskQueue : secondTaskQueue,
                            userRepoSearchActorProvider : userRepoSearchActorProvider);

                        await tx.CommitAsync();
                    }
                }
                else
                {
                    await Task.Delay(Constants.EMPTY_DELAY, cancellationToken);
                }
            }
        }
Exemple #10
0
        public async Task RunAsync(CancellationToken cancellationToken)
        {
            IReliableConcurrentQueue <DependencyUpdateItem> queue =
                await StateManager.GetOrAddAsync <IReliableConcurrentQueue <DependencyUpdateItem> >("queue");

            while (!cancellationToken.IsCancellationRequested)
            {
                try
                {
                    using (ITransaction tx = StateManager.CreateTransaction())
                    {
                        ConditionalValue <DependencyUpdateItem> maybeItem = await queue.TryDequeueAsync(
                            tx,
                            cancellationToken);

                        if (maybeItem.HasValue)
                        {
                            DependencyUpdateItem item = maybeItem.Value;
                            using (Logger.BeginScope(
                                       "Processing dependency update for build {buildId} in channel {channelId}",
                                       item.BuildId,
                                       item.ChannelId))
                            {
                                await UpdateDependenciesAsync(item.BuildId, item.ChannelId);
                            }
                        }

                        await tx.CommitAsync();
                    }

                    await Task.Delay(1000, cancellationToken);
                }
                catch (TaskCanceledException tcex) when(tcex.CancellationToken == cancellationToken)
                {
                    // ignore
                }
                catch (Exception ex)
                {
                    Logger.LogError(ex, "Processing queue messages");
                }
            }
        }
Exemple #11
0
        protected override async Task RunAsync(CancellationToken cancellationToken)
        {
            if (_queue == null)
            {
                // we can make an interesting assumption here
                _queue = await this.StateManager.GetOrAddAsync <IReliableConcurrentQueue <DataPoint> >(QueueName);
            }

            // not sure this works?
            while (!cancellationToken.IsCancellationRequested)
            {
                var  buffer = new List <DataPoint>();
                bool state  = true;
                using (var tx = this.StateManager.CreateTransaction())
                {
                    // process the queue
                    ConditionalValue <DataPoint> point;
                    while ((point = await _queue.TryDequeueAsync(tx, cancellationToken)).HasValue)
                    {
                        buffer.Add(point.Value);

                        if (buffer.Count >= 100)
                        {
                            state = state && Flush(buffer, cancellationToken);
                        }
                    }

                    // if all the flushes succeed
                    if (state && Flush(buffer, cancellationToken))
                    {
                        await tx.CommitAsync();
                    }
                    else
                    {
                        tx.Abort();
                    }
                }

                Thread.Sleep(TimeSpan.FromSeconds(10));
            }
        }
        public async Task <TimeSpan> RunAsync(CancellationToken cancellationToken)
        {
            IReliableConcurrentQueue <ReleasePipelineRunnerItem> queue =
                await StateManager.GetOrAddAsync <IReliableConcurrentQueue <ReleasePipelineRunnerItem> >("queue");

            try
            {
                using (ITransaction tx = StateManager.CreateTransaction())
                {
                    ConditionalValue <ReleasePipelineRunnerItem> maybeItem = await queue.TryDequeueAsync(
                        tx,
                        cancellationToken);

                    if (maybeItem.HasValue)
                    {
                        ReleasePipelineRunnerItem item = maybeItem.Value;
                        using (Logger.BeginScope(
                                   $"Triggering release pipelines associated with channel {item.ChannelId} for build {item.BuildId}.",
                                   item.BuildId,
                                   item.ChannelId))
                        {
                            await RunAssociatedReleasePipelinesAsync(item.BuildId, item.ChannelId, cancellationToken);
                        }
                    }

                    await tx.CommitAsync();
                }
            }
            catch (TaskCanceledException tcex) when(tcex.CancellationToken == cancellationToken)
            {
                return(TimeSpan.MaxValue);
            }
            catch (Exception ex)
            {
                Logger.LogError(ex, "Processing queue messages");
            }

            return(TimeSpan.FromSeconds(1));
        }
        public async Task <TimeSpan> RunAsync(CancellationToken cancellationToken)
        {
            IReliableConcurrentQueue <DependencyUpdateItem> queue =
                await StateManager.GetOrAddAsync <IReliableConcurrentQueue <DependencyUpdateItem> >("queue");

            try
            {
                using (ITransaction tx = StateManager.CreateTransaction())
                {
                    ConditionalValue <DependencyUpdateItem> maybeItem = await queue.TryDequeueAsync(
                        tx,
                        cancellationToken);

                    if (maybeItem.HasValue)
                    {
                        DependencyUpdateItem item = maybeItem.Value;
                        using (Logger.BeginScope(
                                   "Processing dependency update for build {buildId} in channel {channelId}",
                                   item.BuildId,
                                   item.ChannelId))
                        {
                            await UpdateDependenciesAsync(item.BuildId, item.ChannelId);
                        }
                    }

                    await tx.CommitAsync();
                }
            }
            catch (TaskCanceledException tcex) when(tcex.CancellationToken == cancellationToken)
            {
                return(TimeSpan.MaxValue);
            }
            catch (Exception ex)
            {
                Logger.LogError(ex, "Processing queue messages");
            }

            return(TimeSpan.FromSeconds(1));
        }
Exemple #14
0
        private async Task Populate(CancellationToken cancellationToken)
        {
            IReliableConcurrentQueue <string> list = await this.GetQueueAsync();

            using (ITransaction tx = this.stateManager.CreateTransaction())
            {
                await list.EnqueueAsync(tx, Guid.NewGuid().ToString(), cancellationToken);

                await tx.CommitAsync();
            }
            using (ITransaction tx = this.stateManager.CreateTransaction())
            {
                await list.EnqueueAsync(tx, Guid.NewGuid().ToString(), cancellationToken);

                await tx.CommitAsync();
            }
            using (ITransaction tx = this.stateManager.CreateTransaction())
            {
                await list.TryDequeueAsync(tx, cancellationToken);

                await tx.CommitAsync();
            }
        }
Exemple #15
0
        public async Task <TimeSpan> RunAsync(CancellationToken cancellationToken)
        {
            IReliableConcurrentQueue <ReleasePipelineRunnerItem> queue =
                await StateManager.GetOrAddAsync <IReliableConcurrentQueue <ReleasePipelineRunnerItem> >("queue");

            try
            {
                using (ITransaction tx = StateManager.CreateTransaction())
                {
                    ConditionalValue <ReleasePipelineRunnerItem> maybeItem = await queue.TryDequeueAsync(
                        tx,
                        cancellationToken);

                    if (maybeItem.HasValue)
                    {
                        ReleasePipelineRunnerItem item = maybeItem.Value;

                        Build build = await Context.Builds
                                      .Where(b => b.Id == item.BuildId).FirstOrDefaultAsync();

                        if (build == null)
                        {
                            Logger.LogError($"Could not find the specified BAR Build {item.BuildId} to run a release pipeline.");
                        }
                        else if (build.AzureDevOpsBuildId == null)
                        {
                            // If something uses the old API version we won't have this information available.
                            // This will also be the case if something adds an existing build (created using
                            // the old API version) to a channel
                            Logger.LogInformation($"barBuildInfo.AzureDevOpsBuildId is null for BAR Build.Id {build.Id}.");
                        }
                        else
                        {
                            AzureDevOpsClient azdoClient = await GetAzureDevOpsClientForAccount(build.AzureDevOpsAccount);

                            var azdoBuild = await azdoClient.GetBuildAsync(
                                build.AzureDevOpsAccount,
                                build.AzureDevOpsProject,
                                build.AzureDevOpsBuildId.Value);

                            if (azdoBuild.Status.Equals("completed", StringComparison.OrdinalIgnoreCase))
                            {
                                await HandleCompletedBuild(item, azdoBuild, cancellationToken);
                            }
                            else
                            {
                                Logger.LogInformation($"AzDO build {azdoBuild.BuildNumber}/{azdoBuild.Definition.Name} with BAR BuildId {build.Id} is still in progress.");

                                // Build didn't finish yet. Let's wait some time and try again.
                                EnqueueBuildStatusCheck(item, 0);
                            }
                        }
                    }

                    await tx.CommitAsync();
                }
            }
            catch (TaskCanceledException tcex) when(tcex.CancellationToken == cancellationToken)
            {
                return(TimeSpan.MaxValue);
            }
            catch (Exception ex)
            {
                Logger.LogError(ex, "Processing queue messages");
            }

            return(TimeSpan.FromMinutes(1));
        }
Exemple #16
0
        protected override async Task RunAsync(CancellationToken cancellationToken)
        {
            int  batchSize = 100;
            long delayMs   = 20;

            surveyQueue = await this.StateManager.GetOrAddAsync <IReliableConcurrentQueue <ClientModels.SurveyAnswer> >("surveyQueue");

            ISurveyAnalysisService surveyAnalysisService = new Tailspin.SurveyAnalysisService.Client.SurveyAnalysisService();

            List <ClientModels.SurveyAnswer> processItems = new List <ClientModels.SurveyAnswer>();

            try
            {
                while (!cancellationToken.IsCancellationRequested)
                {
                    cancellationToken.ThrowIfCancellationRequested();

                    using (var tx = this.StateManager.CreateTransaction())
                    {
                        ConditionalValue <ClientModels.SurveyAnswer> ret;

                        for (int i = 0; i < batchSize; ++i)
                        {
                            ret = await surveyQueue.TryDequeueAsync(tx, cancellationToken);

                            if (ret.HasValue)
                            {
                                processItems.Add(ret.Value.DeepCopy());
                            }
                            else
                            {
                                break;
                            }
                        }

                        if (processItems.Count > 0)
                        {
                            foreach (var sa in processItems)
                            {
                                var model = sa.ToSurveyAnswer();
                                model.CreatedOn = DateTime.UtcNow;

                                var container = new AzureBlobContainer <ApiModels.SurveyAnswer>(
                                    ServiceFabricConfiguration.GetCloudStorageAccount(),
                                    $"{model.SlugName}-answers");

                                try
                                {
                                    await container.SaveAsync(model.Id, model);
                                }
                                catch (StorageException ex)
                                {
                                    if (ex.Message.Contains("404"))
                                    {
                                        await container.EnsureExistsAsync();

                                        await container.SaveAsync(model.Id, model);
                                    }
                                    else
                                    {
                                        throw ex;
                                    }
                                }

                                await this.AppendSurveyAnswerIdToSurveyAnswerListAsync(model.SlugName, model.Id);

                                await surveyAnalysisService.MergeSurveyAnswerToAnalysisAsync(model.ToAnalysisServiceSurveyAnswer());
                            }

                            processItems.Clear();
                        }

                        await tx.CommitAsync();
                    }

                    await Task.Delay(TimeSpan.FromMilliseconds(delayMs), cancellationToken);
                }
            }
            catch (Exception ex)
            {
                ServiceEventSource.Current.ServiceRequestFailed(ex.ToString());
                throw;
            }
        }
Exemple #17
0
        private async Task <bool> MatchmakeOneGame(CancellationToken cancellationToken, IReliableConcurrentQueue <UserRequest> queue, IReliableDictionary <ActorInfo, PlayersInMatch> usedActors, IReliableDictionary <UserRequest, ActorInfo> matchmakedUsers)
        {
            try
            {
                ConditionalValue <UserRequest> ret;
                PlayersInMatch players = new PlayersInMatch();
                ActorInfo      actorId;

                using (var tx = this.StateManager.CreateTransaction())
                {
                    do
                    {
                        ret = await queue.TryDequeueAsync(tx, cancellationToken);

                        if (ret.HasValue)
                        {
                            players = players.AddPlayer(new UserRequest(ret.Value));
                        }
                    }while (!cancellationToken.IsCancellationRequested && ret.HasValue && players.Count < MatchSize);

                    if (cancellationToken.IsCancellationRequested || players.Count != MatchSize)
                    {
                        ServiceEventSource.Current.ServiceMessage(this.Context, cancellationToken.IsCancellationRequested ? $"Cancellation requested!" : $"Not enough players in the queue to matchmake!");
                        tx.Abort();
                        return(false);
                    }

                    // found enough players - assign them actor
                    //bool usedActor = false;
                    //do
                    //{
                    //    actorId = ActorId.CreateRandom();
                    //    usedActor = await usedActors.ContainsKeyAsync(tx, actorId);
                    //}
                    //while (!cancellationToken.IsCancellationRequested && usedActor);

                    actorId = await GetSimulationActorId(tx, cancellationToken);

                    if (cancellationToken.IsCancellationRequested)
                    {
                        ServiceEventSource.Current.ServiceMessage(this.Context, $"Cancellation requested!");
                        tx.Abort();
                        return(false);
                    }

                    bool added = await usedActors.TryAddAsync(tx, actorId, players);

                    if (!added)
                    {
                        ServiceEventSource.Current.ServiceMessage(this.Context, $"Tried to add already used actor {actorId}");
                        tx.Abort();
                        return(false);
                    }

                    var playersToAdd = players.GetList();
                    List <UserRequest> addedPlayers = new List <UserRequest>();

                    foreach (var player in playersToAdd)
                    {
                        added = await matchmakedUsers.TryAddAsync(tx, player, actorId);

                        if (added)
                        {
                            addedPlayers.Add(player);
                        }
                    }

                    if (addedPlayers.Count != playersToAdd.Count)
                    {
                        foreach (var player in addedPlayers)
                        {
                            await matchmakedUsers.TryRemoveAsync(tx, player);

                            await queue.EnqueueAsync(tx, player);
                        }
                        ServiceEventSource.Current.ServiceMessage(this.Context, $"Some duplicated requests encountered");
                    }

                    await tx.CommitAsync();
                }

                List <UserRequest> playersList = players.GetList();

                // Create actor simulation
                int index = actorId.ActorIndex;

                string           suffix          = GetSimulationActorNameSuffix(index);
                string           actorServiceUri = $"{this.context.CodePackageActivationContext.ApplicationName}/SimulationActorService{suffix}";
                ISimulationActor simulationActor = ActorProxy.Create <ISimulationActor>(actorId.ActorId, new Uri(actorServiceUri));

                bool simulated = await simulationActor.SimulateMatch(playersList, actorId);

                if (!simulated)
                {
                    ServiceEventSource.Current.Message($"Something went wrong with simulation");
                    return(false);
                }

                await simulationActor.SubscribeAsync <ISimulationEvents>(this, ResubsriptionInterval);

                // Notify clients
                IWebService webService = ServiceProxy.Create <IWebService>(new Uri($"{this.context.CodePackageActivationContext.ApplicationName}/WebService"));
                await webService.StartGame(actorId, playersList);

                StringBuilder builder = new StringBuilder();
                builder.Append($"Created new match\n ActorID: {actorId}\n");

                for (int i = 0; i < players.Count; i++)
                {
                    builder.Append($"UserID_{i}: {playersList[i]}\n");
                }

                ServiceEventSource.Current.ServiceMessage(this.Context, builder.ToString());

                return(true);
            }
            catch (Exception ex)
            {
                ServiceEventSource.Current.Message(string.Format("Exception {0}", ex));
                return(false);
            }
        }
        protected override async Task RunAsync(CancellationToken cancellationToken)
        {
            IReliableConcurrentQueue <ReportProcessingStep> processQueue
                = await this.StateManager.GetOrAddAsync <IReliableConcurrentQueue <ReportProcessingStep> >(ProcessingQueueName);

            IReliableDictionary <string, ReportStatus> statusDictionary
                = await this.StateManager.GetOrAddAsync <IReliableDictionary <string, ReportStatus> >(StatusDictionaryName);

            // queue up all the processing steps and create an initial processing status if one doesn't exist already
            using (ITransaction tx = this.StateManager.CreateTransaction())
            {
                ConditionalValue <ReportStatus> tryGetResult
                    = await statusDictionary.TryGetValueAsync(tx, this.reportContext.Name, LockMode.Update);

                if (!tryGetResult.HasValue)
                {
                    foreach (string processingStep in processingSteps)
                    {
                        cancellationToken.ThrowIfCancellationRequested();

                        await processQueue.EnqueueAsync(tx, new ReportProcessingStep(processingStep));
                    }

                    await statusDictionary.AddAsync(tx, this.reportContext.Name, new ReportStatus(0, "Not started."));
                }

                await tx.CommitAsync();
            }

            // start processing and checkpoint between each step so we don't lose any progress in the event of a fail-over
            while (true)
            {
                cancellationToken.ThrowIfCancellationRequested();

                try
                {
                    using (ITransaction tx = this.StateManager.CreateTransaction())
                    {
                        ConditionalValue <ReportProcessingStep> dequeueResult = await processQueue.TryDequeueAsync(tx, cancellationToken);

                        if (!dequeueResult.HasValue)
                        {
                            // all done!
                            break;
                        }

                        ReportProcessingStep currentProcessingStep = dequeueResult.Value;

                        ServiceEventSource.Current.ServiceMessage(
                            this.Context,
                            $"Processing step: {currentProcessingStep.Name}");

                        // This takes a shared lock rather than an update lock
                        // because this is the only place the row is written to.
                        // If there were other writers, then this should be an update lock.
                        ConditionalValue <ReportStatus> dictionaryGetResult =
                            await statusDictionary.TryGetValueAsync(tx, this.reportContext.Name, LockMode.Default);

                        ReportStatus currentStatus = dictionaryGetResult.Value;
                        ReportStatus newStatus     = await this.ProcessReport(currentStatus, currentProcessingStep, cancellationToken);

                        await statusDictionary.SetAsync(tx, this.reportContext.Name, newStatus);

                        await tx.CommitAsync();
                    }
                }
                catch (TimeoutException)
                {
                    // transient error. Retry.
                    ServiceEventSource.Current.ServiceMessage(this.Context, "TimeoutException in RunAsync.");
                }
                catch (FabricTransientException fte)
                {
                    // transient error. Retry.
                    ServiceEventSource.Current.ServiceMessage(this.Context, "FabricTransientException in RunAsync: {0}", fte.Message);
                }
                catch (FabricNotPrimaryException)
                {
                    // not primary any more, time to quit.
                    return;
                }
                catch (FabricNotReadableException)
                {
                    // retry or wait until not primary
                    ServiceEventSource.Current.ServiceMessage(this.Context, "FabricNotReadableException in RunAsync.");
                }
                catch (Exception ex)
                {
                    // all other exceptions: log and re-throw.
                    ServiceEventSource.Current.ServiceMessage(this.Context, "Exception in RunAsync: {0}", ex.Message);

                    throw;
                }

                // delay between each to step to prevent starving other processing service instances.
                await Task.Delay(TimeSpan.FromSeconds(10), cancellationToken);
            }


            ServiceEventSource.Current.ServiceMessage(
                this.Context,
                $"Processing complete!");
        }
Exemple #19
0
        protected override async Task RunAsync(CancellationToken cancellationToken)
        {
            IReliableConcurrentQueue <Trade> exportQueue =
                await this.StateManager.GetOrAddAsync <IReliableConcurrentQueue <Trade> >(QueueName);

            // Take each trade from the queue and insert
            // it into an external trade log store.
            while (true)
            {
                cancellationToken.ThrowIfCancellationRequested();

                try
                {
                    // Wait to process until logs are received, check anyway if timeout occurs
                    if (exportQueue.Count < 1)
                    {
                        await Task.Delay(TimeSpan.FromSeconds(2), cancellationToken);
                    }
                }
                catch (FabricNotReadableException)
                {
                    // Fabric is not yet readable - this is a transient exception
                    // Backing off temporarily before retrying
                    await BackOff(cancellationToken);

                    continue;
                }
                catch (FabricNotPrimaryException)
                {
                    return;
                }

                using (var tx = this.StateManager.CreateTransaction())
                {
                    try
                    {
                        // This can be batched...
                        var result = await exportQueue.TryDequeueAsync(tx, cancellationToken);

                        if (result.HasValue)
                        {
                            var trade = result.Value;
                            if (trade != null)
                            {
                                ServiceEventSource.Current.ServiceMessage(this.Context, $"Writing trade {trade.Id} to log");
                                if (tradeLogger == null)
                                {
                                    Init();
                                }
                                await tradeLogger?.InsertAsync(trade, cancellationToken);

                                await tx.CommitAsync();
                            }
                        }
                    }
                    catch (LoggerDisconnectedException)
                    {
                        // Logger may have lost connection
                        // Back off and retry connection
                        await BackOff(cancellationToken);

                        Init(); // reinitialize connection
                        continue;
                    }
                    catch (FabricNotPrimaryException)
                    {
                        // Attempted to perform write on a non
                        // primary replica.
                        ServiceEventSource.Current.ServiceMessage(this.Context, $"Fabric cannot perform write as it is not the primary replica");
                        return;
                    }
                    catch (FabricNotReadableException)
                    {
                        // Fabric is not yet readable - this is a transient exception
                        // Backing off temporarily before retrying
                        await BackOff(cancellationToken);

                        continue;
                    }
                    catch (InsertFailedException ex)
                    {
                        // Insert failed, assume connection problem and transient.
                        // backoff and retry
                        ServiceEventSource.Current.ServiceMessage(this.Context, $"Logger error,  {ex.Message}");
                        await BackOff(cancellationToken);

                        continue;
                    }
                }
            }
        }