[探讨与整理]关于数据库负载均衡的手法搜集贴
额,昨天发表了一篇文章http://www.cnblogs.com/koumi/archive/2010/10/12/1849077.html,感谢老赵、亚力山大等等同志们的关注与指点。第一次发表文章,也存在很多条理、深入研究上的问题,导致此文章感觉就是一个误区。再接再励,请大家多多指点!
====环境====
OS:windows系统平台。
数据库:MSSQL20XX系列。
前端:ASPNET + IIS。
====目标====
应用业务之数据库负载均衡
我先简要说说,基与dotNET的系统随着用户规模的增长,一般情况下有3个方面的瓶颈。
第一,很快你会遇到图片带宽的压力和图片服务器并发的压力。
第二,IIS并发连接的压力。
第三,数据库CPU使用率出现尖峰波动。峰值达到100%。(平均峰值大于45%就要准备负载方案了)
本着向高层次技术群发展的目标,针对以上情况大家可以各抒己见,共同探讨。
我先说说我的,大家可以参考:
针对第一点,图片方面的压力,这个解决最简单,因为图片是静态的,所以可以采用高性能服务器,当遇到棘手的时候,瞬间可以使用linux服务器顶替,配置上nginx,因为IIS的每秒并发极限大概是2000-4000(随服务器性能而定),而基于linux架构的nginx可以轻松达到60000左右(windows上的nginx目前不推荐使用,并发在4500左右,略微高于IIS,而且目前的版本0.8也还没有使用windows下5大SOCKET架构模型之首的IOCP,尚开发中,所以目前不推荐windows的nginx),且在高速负载的情况下,每个进程内存占用经过实测大概在40MB左右,这个也得力于高效的Ext系统和epoll监听方式。命令行linux安装不熟悉可以使用图形化安装,没什么影响,nginx可以在这里下载 http://www.nginx.org/ 为前苏联哈萨克斯坦igor编写的高性能反向代理服务器,支持http,smtp等协议的负载。好,将来如果单台都不够用了,就在nginx后端启用多台服务器,每个服务器放分散开的不同的图片。然后nginx上配置下conf文件,把不同的地址前缀(比如1.xxx.com和2.xxx.com 也可以是 xxx.com/img1/ 和 xxx.com/img2/ 等,配置是基于正则表达式的,所以很灵活)导向到不同的后端服务器去,实现分流。还有一种方式就是使用squid或者varnish这类缓存服务器来做图片服务器前面的那台缓存服务器,使得负载还可以更上一层楼。另外我插一句,nginx支持"免维护"升级,也就是说,当满负荷的时候,可以不关闭程序实现升级(思路是升级的时候启动备用进程,然后实现连接互换,然后终止老进程,实现平滑升级),这对于超大型网站来说是很重要的技术指标,原理可以看源代码.前端如果一台不够,就做LVS群集,linux群集就比windows群集维护成本低多了...几台就可以支撑相当大的用户群.还有cache+webServer整合性功能产品Cherokee,也不错...也是高负载产品.可以试试.
碰到第二点,遇到IIS并发连接压力,也就是说实打实的GET、POST太多,这个时候前端就挂接一台nginx,然后原来的IIS服务器放到nginx的下面,这里可以放多台IIS服务器,通过FTP实现镜像,然后前端通过nginx导向后端的镜像windows服务,实现IIS负载均衡。另外的方案就是使用windows的方案,最简单办法是通过windows自带的防火墙ICS编程来做端口映射,可以设置一个阀值,采用平均分配或者溢出分配来导向到不同的后端,专业点的就是通过windows自带的负载工具 “TCPIP负载均衡组件” 和 “路由和远程管理”也可以实现把请求分配到后端去的需求,还有种方式就是用ISA Server,恩,也可以直接群集服务了,这后一种在MSDN上推荐,但是成本太高,实践中我发现,他们成本差不多的,还是linux便宜,简单高效。这个时候可能我们的业务还是一台强悍的数据库服务器,CPU波动厉害,峰值超过80%这个时候就要看第三点了。
针对第三点,我们这样来做,根据现有的大型负载方案(新浪,163等),数据库必须实现读写分离,毕竟写入要影响读取的速度,因为有个并发的问题。所以读写要分开,“读”的数据库可以是一台,也可以是多台;同样,“写”操作的数据库也可以是一台,也可以是多台。然后这些服务器之间通过发布订阅实现联机同步。当然这个是mysql的方案,但是sql2000也是类似的方式。这里手法就有点多了。大概思路之一,也是我们程序员比较能接受的,就是通过sqlConnectionString里面的server属*,指向不同的读、写服务器,实现负载,当然负载算法最简单的就是做个监控封装到组件里。操作数据库的时候通过扫描下当前哪个服务器的使用率最低,就用那台服务器的IP作为SQL连接字串的server选项的属性。这里可以参考(DiscuzNT读写分离负载方案 http://blog.csdn.net/daizhj/archive/2010/06/21/5683813.aspx)当然,那个人写的比较抽象,我在上面的文字给他总结了一下,呵呵。另外,如果程序很难适应改动,那么还是可以做负载,方法就是用"路由和远程管理"指定NAT策略,对数据库访问端口实现负载映射,根据压力情况合理的将请求分发到后端"并联"的多台服务器上.
总结下,以上文字大家肯定可以看出,我是什么技术都在用的,可能有些人觉得太杂了,但是我是本着技术无关,适当的环节用适当的技术来实施的,这是我的原则。这样可以结合linux的简单高效低成本的后期运维和windows强大的开发资源。而且可能对于一个高速发展的企业,所用的技术并不是那么单一,可能后期会出现aspx服务,基于apache的php,等等杂七杂八的语言所构建的服务,没关系,只要统统放到反向代理服务器的后端去,就可以整合这些不同开发语言开发的服务,很方便。打个比方,您现在开发的asp.net页面很酷,作为门户了,但是以后的新员工来了,他们在另一个部门,由于竞争关系,他们的头头坚持使用php开发高速高压的统一认证服务,并封装为了webservice,那么就可以通过这种方式,合理整合这些资源。题外话,因此,新浪网站这些,都是各种开发语言鱼龙混杂的,只是通过反向代理整合了这些资源,前端统一体现为比如 index.shtml 这类后缀的网页,隐藏的后端实现而已。
by:成都→苏联程序
技术交流群欢迎您的加入!QQ群:29123371
posted on 2010-10-13 13:50 koumi's blogs 阅读(562) 评论(0) 编辑 收藏 举报