Zookeeper:服务器和会话

会话(Session)构成了Zookeeper中的一个重要抽象。顺序保证(Ordering guarantee),临时节点(Ephemeral znode)和Watch都与会话紧密耦合。因此,Session追踪机制(Session track mechnism)对于Zookeeper来说是非常重要的。( (这篇博客是Flavio Junqueria和Benjamin Reed的Zookeeper书的第9章中Servers and Sessions的翻译)

Zookeeper服务器的一个重要任务就是持续追踪会话。在Standalone模式,一个服务器追踪所有的会话;而在Quorum模式,Leader追踪它们。事实上,Leader服务器和Standalone服务器运行着相同的会话追踪器(Session Tracker) (参考SessionTracker和SessionTrackerImpl)。Follower服务器仅仅是将所有客户端的会话信息转发给Leader(参考LearnerSessionTracker).

为了保持会话存活,服务器需要接收会话对应的心跳(Heartbeat)。心跳以新请求或显示的PING消息形式出现(参考LearnerHandler.run())。在这两种情况,服务器通过更新会话的失效时间来触摸(Touch)会话(参考SessionTrackerImpl.touchSession()),在Quorum模式,Leader发送PING消息给Learner,然后Learner返回自从上次PING消息后触摸到的会话列表。Leader每隔半个滴答(Tick)发送一个PING消息给Learner。滴答是Zookeeper用的最小时间单元,以毫秒表示。所以,如果滴答设置为2s,那么Leader每隔1s发送一个PING消息。

两个重要的点管理会话失效。为了实现会话失效,一个被称为失效队列(参考ExpiryQueue)的数据结构保存了会话信息。这个数据结构将会话保存在桶里,每个桶和一段会话被认为失效的时间范围相关联。Leader每次只将一个桶里的会话失效。为了决定是哪个桶失效,当到了下一个会话失效的截止时间,一个线程会检查失效队列来找出失效的桶。这个线程会一直睡到截止时间。当这个线程苏醒,它会从失效队列中拉出新的一批会话, 并将它们失效。当然也可能拉出来是空的。

(expirationTime/expirationInterval + 1)*expirationInterval

为了提供一个例子,我们假设expirationInterval是2,并且会话的expirationTime发生在时间点10。我们将这个会话分配到桶12中((10/2+1)*2的结果)。注意,当我们触摸会话时,expirationTime会保持增长,所以由此我们可以将会话移到更晚失效的桶里。

使用桶模式的一个重要原因是为了减少会话失效检查的开销。Zookeeper部署可能有成千上万的客户端,以及由此而来的成千上万的Session。使用细粒度(Fine-grained)的会话失效检查方式不适合这种场景。与这个评论相关,注意如果expirationInterval很短,那么Zookeeper最终是使其实是用细粒度的方式进行会话失效检查。expirationInterval目前是一个滴答,而滴答通常是秒级的。

 

转载请附上原博客地址:http://blog.csdn.net/jeff_fangji/article/details/44122541

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Zookeeper是一个开源的分布式协调服务,它提供了一个简单的接口,用于管理和协调分布式系统中的各种资源。它主要用于解决分布式系统中的一致性问题,例如分布式锁、配置管理、命名服务等。 要使用Zookeeper,首先需要下载并安装Zookeeper。根据引用中的内容,可以将下载的Zookeeper文件夹重命名为zookeeper,并修改环境变量,以便在命令行中可以直接访问Zookeeper命令。 一旦安装完成,可以使用Java编写代码来连接和使用Zookeeper。在Java中,org.apache.zookeeper.ZooKeeperZookeeper客户端的入口主类,负责建立与Zookeeper服务器会话。通过创建ZooKeeper对象,可以连接到Zookeeper服务器并执行各种操作,例如创建节点、读取节点数据、监听节点变化等。 以下是一个简单的Java代码示例,演示了如何使用Zookeeper创建一个节点并读取其数据: ```java import org.apache.zookeeper.*; public class ZookeeperExample { private static final String ZOOKEEPER_ADDRESS = "localhost:2181"; private static final int SESSION_TIMEOUT = 5000; public static void main(String[] args) throws Exception { ZooKeeper zooKeeper = new ZooKeeper(ZOOKEEPER_ADDRESS, SESSION_TIMEOUT, null); String path = "/example"; String data = "Hello, Zookeeper!"; // 创建节点 zooKeeper.create(path, data.getBytes(), ZooDefs.Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT); // 读取节点数据 byte[] nodeData = zooKeeper.getData(path, false, null); String nodeDataString = new String(nodeData); System.out.println("Node data: " + nodeDataString); zooKeeper.close(); } } ``` 这个示例代码首先创建了一个ZooKeeper对象,连接到本地的Zookeeper服务器。然后,它创建了一个名为/example的持久节点,并将数据"Hello, Zookeeper!"写入该节点。最后,它读取了该节点的数据并打印出来。 请注意,这只是一个简单的示例,Zookeeper还有很多其他功能和用法。如果你对Zookeeper的更多细节感兴趣,可以查阅官方文档或其他相关资源。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值