于敦德 2006-6-27
FeedBurner(以下簡(jiǎn)稱FB,呵呵)我想應(yīng)該是大家耳熟能詳?shù)囊粋€(gè)名字,在國(guó)內(nèi)我們有一個(gè)同樣的服務(wù)商,叫做FeedSky。在2004年7月份,F(xiàn)B的流量是300kbps,托管是5600個(gè)源,到2005年4月份,流量已經(jīng)增長(zhǎng)到5Mbps,托管了47700個(gè)源;到2005年9月份流量增長(zhǎng)到20M,托管了109200個(gè)源,而到2006年4月份,流量已經(jīng)到了115Mbps,270000個(gè)源,每天點(diǎn)擊量一億次。
FB的服務(wù)使用Java實(shí)現(xiàn),使用了Mysql數(shù)據(jù)庫(kù)。我們下面來看一下FB在發(fā)展的過程中碰到的問題,以及解決的方案。
在2004年8月份,F(xiàn)B的硬件設(shè)備包括3臺(tái)Web服務(wù)器,3臺(tái)應(yīng)用服務(wù)器和兩臺(tái)數(shù)據(jù)庫(kù)服務(wù)器,使用DNS輪循分布服務(wù)負(fù)載,將前端請(qǐng)求分布到三臺(tái)Web服務(wù)器上。說實(shí)話,如果不考慮穩(wěn)定性,給5600個(gè)源提供服務(wù)應(yīng)該用不了這么多服務(wù)器?,F(xiàn)在的問題是即使用了這么多服務(wù)器他們還是無法避免單點(diǎn)問題,單點(diǎn)問題將至少影響到1/3的用戶。FB采用了監(jiān)控的辦法來解決,當(dāng)監(jiān)控到有問題出現(xiàn)時(shí)及時(shí)重啟來避免更多用戶受到影響。FB采用了Cacti(http://www.cacti.net)和Nagios(http://www.nagios.org)來做監(jiān)控。
FB碰到的第二個(gè)問題是訪問統(tǒng)計(jì)和管理??梢韵胂?,每當(dāng)我們?cè)赗SS閱讀器里點(diǎn)擊FB發(fā)布的內(nèi)容,都需要做實(shí)時(shí)的統(tǒng)計(jì),這個(gè)工作量是多么的巨大。大量寫操作將導(dǎo)致系統(tǒng)的效率急劇下降,如果是Myisam表的話還會(huì)導(dǎo)致表的死鎖。FB一方面采用異步寫入機(jī)制,通過創(chuàng)建執(zhí)行池來緩沖寫操作;只對(duì)本日的數(shù)據(jù)進(jìn)行實(shí)時(shí)統(tǒng)計(jì),而以前的數(shù)據(jù)以統(tǒng)計(jì)結(jié)果形式存儲(chǔ),進(jìn)而避免每次查看訪問統(tǒng)計(jì)時(shí)的重復(fù)計(jì)算。所以每一天第一次訪問統(tǒng)計(jì)信息時(shí)速度可能會(huì)慢,這個(gè)時(shí)候應(yīng)該是FB在分析整理前一天的數(shù)據(jù),而接下來的訪問由于只針對(duì)當(dāng)日數(shù)據(jù)進(jìn)行分析,數(shù)據(jù)量小很多,當(dāng)然也會(huì)快很多。FB的Presentation是這樣寫,但我發(fā)現(xiàn)好像我的FB里并沒有今天實(shí)時(shí)的統(tǒng)計(jì),也許是我觀察的不夠仔細(xì)-_-!
現(xiàn)在第三個(gè)問題出現(xiàn)了,由于大多數(shù)的操作都集中在主數(shù)據(jù)庫(kù)上,數(shù)據(jù)庫(kù)服務(wù)器的讀寫出現(xiàn)了沖突,前面提到過Myiasm類型的數(shù)據(jù)庫(kù)在寫入的時(shí)候會(huì)鎖表,這樣就導(dǎo)致了讀寫的沖突。在開始的時(shí)候由于讀寫操作比較少這個(gè)問題可能并不明顯,但現(xiàn)在已經(jīng)到了不能忽視的程度。解決方案是平衡讀寫的負(fù)載,以及擴(kuò)展HibernateDaoSupport,區(qū)分只讀與讀寫操作,以實(shí)現(xiàn)針對(duì)讀寫操作的不同處理。
現(xiàn)在是第四個(gè)問題:數(shù)據(jù)庫(kù)全面負(fù)載過高。由于使用數(shù)據(jù)庫(kù)做為緩存,同時(shí)數(shù)據(jù)庫(kù)被所有的應(yīng)用服務(wù)器共享,速度越來越慢,而這時(shí)數(shù)據(jù)庫(kù)大小也到了Myisam的上限-4GB,F(xiàn)B的同學(xué)們自己都覺得自己有點(diǎn)懶?。解決方案是使用內(nèi)存做緩存,而非數(shù)據(jù)庫(kù),他們同樣使用了我們前面推薦的memcached,同時(shí)他們還使用了Ehcache(http://ehcache.sourceforge.net/),一款基于Java的分布式緩存工具。
第五個(gè)問題:流行rss源帶來大量重復(fù)請(qǐng)求,導(dǎo)致系統(tǒng)待處理請(qǐng)求的堆積。同時(shí)我們注意到在RSS源小圖標(biāo)有時(shí)候會(huì)顯示有多少用戶訂閱了這一RSS源,這同樣需要服務(wù)器去處理,而目前所有的訂閱數(shù)都在同一時(shí)間進(jìn)行計(jì)算,導(dǎo)致對(duì)系統(tǒng)資源的大量占用。解決方案,把計(jì)算時(shí)間錯(cuò)開,同時(shí)在晚間處理堆積下來的請(qǐng)求,但這仍然不夠。
問題六:狀態(tài)統(tǒng)計(jì)寫入數(shù)據(jù)庫(kù)又一次出問題了。越來越多的輔助數(shù)據(jù)(包括廣告統(tǒng)計(jì),文章點(diǎn)擊統(tǒng)計(jì),訂閱統(tǒng)計(jì))需要寫入數(shù)據(jù)庫(kù),導(dǎo)致太多的寫操作。解決方案:每天晚上處理完堆積下來的請(qǐng)求后對(duì)子表進(jìn)行截?cái)嗖僮鳎?/p>
– FLUSH TABLES; TRUNCATE TABLE ad_stats0;
這樣的操作對(duì)Master數(shù)據(jù)庫(kù)是成功的,但對(duì)Slave會(huì)失敗,正確的截?cái)嘧颖矸椒ㄊ牵?/p>
– ALTER TABLE ad_stats TYPE=MERGE UNION=(ad_stats1,ad_stats2);
– TRUNCATE TABLE ad_stats0;
– ALTER TABLE ad_stats TYPE=MERGE UNION=(ad_stats0,ad_stats1,ad_stats2);
解決方案的另外一部分就是我們最常用的水平分割數(shù)據(jù)庫(kù)。把最常用的表分出去,單獨(dú)做集群,例如廣告啊,訂閱計(jì)算啊,
第七個(gè)問題,問題還真多,主數(shù)據(jù)庫(kù)服務(wù)器的單點(diǎn)問題。雖然采用了Master-Slave模式,但主數(shù)據(jù)庫(kù)Master和Slave都只有一臺(tái),當(dāng)Master出問題的時(shí)候需要太長(zhǎng)的時(shí)間進(jìn)行Myisam的修復(fù),而Slave又無法很快的切換成為Master。FB試了好多辦法,最終的解決方案好像也不是非常完美。從他們的實(shí)驗(yàn)過程來看,并沒有試驗(yàn)Master-Master的結(jié)構(gòu),我想Live Journal的Master-Master方案對(duì)他們來說應(yīng)該有用,當(dāng)然要實(shí)現(xiàn)Master-Master需要改應(yīng)用,還有有些麻煩的。
第八個(gè)問題,停電!芝加哥地區(qū)的供電狀況看來不是很好,不過不管好不好,做好備份是最重要的,大家各顯神通吧。
這個(gè)Presentation好像比較偏重?cái)?shù)據(jù)庫(kù),當(dāng)然了,誰(shuí)讓這是在Mysql Con上的發(fā)言,不過總給人一種不過癮的感覺。另外一個(gè)感覺,F(xiàn)B的NO們一直在救火,沒有做系統(tǒng)的分析和設(shè)計(jì)。
最后FB的運(yùn)維總監(jiān)Joe Kottke給了四點(diǎn)建議:
1、 監(jiān)控網(wǎng)站數(shù)據(jù)庫(kù)負(fù)載。
2、 “explain”所有的SQL語(yǔ)句。
3、 緩存所有能緩存的東西。
4、 歸檔好代碼。
最后,F(xiàn)B用到的軟件都不是最新的,夠用就好,包括:Tomcat5.0,Mysql 4.1,Hibernate 2.1,Spring,DBCP。
聯(lián)系客服