摘要:為了避免垃圾郵件給電子郵件的使用帶來(lái)不便,通過(guò)對(duì)電子郵件地址在垃圾電子郵件黑名單進(jìn)行對(duì)比、過(guò)濾便成為一個(gè)行之有效的手段。項(xiàng)目從設(shè)計(jì)思想、具體實(shí)現(xiàn)以及性能提升等方面闡述了基于黑名單識(shí)別垃圾郵件地址技術(shù)。
關(guān)鍵詞:垃圾郵件;黑名單;數(shù)據(jù)庫(kù);java BerkeleyDB
中圖分類(lèi)號(hào):TP311文獻(xiàn)標(biāo)識(shí)碼:A 文章編號(hào):1009-3044(2009)36-10606-02
Design and Implementation of Anti-Spam module Based on the Blacklist of Email Address
LI Qiong
(Mianyang Normal University, Mianyang 621000, China)
Abstract: In order to avoid the inconvenience caused by Spam,filtering spam address in the blacklist has become an effective means. In this paper, the design, implementation, performance described blacklist technology to identify spam.
Key words: spam; blacklist; database; java BerkeleyDB
電子郵件是最常用的網(wǎng)絡(luò)應(yīng)用之一,已經(jīng)成為網(wǎng)絡(luò)交流溝通的重要途徑。但是,垃圾郵件(spam)隨著互聯(lián)網(wǎng)的不斷發(fā)展而大量增長(zhǎng),現(xiàn)在包含著商業(yè)宣傳、色情、政治,以及計(jì)算機(jī)病毒等不同內(nèi)容的垃圾郵件可以說(shuō)是鋪天蓋地。我校為方便全校教師教學(xué)工作而自行開(kāi)發(fā)的郵件服務(wù)器受到了垃圾郵件的侵害,給學(xué)校的教師的正常教學(xué)工作帶來(lái)極大的煩惱。為了解決這一問(wèn)題,開(kāi)發(fā)識(shí)別垃圾郵件模塊的需求迫在眉睫。
1 需求分析
設(shè)計(jì)一個(gè)合格的垃圾郵件地址過(guò)濾模塊,需要對(duì)模塊需求有個(gè)大致的分析:
1) 數(shù)據(jù)空間占用估算:目前我們已經(jīng)擁有一個(gè)近百萬(wàn)級(jí)的垃圾郵件地址黑名單,為了滿足日后需要,我們?cè)O(shè)計(jì)一個(gè)擁有5百萬(wàn)個(gè)垃圾電子郵件地址的黑名單,如果按照一個(gè)郵件地址約為28個(gè)字節(jié)的估算,則該黑名單約需占用133.51MB存儲(chǔ)空間大小(尚未包括附屬的空間開(kāi)銷(xiāo))。如果服務(wù)器不僅僅完成黑名單查詢工作,出于可靠以及內(nèi)存消耗考慮,所有垃圾郵件數(shù)據(jù)是需要通過(guò)使用磁盤(pán)來(lái)存儲(chǔ)。
2) 查詢時(shí)間占用估算:按照用戶收發(fā)郵件的習(xí)慣,大家希望能在數(shù)秒內(nèi)收到相應(yīng)的郵件,這就約束了郵件地址過(guò)濾時(shí)間應(yīng)該相當(dāng)短暫,不宜超過(guò)1~2秒。
3) 原來(lái)的郵件服務(wù)器是使用Java編寫(xiě)的,為了能較好的與原郵件系統(tǒng)進(jìn)行融合,過(guò)濾模塊同樣采用Java實(shí)現(xiàn)。
2 技術(shù)基礎(chǔ)
為了同時(shí)滿足以上必要條件,從而排除了使用java中Set、Map容器(雖然該容器有很高的查詢性能、但由于黑名單太大,這兩種容器無(wú)法處理這樣大量數(shù)據(jù))以及常見(jiàn)的關(guān)系/對(duì)象型數(shù)據(jù)庫(kù)(不能在很短的時(shí)間內(nèi)在5百萬(wàn)的記錄中查詢出相應(yīng)結(jié)果),而號(hào)稱每秒能完成近百萬(wàn)次查詢的高性能Berkeley DB是方案的不二之選。
Berkeley DB(BDB)是一個(gè)高性能的,嵌入數(shù)據(jù)庫(kù)編程庫(kù),和C語(yǔ)言,C++,Java,Perl,Python,Tcl以及其他很多語(yǔ)言都有應(yīng)用程序編程界面。Berkeley DB可以保存任意類(lèi)型的鍵/值對(duì),而且可以為一個(gè)鍵保存多個(gè)數(shù)據(jù)。Berkeley DB可以支持?jǐn)?shù)千的并發(fā)線程同時(shí)操作數(shù)據(jù)庫(kù),支持最大256TB的數(shù)據(jù),廣泛用于各種操作系統(tǒng)包括大多數(shù)Unix類(lèi)操作系統(tǒng)和Windows操作系統(tǒng)以及實(shí)時(shí)操作系統(tǒng)。數(shù)據(jù)訪問(wèn)算法可選用B+樹(shù)算法、HASH算法、Recno算法和Queue算法。
經(jīng)過(guò)實(shí)際測(cè)試,Berkeley DB確實(shí)能勝任該項(xiàng)任務(wù)。
3 設(shè)計(jì)及實(shí)現(xiàn)
Berkeley DB作為垃圾郵件地址黑名單的存儲(chǔ)、查詢引擎,整個(gè)模塊設(shè)計(jì)及實(shí)現(xiàn)盡可能?chē)@著提高處理性能展開(kāi)。垃圾郵件地址作為Key(Data在這里沒(méi)有存在的意義,但由于數(shù)據(jù)庫(kù)的需要,就用1個(gè)字節(jié)的任意數(shù)值代替),記入黑名單數(shù)據(jù)庫(kù)中。為了減小存儲(chǔ)空間并提高性能,模塊里對(duì)垃圾郵件地址作了一次反轉(zhuǎn)操作,如將15608111788@sc.com轉(zhuǎn)換為“moc.cs@88711180651”,使得整個(gè)黑名單數(shù)據(jù)的字母順序非常接近,大大提高了緩存的效率和性能。對(duì)于海量數(shù)據(jù)Berkeley DB支持B+Tree以及Hash兩種訪問(wèn)算法,通過(guò)分析垃圾郵件地址的規(guī)律,并且通過(guò)實(shí)際測(cè)試(采用了9百萬(wàn)的數(shù)據(jù)),最終選擇了B+ Tree算法。Berkeley DB本身還提供三種操作方式:Transactional(事物)、 Concurrent(并發(fā))和Private(私有)。出于目前作為單機(jī)系統(tǒng)的考慮,模塊采用Private方式,極大提高訪問(wèn)速度。
整個(gè)模塊以blacklist類(lèi)來(lái)定義并實(shí)現(xiàn),其他代碼直接調(diào)用該類(lèi)的類(lèi)成員方法即可實(shí)現(xiàn)相應(yīng)功能,以下是blacklist類(lèi)的定義:
public class blacklist
{
private Environment m_DbEnvironment = 1;
privateDatabase m_Db = 1;
private static final String m_DbFileName = \"blacklist.db\"; //黑名單庫(kù)的名稱
private static final File m_EnvDir = new File(\"/blacklist/env\"); //BDB的環(huán)境文件目錄
private static final File m_DbDir = new File(\"/blacklist/db\");//BDB的數(shù)據(jù)庫(kù)文件目錄
public blacklist() {…}
public boolean blacklist_open(){…} //打開(kāi)數(shù)據(jù)庫(kù)
public void blacklist_close(){…} //關(guān)閉數(shù)據(jù)庫(kù)
public void blacklist_append(String email){…} //在數(shù)據(jù)庫(kù)中追加黑名單
public boolean blacklist_delete(String email){…} //在數(shù)據(jù)庫(kù)中刪除黑名單
public long blacklist_load(String filename){…} //從文件中批量導(dǎo)入黑名單
public boolean blacklist_search(String email){…} //在數(shù)據(jù)庫(kù)中查找是否垃圾郵件
}
從以上類(lèi)的定義中可看出類(lèi)方法主要由load(從垃圾郵件名單文本文件中批量載入并保存至黑名單數(shù)據(jù)庫(kù)中)、search(對(duì)任意郵件地址在黑名單數(shù)據(jù)中查詢)、append(添加單個(gè)垃圾郵件地址至黑名單數(shù)據(jù)庫(kù)中)和delete(從黑名單數(shù)據(jù)庫(kù)中刪除單個(gè)垃圾郵件地址)四個(gè)主要功能方法以及open和close兩個(gè)輔助方法構(gòu)成。
下面的例子使用blacklist類(lèi)的load方法對(duì)含有915萬(wàn)個(gè)郵件地址進(jìn)行導(dǎo)入測(cè)試:
(測(cè)試計(jì)算機(jī)配置:CPU為Intel P4 3.00GHz、RAM 512M、硬盤(pán) IDE 7200RPM、WinXP SP2、JDK 1.6、Berkeley DB 4.7.25)
public class load {
public load() { }
public static void main(String[] args) {
blacklist app = new blacklist();
app.open();
long start, end;
start = System.currentTimeMillis();
app.load(\"/blacklist/915.txt\");
end = System.currentTimeMillis();
System.out.println(\"load file(ms):\" + (end - start));
app.close();
}
}
結(jié)果為:load file(ms):1312516
生成一個(gè)文件大小為413M的垃圾郵件地址的黑名單數(shù)據(jù)庫(kù),耗時(shí)也不過(guò)1313秒。通過(guò)以上結(jié)果可計(jì)算出,模塊進(jìn)行批量導(dǎo)入時(shí)每秒可導(dǎo)入5243個(gè)郵件地址。
下面這個(gè)簡(jiǎn)單例子,在相同平臺(tái)下對(duì)先前生成的黑名單進(jìn)行模擬查詢測(cè)試(測(cè)試的樣本為2000個(gè)郵件地址,其中1000個(gè)在黑名單中,剩余1000個(gè)不在黑名單中):
public class query
{
public query() {}
public static void main(String[] args)
{
blacklist app = new blacklist();
app.open();
long start = 0, end = 0;
File file = new File(\"/blacklist/test.txt\");
BufferedReader reader = 1;
start = System.currentTimeMillis();
try
{reader = new BufferedReader(new FileReader(file));
String line = 1;
while ((line = reader.readLine()) != 1)
{app.search(line);
}
reader.close();
}
catch (IOException e)
{
e.printStackTrace();
}
end = System.currentTimeMillis();
System.out.println((end-start) + \"ms\");
app.close();
}
}
結(jié)果為:156ms(毫秒)
可見(jiàn),不論是否在黑名單庫(kù)中,判別一個(gè)郵件地址的速度極快,每秒種可完成約12820次查詢)。
整個(gè)模擬測(cè)試運(yùn)行中包括java虛擬機(jī)本身整個(gè)空間占用約為13M(包含1M緩存),基本滿足垃圾郵件地址過(guò)濾的功能需求。
4 性能提高
如果需要增強(qiáng)垃圾郵件地址過(guò)濾處理能力,現(xiàn)有單機(jī)系統(tǒng)可以采用號(hào)稱讀取100萬(wàn)數(shù)據(jù)只需要0.33秒的Tokyo Cabinet數(shù)據(jù)庫(kù),該數(shù)據(jù)庫(kù)比Berkeley DB 快3倍左右,并且能過(guò)Tokyo Tyrant輕松實(shí)現(xiàn)分布式處理。只是由于只能運(yùn)行于Linux及32位操作系統(tǒng)下存在單個(gè)數(shù)據(jù)庫(kù)文件不能超過(guò)2G的限制,因而本次沒(méi)有采用該數(shù)據(jù)庫(kù)引擎。
另外還可以采用分布式計(jì)算,更可大幅度提高整個(gè)模塊處理性能,例如采用FastDHT(高性能分布式Hash系統(tǒng),底層存儲(chǔ)仍采用Berkeley DB)、BigTable、HBase以及上面提到的Tokyo Tyrant等等,只是識(shí)別正確率可能會(huì)隨著分布式系統(tǒng)的可能出現(xiàn)的節(jié)點(diǎn)故障而有所下降。
5 結(jié)束語(yǔ)
本文研究了對(duì)大批量垃圾郵件地址黑名單的存儲(chǔ)、查詢處理,在保證了較高的正確率、較少的空間占用的前提下,能夠以較快的速度完成查詢過(guò)濾工作,并且接口方法簡(jiǎn)單,較好的達(dá)到模塊要求。
該模塊經(jīng)過(guò)近2個(gè)月的運(yùn)行,工作正常,有效地阻止了垃圾郵件的傳播,極大地改善了教學(xué)環(huán)境,較好的達(dá)到防止垃圾郵件的目的。
參考文獻(xiàn):
[1] 《嵌入式數(shù)據(jù)庫(kù)系統(tǒng)Berkeley DB》.http://www.ibm.com/developerworks/cn/linux/l-embdb/index.html.
[2] 《Getting Started with Berkeley DB for Java》. http://www.oracle.com/technology/documentation/berkeley-db/db/gsg/JAVA/BerkeleyDB-Core-JAVA-GSG.pdf.
[3] Bind DLZ. http://bind-dlz.sourceforge.net/bdbhpt_driver.html.