Пример #1
0
 public bool IsObedientFollower(Followership follower)
 {
     return(Tock <= follower.Tock + FollowershipLeeway);
 }
Пример #2
0
 public bool IsDeadFollower(Followership follower)
 {
     return((Term == follower.Term && Tock > follower.Tock + FollowershipInsolence) ||
            (Term > follower.Term && Tock > FollowershipInsolence));
 }
        void Follow()
        {
            using (var session = RavenFactory.OpenSession())
            {
                var l = session.Advanced.Lazily.Load <Leadership>(Leadership.Identifier);
                var m = session.Advanced.Lazily.Load <Followership>(Followership.FormatId(ProcessIdentity));
                session.Advanced.Eagerly.ExecuteAllPendingLazyOperations();

                var leadership = l.Value ?? new Leadership();
                var me         = m.Value;

                if (me == null)
                {
                    me = new Followership(ProcessIdentity);
                    session.Store(me);
                }

                if (leadership.Status == Leadership.ClusterStatus.Turmoil ||
                    leadership.DeniedAssignment(ProcessIdentity))
                {
                    while (_workQueue.Count > 0)
                    {
                        RavenTransportMessage trash;
                        _workQueue.TryTake(out trash); //clear the queue
                    }

                    Thread.Sleep(10);       //make sure workers have enough time to get their work in the InProgress collection
                    RecentMessages.Clear(); //we're clearing the decks, so forget what we've seen and rely on db
                }

                if (RecentMessages.Count == 0)
                {
                    me.LastSequenceNumber = 0;
                }

                if (leadership.Status == Leadership.ClusterStatus.Harmony &&
                    leadership.HasAssignment(ProcessIdentity))
                {
                    var assignment = leadership.GetAssignment(ProcessIdentity);

                    var take = MaxMessagesToRead - _workQueue.Count;

                    RavenQueryStatistics stats = null;

                    var messages =
                        session.Query <RavenTransportMessage, RavenTransportMessageIndex>()
                        .Statistics(out stats)
                        .Where(x => x.Destination == _address.Queue)
                        .Where(x => x.ClaimTicket >= assignment.LowerBound && x.ClaimTicket <= assignment.UpperBound)
                        .Where(x => x.SequenceNumber >= me.LastSequenceNumber)
                        .OrderBy(x => x.SequenceNumber)
                        .Take(take)
                        .ToList();

                    Console.WriteLine("Follower Query Stats: {0:N0}", stats.DurationMilliseconds);

                    messages = messages.Where(x => !RecentMessages.Contains(x.Id)).ToList();
                    messages.ForEach(_workQueue.Add);
                    messages.Select(x => x.Id).ToList().ForEach(RecentMessages.Enqueue);

                    if (messages.Any())
                    {
                        me.LastSequenceNumber = messages.Last().SequenceNumber;
                    }
                }

                var progress = InProgress.Select(x => x.Value).Where(x => !string.IsNullOrWhiteSpace(x)).ToList();
                me.MakeReportForLeader(leadership, progress);
                session.SaveChanges();
            }
        }