基於XMPP協議的Android即時通訊系

yangxi_001發表於2014-08-06

以前做過一個基於XMPP協議的聊天社交軟體,總結了一下。發出來。

      設計基於開源的XMPP即時通訊協議,採用CS體系結構,通過GPRS無線網路用TCP協議連線到伺服器,以架設開源的Openfn'e伺服器作為即時通訊平臺。

         系統主要由以下部分組成:一是伺服器,負責管理髮出的連線或者與其他實體的會話,接收或轉發XML(ExtensibleMarkup Language)流元素給授權的客戶端、伺服器等;二是客戶終端。它與伺服器相連,通過XMPP獲得由伺服器或任何其它相關的服務所提供的全部功能。三是協議閘道器。完成XMPP協議傳輸的資訊與外部訊息系統可識別資訊間的翻譯。再就是XMPP網路。實現各個伺服器、客戶端間的連線。系統採用客戶端(Client)/服務端(Server)架構體系結構。

 

客戶端:

        客戶端基於Android平臺進行開發。負責初始化通訊過程,進行即時通訊時,由客戶端負責向伺服器發起建立連線請求。系統通過GPRS無線網路與Internet網路建立連線,通過伺服器實現與Android客戶端的即時通訊腳。


伺服器端:

       伺服器端則採用Openfire作為伺服器。允許多個客戶端同時登入並且併發的連線到一個伺服器上。伺服器對每個客戶端的連線進行認證,對認證通過的客戶端建立會話,客戶端與伺服器端之間的通訊就在該會話的上下文中進行。

 

1.1伺服器端設計(這塊幾乎可以說是有成品了。不用多糾結)

        androidpn伺服器端是java語言實現的,基於openfire開源工程,Web部分採用的是spring框架,這一點與openfire是不同的。Androidpn伺服器包含兩個部分,一個是監聽特定埠上的XMPP服務,負責與客戶端的XMPPConnection類進行通訊,作用是使用者註冊和身份認證,併傳送推送通知訊息。另外一部分是Web伺服器,採用一個輕量級的HTTP伺服器,負責接收使用者的Web請求。

       主要的四個組成部分,分別是SessionManager,Auth Manager,PresenceManager以及Notification Manager。SessionManager負責管理客戶端與伺服器之間的會話,Auth Manager負責客戶端使用者認證管理,Presence Manager負責管理客戶端使用者的登入狀態,NotificationManager負責實現伺服器向客戶端推送訊息功能。

       系統客戶端基於Android手機平臺。採用XMPP作為即時通訊協議。XMPP是基於XML,實現任意兩個網路終端準實時的交換結構化資訊的通訊協議。採用Android平臺提供的XML解析包對XML進行解析。由於應用活動都執行於主執行緒。故用多執行緒技術來解決系統通訊問題。針對通訊安全問題.系統的使用者資訊和聊天資訊在客戶端儲存在Android平臺自身所帶的SQLite資料庫中,多媒體檔案和圖片檔案儲存在Android平臺虛擬檔案儲存裝置SD Card中。

 

        通訊模組負責與伺服器建立通訊舊。通過建立3個執行緒來進行處理。分別負責訊息的傳送、接收和心跳資訊的傳送;解析模組主要用來解析XML資料流。根據解析元素不同型別封裝成不同的資料物件:資料模組定義整個客戶端中大部分的資料型別和物件;應用模組包括即時通訊、圖片瀏覽和音樂播放。是客戶端和使用者交流的介面;加密模組對傳送和接收的訊息進行加解密。以確保通訊資料的安全。

 

系統的客戶端分為5大模組進行設計開發,如圖2所示。

       通訊模組負責與伺服器建立通訊舊。通過建立3個執行緒來進行處理。分別負責訊息的傳送、接收和心跳資訊的傳送;解析模組主要用來解析XML資料流。根據解析元素不同型別封裝成不同的資料物件:資料模組定義整個客戶端中大部分的資料型別和物件;應用模組包括即時通訊、圖片瀏覽和音樂播放。是客戶端和使用者交流的介面;加密模組對傳送和接收的訊息進行加解密。以確保通訊資料的安全。

加密(首先將二進位制碼轉換成BASE64碼,在轉換成BASE64碼之後,再進行MD5加密,)

XMPP伺服器之間、客戶與伺服器之間採用的是TCP連線罔。TCP提供一種瓦向連線、可靠的位元組流服務。保持一個實時雙向的傳輸通道。TCP將使用者資料打包構成報文段。它傳送資料後啟動一個定時器,等待對端資料確認,另一端對收到的資料進行確認,對失序的資料重新排序,並丟棄重複資料;TCP提供端到端的流量控制。計算和驗證一個強制性的端到端檢驗。但是GPRS網路對TCP鏈路存在一個限制。當TCP鏈路在長時間無有資料流量時。會自動降低此鏈路的優先順序直至強制斷開此鏈路。所以在應用中.採用傳送心跳的方式來維持此鏈路。

 資料格式

        XMLXMPP系統架構的核心。它能表述幾乎任何一種結構化資料。特別是XMPP利用XML資料流進行客戶端一伺服器端、伺服器端一伺服器端的通訊。XML資料流一般是由客戶端發起至服務端,XML資料流的有效時間直接與使用者的線上會話有效時間相關聯。

 協議訊息格式

XMPP協議包括3個頂層XML元素:MessagePresenceIQmMessage用來表示傳輸的訊息,當使用者傳送一條訊息時。就會在流的上下文中插入一個Message元素,中間有使用者傳送的相關資訊;Presence用來表示使用者的狀態。當使用者改變自己的狀態時。就會在資料流的上下文中插入一個Presence元素,用來表示使用者現在的狀態;IQ用來表示一種請求,響應機制,從一個實體傳送請求,另外一個實體接受請求並響應。

後臺Servic

從類的層次看這個結構比較簡單,讓其變得複雜的是,其裡面有三個執行緒:主執行緒,進行Xmpp通訊執行緒,連線出錯重試執行緒。

對圖說明:

  1. NotificationService裡建立一個單執行緒,讓其對伺服器進行連線,由於使用Xmpp連線伺服器要分為三步:連線,註冊,登陸。所以用一個棧來儲存要執行的Task任務(ConnectTaskRegisterTaskLoginTask),還後再按這個順序進行執行。

  2. 連線Xmpp伺服器的執行緒用的是Executors.newSingleThreadExecutor(),這個本身可以不停的submit任務。為什麼還要自己用一個棧來儲存Task

  3. 連線執行緒在連線,註冊,登陸的過程中,都有可能出錯,都可能會失敗,這時我就要有一個重連的機制,在Androidpn裡開了另外一個執行緒來進行重試,其重試不是每次都按多少秒來進行重試,而是有其自己的規則。 

  4. LoginTask裡,如果登陸了伺服器端,其就會註冊一個監聽器,用於監聽伺服器push的資料包(Packet),再通過傳送廣播的方式來通知要進行顯示的程式。

  5. 在登陸伺服器後,也有可能出錯,所以在登陸後,會設定一個ConnectionListener,用於監聽連線出錯的時候,再合適重連執行緒,進行重連

  6. 在登陸過程中,有一種錯誤要單獨處理,就是賬號和密碼無效的時候,這個時候其返回的狀態碼是401,這種情況應該把本地儲存的帳號和密碼都清掉,再重新進行連線,不然會永遠都登陸不上伺服器端。

由於該系統所有的功能實現都是基於網路間的XML流的通訊,所以,需要有一個模組專門負責網路問通訊和XML流的處理,主要功能包括伺服器和客戶端之問通訊時TCP套接字的處理,XML流的解析、儲存等功能。

資料模組負責XML流的解析和封裝的XML模組,主要功能是:將XML流解析成java物件,將iava物件封裝成XML流;

其流程是XMPP伺服器接收到XML流之後,會有瀆取器將其讀取出來並將其作為入口引數傳入XML解析器,XML解析器通過對其名稱空間的解析,從而確定將剩餘的XML元素解析出來並傳入相應的;ava物件中,從而最終將XML轉換成iava物件,然後將iava物件傳入應用程式模組中,實現其請求完成的功能並返回iava物件,但是該iava物件不能在網路中直接傳輸,必須先轉換成XML節,於是,該iava物件會被傳入XML封裝器中,被封裝成XML節,通過XMPP伺服器的傳送埠發往目的節點。

java物件處理模組處理流程如下:當該模組接收到iava物件時,會先將該物件通過解密演算法和解密金鑰解密成base64碼,然後f耳將base64碼轉換成二進位制碼,從而實現對java物件的解析。當完成業務邏輯處理後,該模組會將返回的java物件先由二進位制碼轉換成base64碼,然後用加密演算法將其加密,這裡的加密演算法是由雙方在建立會話時通過三次握手協議協商的。

XML節被封裝成java物件後,必須被轉發至訂:確的模組中加以處理,這就要求有一個路由轉發模組,如圖33所示。該模組的實現原理是:在系統啟動時載入該路由模組,從而在記憶體中建立了一塊路由模組,記錄了命名空和功能模組之間的對應關係,當iava物件被封裝好之後,系統會讀出其名稱空間,再在路由表中查詢其所對應的模組,從而動態地載入該模組,並將該java物件轉發至該模組,從而實現路山轉發的功能。

相關文章