熊小最近在看有關一些大型網站如何運作的文章...發現有一些同通點。
1. Cache
-將資料存放於RAM...以減少db的查詢...比較常用的是memcached(user data cache, 支援跨主機)...APC(Opcode + user data cache, 不過只限同一主機)
2. NoSQL
-取代MySQL等Relational DB...(內容後補)
3. CDN
-Content Delivery Network...也就是用其他網絡供應商放置一些用戶存取的檔案...分散處理 (內容後補)
這次主要關於cache方面...雖然discuz有一些cache的功能...不過只限於file based...如要加快存取速度...以APC/memcached等memory cache效果更好。
論壇一直有用APC做Opcode caching...不過user data就沒試過。
本次目標是cache db query...以減少對db query的次數。
1. 安裝APC for pecl (最新的stable是3.1.6)
2. 查找論壇那些部份可以做caching
3. 利用apc_store / apc_fetch 來存取cache data
以下一條discuz常見的query
引用:
$query = $db->query("SELECT * FROM {$tablepre}threads t WHERE tid='$tid' AND displayorder>='0'");
$var = $db->fetch_array($query);
修改成APC版..用一個簡單function, 加到include/global.func.php
引用:
function query_cache($sql,$ttl=86400) {
if ($sql == '')
return null;
global $db;
$iKey = md5($sql);
if (!$cached_res = apc_fetch($iKey)) {
$query = $db->query($sql);
while($this_res = $db->fetch_array($query)) {
$cached_res[] = $this_res;
}
apc_store($iKey, $cached_res,$ttl);
return $cached_res;
}
本來的code改成:
引用:
$sql = "SELECT * FROM {$tablepre}threads t WHERE tid='$tid' AND displayorder>='0'"
$var = query_cache($sql);
結果 (as of 2011-03-17)
減少query數如下
index.php - 1
forumdisplay.php - 3
viewthread.php - 3
問題:
1. cache何時refresh
-當forumdisplay被cache後...新增主題/回覆不會顯示...因為它們不存在於cache內...這時必須刪除舊cache而重新query db以得到新cache...但因為apc_delete不支援prefix/suffix刪除...md5後的key變得難以單一刪除...現在的做法是當有新增文章/回覆時...刪除全部cache...方法不是很好...不過暫時沒想到更好的.
2. discuz內query最多的是common.inc.php內有關memeber...與viewthread.php有關post...不過2者太多..(每個member, 每個post都是一個獨立query)...cache效果不大。