文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

php zookeeper常见问题解决方案

2024-02-27 19:23

关注

在《PHP Zookeeper你需要知道的细节》(以下称为php_zk)一章中我们提出了问题,并且通过分析PHP-ZooKeeper源码找出了问题的原因,但是并没有给出解决方法。本章我们就来看一看解决的办法。

解决的办法分为两种:

一是修改PHP-ZooKeeper源码,重新编译安装
二是修改php代码

下面我们先来看第一种方式。

修改PHP-ZooKeeper源码

在php_zk一章中我们看到,其实在znode节点值为NULL的时候,使用php-zookeeper的get()方法能监听znode节点,但是并不能成功调用回调函数。原因就在于get()这个函数底层实现是当znode值为null的时候调用的函数如下


status = zoo_exists(i_obj->zk, path, 1, &stat);

但是我们可以看一下当znode有值的时候,它会调用到下面的函数


status = zoo_wget(i_obj->zk, path, (fci.size != 0) ? php_zk_watcher_marshal : NULL,
	          cb_data, buffer, &length, &stat);

所以我们分析php_zk_watcher_marshal是解析回调函数的,而在zoo_exists()中第三个参数为1,因此要想解决问题,必须要在zoo_exists()这个函数上找突破。继续进入zoo_exists()函数底层的定义发现其实该函数的实现也很简单


int zoo_exists(zhandle_t *zh, const char *path, int watch, struct Stat *stat)
{              
    return zoo_wexists(zh,path,watch?zh->watcher:0,zh->context,stat);
}

在它的底层又调用了zoo_wexists()函数。所以说我们完全可以在get()函数定义中将zoo_exists()函数改成zoo_wexists()。示例如下


if (max_size <= 0) {
    
    status =zoo_wexists(i_obj->zk,path,(fci.size!=0)?php_zk_watcher_marshal:NULL,cb_data,&stat);
    if (status != ZOK) {
	php_cb_data_destroy(&cb_data);
	php_error_docref(NULL TSRMLS_CC, E_WARNING, "error: %s", zerror(status));
	return;

    }
    length = stat.dataLength;
} else {
    length = max_size;
}

这样一来,回调函数就会被执行了。

保存以后,重新编译安装就可以了


# ./configure --with-libzookeeper-dir=/opt/zk_c/ --with-php-config=/usr/local/php5/bin/php-config
# make
# make test
# make install

因为之前已经在php.ini中添加了zookeeper的配置,所以这里不用在进行任何配置。

完成以后再次按照php_zk文章中进行php代码的运行步骤就会发现能正常的进行新的leader的选举了。

修改php代码

虽然能修改PHP-ZooKeeper的源码来解决问题,但是没有十足的把握还是不要修改源码,因为这可能会影响到其它函数的使用。所以这里我们可以在php代码层来进行修改。

我们在php_zk一章中看到,在进行/cluster子节点的创建中使用的是下面的代码


$this->znode = $this->create(self::CONTAINER . '/w-', null, $this->acl, Zookeeper::EPHEMERAL | Zookeeper::SEQUENCE);

在$this->create()函数中,第三个参数是znode的值,这里我们默认为null。如果我们给他一个不为null的默认值的话,这个问题就迎刃而解了。如下示例


$this->znode = $this->create(self::CONTAINER . '/w-', '1', $this->acl, Zookeeper::EPHEMERAL | Zookeeper::SEQUENCE);

当然我们这里为了测试,只是简单的给了一个1。在实际场景中在创建节点的时候会根据实际应用来给出默认值,这里就暂且使用1来测试。

修改以后再次按照之前的步骤运行——不用在zookeeper客户端单独进行值的设置——就会发现也是能重新选出leader的。

以上两种方式我都是经过代码测试的,实践证明其可行。但是在实际中应该怎样去使用PHP-ZooKeeper都要根据场景去定。我这里只是抛砖引玉,指出在学习中的一些问题,希望能帮到各位。

阅读原文内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     813人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     354人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     318人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     435人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     224人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-后端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯