使用缓存数据库可以有效的提升系统性能,但是基于由于缓存数据库的自身特性,相比起实例化数据库,在性能抖动,丢失方面,尤其是缓存失效的严重问题层面,处理不足,及其容易带来,对底层数据库的瞬间并发访问,造成数据库的宕机。
所以,最好的方案,可以考虑,略微降低性能,在缓存的集群上面,仿照实例化数据库实现一些代理方案,这样可以实现类似zoonkeeper概念的一直死活控制。
现在缓存数据库,比较常见的是:
1:支持并发的高效率,无磁盘负责的memcached,自身不支持集群方案,必须走代理;
2:读写相对均衡的单线程的redis,自身支持完好的集群方案,并有可选的实例化方案,实例化与对外业务是从属于不同的线程。
3:不支持并发的大数据缓存,文档型数据库,mongodb,其内部设计,采用了,异常压制方案,出了问题,比较难以调式,自身有很好的集群能力。
实现缓存的集群方案是很好的,这样可以很好的降低了底层数据库的扩张与成本,且性能远大于底层数据库实现的分布式或者集群。唯一的关键点,是做好底层数据库与缓存数据库之间的保护屏障,于是,站在巨人的肩膀上面,可以选择如下方案:
Twitter的Redis/Memcached代理服务:Twemproxy
Twemproxy是一个使用C语言编写的Redis 和 Memcache 代理服务器,通过引入一个代理层,将应用程序后端的多台Redis或Memcached实例进行统一管理,使应用程序只需要在Twemproxy上进行操作,而不用关心后面具体有多少个真实的Redis或Memcached实例。当某个节点宕掉时,Twemproxy可以自动将它从集群中剔除,而当它恢复服务时,Twemproxy也会自动连接。由于是代理,所以Twemproxy会有微小的性能损失。
无论从底层实现或者其给出的功能,都是绝佳的可选方案。问题是限制在了reids或者memcached的,应该可以满足绝大部分的场景。
Facebook的Memcached协议路由器:McRouter
McRouter是一个使用C++(主要语言,使用了大量的C++ 11特性)开发的基于Memcached协议的路由器,它是Facebook和Instagram缓存架构的核心组件,在高峰时期可以处理近50亿请求。McRouter中客户端可以共享连接池,这样能减少连接的数量。McRouter可以根据key前缀把客户端分配到不同的Memcached池中,允许以主机、池或者集群为单位设置任何请求的速率的阀值,同时也支持限制请求的速度以减缓请求的发送速度,以保障服务质量。
钟爱于并发的可选方案。
Youtube的Mysql中间件:Vitess
缓存层存在的初衷是减少应用与数据库的交互,以提高响应时间,与其将缓存与数据库分离,不如直接将缓存嵌入数据库中。Vitess是Youtube的开源分布式MySQL工具集,主要使用Go语言编写,已经用于Youtube生产环境。Vitess支持行级缓存,并与Memcached进行了集成,可以有效提高带主键查询的速率,查询只有在Memcached中查询不到时才会进入数据库查询,而当数据被修改或者数据库表结构发生变化时,缓存数据会被删除。
近来对mysql的nosql化呼声较高,可惜看这个数据库现在半死不活的架势,不知道后面会被甲骨文怎么捯饬。
mongodb的目前没有,应该是其自身的方案难以超越吧。相对与memcached,mongo即没有线程的概念,更谈不上并发,v8引擎,解释着C代码,但是,在妥善的控制客户端并发访问句柄的前提下,其基于事件队列的访问速度,毫不逊色,只是,由于其超时机制,不知道是使用难以得当,还是实现的有问题,总是会在密集访问下面,导致很多客户端线程把服务端卡住。基于大数据概念的文档松散型数据结构,往往令人欲罢不能。
mongodb如果跟memcached的合二为一,那真是当真的完美了。