2009年2月2日

自力開發的Java FTP Server

去年年底忙完國科會計劃書之後,就開始發瘋的用Java寫FTP Server,過年期間同樣沒有懈怠,持續發瘋中~

既然是發瘋的成果,自然成果驚人。

我寫的FTP Server取名叫做「MyFTPBox」。

和其他自己寫得程式一樣,在開發時有注意使用的套件授權。
目前MyFTPBox使用的第三方套件只有SQLiteJDBC,這個SQLite的Java API授權是BSD,非常自由。
因此目前來說,產權沒有任何問題。

MyFTPBox目前已經支援下面功能:
1. 完全支援 UTF8,啟動時偵測系統的檔案編碼,並以此作為預設編碼,FTP Client登入後,可以使用OPTS UTF8 ON支援UTF8(Linux下由於預設都已經是UTF8編碼,因此FTP Server預設編碼直接是UTF8)

2. 經過簡單的測試,看起來能夠正常支援MODE ZMODE Z是一種壓縮技術,使用zlib作為壓縮的演算法,它會在資料傳輸過程中自動壓縮,不需要額外設定,但FTP Client同樣需要支援MODE Z,目前用CuteFTP Pro、SmartFTP測試,在使用MODE Z後,CuteFTP ProSmartFTP仍舊能夠正常的顯示出檔案列表,證明應該是work的

3. 流量控制,每個使用者能夠設定流量限制,但目前只能對每個連線限制流量,例如我限制10k,當同時下載2個檔案時,2個檔案都是10k

4. 極端混亂且可能有問題的虛擬檔案系統,我仿照ZFTP Server的模式設定,可以新增虛擬目錄,也可以把實體目錄對應到虛擬目錄下,但目前還有些bug(混亂原因在於,ZFTP那應該是用linklist寫的,我是用SQL寫的,SQL上資料都是平面的,而且因為欄位的關係,目前我處理目錄的方式很笨,寫得也亂)

5. 帳號管理、虛擬檔案系統均使用SQLite管理,因為都使用SQL code,因此未來很容易可以移植到mysql、M$ SQL Server,甚至M$ Access中,至於Server的設定,由於要可以指定使用的SQL Server和帳號密碼等,目前傾向另外用xml來儲存,用xml儲存的設定應該會包括Server Port、Admin Port、SQL、系統編碼

6. 簡易的Telnet管理介面,目前有實做了管理用Telnet Admin Server,目前可以用telnet的方式連入進行帳號、虛擬檔案系統的管理,未來畫出GUI的管理程式後,就可以有類似ZFTP Administraotr Interface那樣的管理程式來操作了。

7. 其他比較值得提到的,大概就是PASV/PORT mode,正式一點的FTP Server原則上都支援了,只有那種超小型的FTP Server半成品才不支援PASV mode,我的Java FTP Server能夠正常的支援PASV/PORT mode;此外,大概就是檔案列表吧~目前我的Java FTP Server支援UNIX Style檔案列表和MLSD/MLST Style檔案列表,這也是比較正式的FTP Server原則上都支援的(UNIX上的FTP Server有可能只支援UNIX Style)

整體來說,基於老王賣瓜的心裡,我認為這FTP Server還不錯,不過還需要花很多時間繼續加功能和修程式,但以功能性來說,目前Windows上主流FTP Server有的幾個功能都有支援了,不過都不夠完善就是了。
那最容易被問到的就是,既然都有了,那寫它幹嘛?它作用是?
首先,它就基本的FTP Server來說算是完成度很高的,它再加入SSH Tunnel的功能後,可以寫成類似Tunnelier這樣的SSH Tunnel程式,並且和Tunnelier一樣可以作到FTP-SFTP-Bridge的功能。
而目前Java的SSH Tunnel API很多,而且幾乎都是BSD、LGPL的,要開發Java版的SSH Tunnel並不難。
除了可以延伸寫成支援FTP-SFTP-Bridge的SSH Tunnel外,它算是我第一個檔案傳輸伺服器的程式,基本樣式完成了,未來要改成影像串流或其他檔案傳輸用的Custom Server都可以節省伺服器開發的功夫。
而這套Java FTP Server本身可能的賣點是,雖然在Windows上FTP Server選擇很多,像ZFTP Server、FileZilla Server、G6都是常見的選擇,我也是以它們為範本開發的,但首先,ZFTP Server在3.0之前都還不支援UTF8,G6要錢,FileZilla Server的管理介面非常難用。
其次,我們把場景放到Linux上,Linux上的FTP Server幾乎都強調高效能、高穩定性,但是很少可以像ZFTP Server、FileZilla Server這樣有虛擬檔案系統可以讓我們自己拉目錄,使用者管理又幾乎都跟系統帳戶綁在一起,不用系統帳戶,就要透過複雜的步驟讓FTP Server支援mysql。
對大部分人來說,僅僅希望在Linux上安裝個FTP站台,專門放mp3、動畫這樣簡單的需求,卻要搞得好像要開ftp.ntu.edu.tw這樣的大型站台。
然而對於一般性的需求,像是頻寬限制,帳戶登入時間管制之類的,卻要辛苦的k 使用手冊,找設定找半天才能作到,如果以這樣的角度來看,我認為我這套Java FTP Server是有賣點在的,因為它跨平台,又以Windows FTP Server為範本,用在Linux上反而能凸顯出它的特殊性,像MODE Z,Linux上有多少FTP Server支援它?應該很少吧~

PS:
最後附註一下,一直以來Java都號稱對網路程式開發可以很容易的設計,我一直都對此疑惑,但這次寫FTP Server,我發現Java在開發FTP Server時,其實滿容易的,Java本身幾乎支援FTP Server所需的所有功能,像MODE Z的核心zlib,Java直接就有InputStream、OutputStream可以套用,套上去就有了,像UTF8也是,直接套個InputStreamReader加個編碼就搞定了,同樣是開發FTP Server,我相信用gcc和glibc應該會複雜很多,光要把zlib library套進socket stream應該就有點麻煩了,再處理UTF8和non-UTF8應該也不是輕鬆的事。

5 則留言:

匿名 提到...

真是太厲害了~

不過為什麼會想要自己寫啊?練功嗎?

匿名 提到...

>> 但是很少可以像ZFTP Server、FileZilla Server這樣有虛擬檔案系統可以讓我們自己拉目錄

在 Linux 上要實作這種虛擬檔案系統的功能非常簡單,使用 mount --bind 即可,只需一個指令。:p

>> 使用者管理又幾乎都跟系統帳戶綁在一起,不用系統帳戶,就要透過複雜的步驟讓FTP Server支援mysql。

在 Linux 上 Proftpd/Pureftpd 都可以不用綁系統帳戶,而且還支援 LDAP 等認証。當然易用性上不是那麼親和就是,熟的人會覺得很簡單啦... :p

>> 對大部分人來說,僅僅希望在Linux上安裝個FTP站台,專門放mp3、動畫這樣簡單的需求,卻要搞得好像要開ftp.ntu.edu.tw這樣的大型站台。

只有這樣的需求的話,那可以使用 vsftpd,含安裝啟動只需兩個步驟。其他的也是如此,只是其操作多為文字介面,讓人不習慣而已

>> 然而對於一般性的需求,像是頻寬限制,帳戶登入時間管制之類的,卻要辛苦的k 使用手冊,找設定找半天才能作到,如果以這樣的角度來看,我認為我這套Java FTP Server是有賣點在的

的確,良好的操作介面很重要:)

>> 因為它跨平台,又以Windows FTP Server為範本,用在Linux上反而能凸顯出它的特殊性,像MODE Z,Linux上有多少FTP Server支援它?應該很少吧~

Proftpd 有 mod_flate 模組可完整支援 MODE Z... 而且他還有一堆模組可以實現很酷的功能...

不過,私以為 MODE Z 只適用小型站台... 高流量站台,加上 MODE Z 會額外增加不少系統的負載程度...

Cody 提到...

的確~練功的成份比較多些。

在Linux上的確有幾套不錯的FTP Server可以選擇,但是正如留言中提到的,Linux上的FTP Server通常不大人性化。
而且通常有一好沒兩好。

像vsftpd我很常用,它設定簡單,可是他不支援虛擬檔案系統、MODE Z、獨立帳號管理,同樣簡單方便的FTP Server在Windows上,ZFTP、G6都支援。
在Linux上要俱備虛擬檔案系統、MODEZ、獨立帳號管理的不是沒有,但是像proftpd設定很麻煩,它設定檔類似apache的VirtualHost,這並不好設。

Benson 提到...

我正在為了linux下找不到原生支援utf8的ftp server煩腦中就看到這篇了...
收獲不少...謝謝!

Unknown 提到...

先進:

手中有需求
需透過ftps implicit
下載檔案
正利用Java
但無法突破

先進可否指點?

謝謝

Chan