示例#1
0
        private object LockOperation()
        {
            do
            {
                if (id == null)
                {
                    long   sessionId = Zookeeper.SessionId;
                    string prefix    = "x-" + sessionId + "-";
                    FindPrefixInChildren(prefix, Zookeeper, dir);
                    idName = new ZNodeName(id);
                }

                if (id == null)
                {
                    continue;
                }

                List <string> names = Zookeeper.GetChildren(dir, false);
                if (names.IsEmpty())
                {
                    LOG.Warn("No children in: " + dir + " when we've just " +
                             "created one! Lets recreate it...");
                    // lets force the recreation of the id
                    id = null;
                }
                else
                {
                    // lets sort them explicitly (though they do seem to come back in order ususally :)
                    var sortedNames = new SortedSet <ZNodeName>();
                    foreach (string name in names)
                    {
                        sortedNames.Add(new ZNodeName(dir.Combine(name)));
                    }
                    ownerId = sortedNames.First().Name;
                    SortedSet <ZNodeName> lessThanMe = sortedNames.HeadSet(idName);
                    if (!lessThanMe.IsEmpty())
                    {
                        ZNodeName lastChildName = lessThanMe.Last();
                        lastChildId = lastChildName.Name;
                        if (LOG.IsDebugEnabled)
                        {
                            LOG.Debug("watching less than me node: " + lastChildId);
                        }
                        Stat stat = Zookeeper.Exists(lastChildId, new LockWatcher(this));
                        if (stat != null)
                        {
                            return(false);
                        }

                        LOG.Warn("Could not find the stats for less than me: " + lastChildName.Name);
                    }
                    else
                    {
                        if (Owner)
                        {
                            OnLockAcquired();
                            return(true);
                        }
                    }
                }
            } while (id == null);
            return(false);
        }
示例#2
0
        public bool RunForLeader()
        {
            long   sessionId = Zookeeper.SessionId;
            string prefix    = "election-" + sessionId + "-";
            var    names     = Zookeeper.GetChildren(path, false);

            // See whether we have already run for election in this process
            foreach (string name in names)
            {
                if (name.StartsWith(prefix))
                {
                    id = name;
                    if (LOG.IsDebugEnabled)
                    {
                        LOG.DebugFormat("Found id created last time: {0}", id);
                    }
                }
            }

            if (id == null)
            {
                id = Zookeeper.Create(path.Combine(prefix), data, Acl, CreateMode.EphemeralSequential);

                if (LOG.IsDebugEnabled)
                {
                    LOG.DebugFormat("Created id: {0}", id);
                }
            }

            idName = new ZNodeName(id);

            names = Zookeeper.GetChildren(path, false);
            var sortedNames = new SortedSet <ZNodeName>();

            foreach (var name in names)
            {
                sortedNames.Add(new ZNodeName(name));
            }

            var priors = sortedNames.HeadSet(idName);

            if (priors.Count == 0)
            {
                throw new InvalidOperationException("Count of priors is 0, but should at least include this node.");
            }

            if (priors.Count == 1)
            {
                IsOwner = true;
                watcher.TakeLeadership();
                return(true);
            }
            // only watch the node directly before us
            ZNodeName penultimate = null, last = null;

            foreach (var name in sortedNames)
            {
                penultimate = last;
                last        = name;
            }
            if (penultimate == null)
            {
                throw new InvalidOperationException("Penultimate value in priors is null, but count shoudl have been at least 2.");
            }
            var penultimatePath = path.Combine(penultimate.Name);

            if (Zookeeper.Exists(penultimatePath, new LeaderWatcher(Zookeeper, this, penultimatePath, watcher, path, id)) == null)
            {
                IsOwner = true;
                watcher.TakeLeadership();
                return(true);
            }
            return(false);
        }