设为首页 收藏本站
查看: 687|回复: 0

[经验分享] 一种zabbix server扩容改造方案

[复制链接]

尚未签到

发表于 2018-10-19 12:01:16 | 显示全部楼层 |阅读模式
  本文原创作者鲍光亚,京东商城基础平台部软件开发工程师,经作者同意发表于本人博客,如需转载需经本人同意。
  一、引言
  随着监控量的迅速增长,zabbix管理员有一天会发现硬盘iops达到了数万,接近硬盘io的极限,无力支持处理更多监控数据。本文提出一种横向扩展方案,以尽量小的改动,增加zabbix系统的数据io能力。
  考虑到zabbix的数据库io主要在于history表和trends表,这一方案是在不增加zabbix server数量的情况下,将history表和trends表的io分散到其他主机上。此方案的优点是保持单个zabbix server,不需要考虑多server之间的协同一致。这一数据库分离模式还可以兼容原有的集中模式。但是,由于io分散到多个主机上,当需要读写数据时,不得不访问多个数据库实例。同时,代码中涉及数据库读写的部分,包括zabbix server和web api,都需要重写,好在大部分可以参考已有的代码。
  本方案设计基于zabbix 3.0.10版本。本文只论及对zabbix server的改造方案,对web api的修改方案将另文讨论,本文不涉及。
  二、zabbix数据读写机制
  由于configuration数据的io远小于history和trends数据io,本方案没有涉及对configuration数据的改动。
  cache和vc_cache是zabbix源码中的两个变量名称,前者用于存储来自agent/proxy的原始数据,后者存储的则是从数据库中加载的数据(当数据已过期时,新数据则会直接从前者复制到后者之中),用于进行trigger计算等。
  1.history和trends数据的写入
  poller和trapper两类进程(包括pinger)负责从agent和proxy接收history数据,然后flush到cache中,同时更新cache中的trends数据。对cache的更新主要通过函数 process_hist_data实现。
  dbsyncer进程则负责将cache中的数据写入到数据库中的history表和trends表中。由于dbsyncer存在多个进程,进程之间通过锁进行协调,避免冲突。cache数据入库主要通过DCsync_history和DCsync_trends两个函数实现。

  • history和trends数据的读取  vc_cache在程序启动时分配空间,但是并不加载数据。此时poller和trapper进程尚未开始接收数据,因此也不会往vc_cache中写数据。
      程序启动以后,当需要数据进行计算时,会尝试从vc_cache中获取values,如果获取不到则会从history表中加载数据到vc_cache中。源文件中有三个函数用于从数据库读取value并加载到vc_cache中,这三个函数名为vc_db_read_values_by_time、vc_db_read_values_by_count、 vc_db_read_values_by_time_and_count。
  • history和trends数据的删除  housekeeper进程负责将过期的数据从history和trends表中删除。housekeeper还负责删除过期的events、alerts、sessions等。
  • 数据库连接  zabbix各进程对数据库的访问通过单个connection来建立连接。各个查询的执行函数都没有设置连接参数,而是通过全局性的conn变量维持连接。如果要实现对多数据库的访问,则只能增加连接变量数,或者动态修改conn。
  • watchdog  watchdog进程负责监视数据库状态,当发现连接失败时发送报警信息。
  三、具体方案及实现
  在数据库中,history表依照数据类型不同分为history、history_uint、history_str、history_text、history_log五个表,trends表则分为trends和trends_uint两个表。遵循着分散io的思路,可以考虑两种方案,第一种方案是按照类别将history和trends分散到两个独立的数据库中,另外一种是按照类别以及数据类型的不同,将每一个表都独立地存储到单个数据库中。下文主要按照第一种方案进行论述。

  • 改写配置文件  在配置文件中增加所需的数据库连接参数,以及用于集中和分离模式切换的开关。配置文件的解析在程序启动时进行,因此还需要修改启动程序,增加存储数据库连接参数的数组元素以及开关变量。
  • 修改数据库connect函数  在保留原有connect函数的基础上,新增一个带有入参的connect,以根据需要建立不同的连接。同时增加全局变量,用于保持多个连接。
  • 修改数据库查询函数  在保持原有查询函数的基础上,增加带有连接参数的查询函数,以动态变换查询连接。zabbix中有多个查询函数,用于不同类型的查询,所有这些都需要修改。
  • 对函数的调用  上文提及的涉及history和trends读写的函数中,对数据库的访问部分都需要修改,增加对模式开关的条件判断,以调用不同的函数。模式开关的逻辑应保证通过重启服务可以使数据存储模式在集中和分离模式之间切换。
      如果采用按监控数据类型分库的方案,则还需要对sql文本构造过程进行修改。
  • 修改watchdog逻辑  将原来的单个实例状态监视,改为多实例同时监视,有任何实例连接失败时均报警。
  四、数据一致性问题
  分离模式存在的风险之一是数据一致性问题。在集中模式时,zabbix通过互斥锁来协调对缓存的访问,保证缓存数据的一致性。写数据库时则通过transaction保证一致性。因为缓存锁机制的存在,数据库的分离与否并不会影响缓存的一致性,问题只能存在于数据库内部。
  如果采用按类别分离的方案,即history和trends数据分别存储在两个数据库中,则需要考虑history、trends和其他表之间的一致性。如果采用按类别+数据类型分离的方案,则同时要考虑history各个表之间的数据一致性以及trends表之间的一致性。
  通过分析源码中的transaction逻辑,history/trends表的更新操作不需要与其他表保持一致性(在数据库级别),在程序允许的情况下,双方可以独立写数据库。
  五、进一步的方案
  遵循数据库分离的思路,更激进的方案是将history和trends数据中的每一个表都进行拆分,以itemid或者clock为key按照一定的哈希算法,将数据分散存储到更多的数据库中。


运维网声明 1、欢迎大家加入本站运维交流群:群②:261659950 群⑤:202807635 群⑦870801961 群⑧679858003
2、本站所有主题由该帖子作者发表,该帖子作者与运维网享有帖子相关版权
3、所有作品的著作权均归原作者享有,请您和我们一样尊重他人的著作权等合法权益。如果您对作品感到满意,请购买正版
4、禁止制作、复制、发布和传播具有反动、淫秽、色情、暴力、凶杀等内容的信息,一经发现立即删除。若您因此触犯法律,一切后果自负,我们对此不承担任何责任
5、所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其内容的准确性、可靠性、正当性、安全性、合法性等负责,亦不承担任何法律责任
6、所有作品仅供您个人学习、研究或欣赏,不得用于商业或者其他用途,否则,一切后果均由您自己承担,我们对此不承担任何法律责任
7、如涉及侵犯版权等问题,请您及时通知我们,我们将立即采取措施予以解决
8、联系人Email:admin@iyunv.com 网址:www.yunweiku.com

所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其承担任何法律责任,如涉及侵犯版权等问题,请您及时通知我们,我们将立即处理,联系人Email:kefu@iyunv.com,QQ:1061981298 本贴地址:https://www.yunweiku.com/thread-623626-1-1.html 上篇帖子: sql优化的几种方法 下篇帖子: LinQ to Sql中的增删改查2种方法
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

扫码加入运维网微信交流群X

扫码加入运维网微信交流群

扫描二维码加入运维网微信交流群,最新一手资源尽在官方微信交流群!快快加入我们吧...

扫描微信二维码查看详情

客服E-mail:kefu@iyunv.com 客服QQ:1061981298


QQ群⑦:运维网交流群⑦ QQ群⑧:运维网交流群⑧ k8s群:运维网kubernetes交流群


提醒:禁止发布任何违反国家法律、法规的言论与图片等内容;本站内容均来自个人观点与网络等信息,非本站认同之观点.


本站大部分资源是网友从网上搜集分享而来,其版权均归原作者及其网站所有,我们尊重他人的合法权益,如有内容侵犯您的合法权益,请及时与我们联系进行核实删除!



合作伙伴: 青云cloud

快速回复 返回顶部 返回列表