作者:shunz,出处:http://shunz.net/2008/06/mysql_discuz_.html
最近,帮一个朋友优化一个拥有20万主题,100万帖子,3万多会员,平均在线人数2000人的Discuz!论坛,采用Linux2.6+Apache2+mod_php5+MySQL5,服务器配置为双至强+4G内存,优化前,系统平均负载(load average)基本维持在10以上,MySQL的CPU占用率基本在90%以上,优化后,系统平均负载降到0.5以下,MySQL的CPU占用率很少有超过10%的时候。优化前YSlow得分只有35分,优化后YSlow得分86分。现将优化的过程和经验做一个记录:
首先,对Apache进行优化,编辑httpd.conf,设置HostnameLookups、KeepAlive、MaxKeepAliveRequests以及KeepAliveTimeout四个参数,调整MaxSpareServers、ServerLimit、MaxClients以及MaxRequestsPerChild参数,还可以考虑弃用prefork而采用worker MPM。设置mod_deflate及mod_expires模块,不过注意Discuz!不能对PHP文件开启Expires,否则会出现问题。另外还可以考虑开启mod_cache和mod_mem_cache模块。另外利用cronolog按天对日志进行轮循截断,如果日志特别大,也可以按小时截断。另外再加上Awstats对日志进行分析,并用gzip对日志进行压缩,自动删除1个月前的日志。
其次,对PHP进行优化,编辑php.ini,调整output_buffering、zlib.output_compression及max_execution_time、max_input_time、memory_limit等参数,并安装Xcache和Zend Optimizer。
然后对MySQL进行优化。首先重新静态编译MySQL,使其只支持MyISAM和Memory两种引擎,并按Discuz!编码选择只支持UTF-8或者GBK字符集。编辑my.cnf,设置skip-locking、skip-external-locking、skip-networking和skip-name-resolve,根据内存和数据库状态具体调整key_buffer_size、query_cache_size、query_cache_limit、max_allowed_packet、table_cache、thread_cache_size、sort_buffer_size、read_buffer_size、read_rnd_buffer_size、join_buffer_size、tmp_table_size、max_tmp_tables、back_log、max_connections、wait_timeout的参数。
对数据库进行优化,将threads和posts表中部分未索引的字段增加索引,并将supersite数据库表从bbs数据库独立出去。修改discuz!配置文件,设置开启pconnect。
对Discuz!设置进行优化。进入Discuz!系统设置,修改页面缓存设置中的缓存有效期和缓存系数,修改服务器优化中的禁止浏览器缓冲和页面Gzip压缩,修改防盗链设置中下载附件来路检查,用JSMin自动对js文件进行缩减(Discuz! 6.1的common.js原文件29.3k,经JSMin缩减后为24.1k,再经deflate后为7.3k),修改attachments.php文件,将:
//dheader('Cache-control: max-age=31536000');
//dheader('Expires: '.gmdate('D, d M Y H:i:s', $timestamp + 31536000).' GMT');
前的注释去掉。修改模板目录下adv.htm,去掉与Insenz有关的代码。
通过查看MySQL的status,可以看出优化后,长时间运行的Key_read_ratio基本保持在0.05%以下,Threads_cache_hitrate保持在99.9%以上。个人感觉,Discuz!将Session保存在数据库中,极大地降低了Query Cache的命中率,如果需要进一步优化,可以考虑修改Discuz!源码,将Session保存到Memcache中。
优化之后用Siege做并发压力测试,在200并发下,基本没有任何错误。如果将来人数更多,可以考虑将平台迁移到Ngix+PHP FastCGI上。
下面是用Siege在300并发下的测试结果:
#siege -c 300 -b -r 35 -f bbs.url
** SIEGE 2.67
** Preparing 300 concurrent users for battle.
The server is now under siege.. done.
Transactions: 10500 hits
Availability: 100.00 %
Elapsed time: 52.68 secs
Data transferred: 65.67 MB
Response time: 1.27 secs
Transaction rate: 199.32 trans/sec
Throughput: 1.25 MB/sec
Concurrency: 253.07
Successful transactions: 10500
Failed transactions: 0
Longest transaction: 24.88
Shortest transaction: 0.00
500并发下的测试结果:
#siege -c 500 -b -r 20 -f bbs.url
** SIEGE 2.67
** Preparing 300 concurrent users for battle.
The server is now under siege.. done.
Transactions: 9979 hits
Availability: 99.79 %
Elapsed time: 86.52 secs
Data transferred: 82.66 MB
Response time: 3.30 secs
Transaction rate: 115.34 trans/sec
Throughput: 0.96 MB/sec
Concurrency: 381.07
Successful transactions: 9979
Failed transactions: 21
Longest transaction: 34.80
Shortest transaction: 0.00
昨天,将服务器迁移到了Nginx+php-fpm,以下是迁移后测试,相差真的很明显,回头再写Nginx+php-fpm的经验:
[root@bbs ~]# siege -c 300 -r 50 -f bbs.url
** SIEGE 2.67
** Preparing 300 concurrent users for battle.
The server is now under siege.. done.
Transactions: 15000 hits
Availability: 100.00 %
Elapsed time: 64.12 secs
Data transferred: 67.79 MB
Response time: 0.55 secs
Transaction rate: 233.94 trans/sec
Throughput: 1.06 MB/sec
Concurrency: 128.95
Successful transactions: 14976
Failed transactions: 0
Longest transaction: 3.96
Shortest transaction: 0.00[root@bbs ~]# siege -c 500 -r 50 -f bbs.url
** SIEGE 2.67
** Preparing 500 concurrent users for battle.
The server is now under siege.. done.
Transactions: 25000 hits
Availability: 100.00 %
Elapsed time: 65.52 secs
Data transferred: 83.65 MB
Response time: 0.57 secs
Transaction rate: 381.56 trans/sec
Throughput: 1.28 MB/sec
Concurrency: 216.02
Successful transactions: 21707
Failed transactions: 0
Longest transaction: 5.83
Shortest transaction: 0.00
=======
BTW:做个小广告,有偿提供各种Apache、MySQL或Discuz!优化。
30 条评论了已经
Trackbacks/Pingbacks.
发表评论
字体为 粗体 是必填项目,邮箱地址 永远不会 公布。
允许部分 HTML 代码:<a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>
URIs must be fully qualified (eg: http://shunz.net/) and all tags must be properly closed.
超出部分系统将会自动分段及换行。
请保证评论内容是与日志或 Blog 内容相关的,灌水、攻击性或不恰当的评论 may 会被编辑或删除。













前面不是说 2000 人在线么?
后面的 200个 并发是什么 ?
re fenng
前面说的2000人在线是指Discuz!论坛本身的一个指标,默认是20分钟内的在线人数
文中说了“迁移到Ngix PHP FastCGI”,那现在使用的是什么系统呢?尽量详细些
to IndexZ
Linux2.6 Apache2 mod_php5 MySQL5
这个收藏一下,以后会有用到的
对了,博主是搞什么行业的呀?很厉害~~~~~~~~~
高手,前后差别这么大!
优化这么多?
高,实在是高!
厉害!
高!厉害!!
不知道discuz官方是如何优化的
看了以后,还是很模糊,唉,再深入些嘛!虽然有偿对外做,但既然此日志一出,就一步到位嘛!
呵!!
呵呵,老哥帮我做的,速度超快!
怎末联系你啊~~真想找你帮忙呢
我的邮箱是shunza#gmail.com,将#改为@
前几天听说过MySQL的设计很重要,楼主真乃高人也~强帖留名!
提到的很多优化步骤并不会有效。比如编译成静态文件,这个只有在频繁重启的情况下才有可能降低系统负载;裁剪mysql支持的数据库类型,仅仅消除一个线性匹配查找的可能性,这个匹配查找既不在关键路径上,本身开销也很低,也不在循环中;
个人感觉有效果的优化在三个地方
1. 压缩;一般放托管机房的服务器都有带宽限制,通常在平均带宽占到可用带宽的 80% 时,突发访问就会受到影响;更快的把页面发送到客户端,可以减小并发执行进程数量,降低进程切换的开销;
2. apache 进程参数调整;
3. 数据库优化:按照 mysql 占 CPU 90% 以上的现象, io wait 是很低的。这提示磁盘访问并不是一个问题。一般这种现象和 mysql 线性全扫描处理在内存中缓冲的数据有关系,对涉及到的数据库添加索引多数能有效解决;在个别情况下,可能需要根据数据的实际情况,手工进行 mysql 查询的优化,调整 where 子句中多个条件的先后顺序,以达到线性扫描处理数据集最少的目标
这三个调整中,根据原先的实际负载来看,添加索引应该是最有效的处理。
当然,这里没有考虑盗链问题,如果存在很严重的盗链情况的话,消除盗链是最有效的优化,因为很多系统的每次图片访问实际上要带来多次mysql查询;用apache的话,用条件匹配和环境变量相配合,可以把盗链全部转向到不访问数据库的页面。
顶@lark
LZ只说了设置哪些参数, 却没有说从多少改成多少, 太笼统了!
Apache 几个参数应该默认就关闭的吧, 那么你把它开启了?
还有开启mem_cache有什么用?
高手
非常感谢
学习了哦
我想优化个服务器,如果可以请联系我的email: yrpark.com@gmail.com 多谢了
2008/12/22
北京新鑫互联 提供:美国-香港-台湾-北京-上海-浙江-两岸八地-空间服务器租用 QQ:603335822
电话:010-51668748 http://www.idcnew.cn