您好,登錄后才能下訂單哦!
在客戶端中,我們在AndroidManifest.xml文件中找到程序入口,即如下的DemoAppActivity類,
在此類中主要代碼如下
ServiceManager serviceManager = new ServiceManager(this);
serviceManager.setNotificationIcon(R.drawable.notification);
serviceManager.startService();
一路跟進,NotificationService中有個XmppManager類的調用(xmppManager.connect();),而XmppManager類就是客戶端比較重要的類,有這幾個方法
public void connect() {
Log.d(LOGTAG, "connect()...");
submitLoginTask();
}
private void submitConnectTask() {
Log.d(LOGTAG, "submitConnectTask()...");
addTask(new ConnectTask());
}
private void submitRegisterTask() {
Log.d(LOGTAG, "submitRegisterTask()...");
submitConnectTask();
addTask(new RegisterTask());
}
private void submitLoginTask() {
Log.d(LOGTAG, "submitLoginTask()...");
submitRegisterTask();
addTask(new LoginTask());
}
addTask方法中有一個線程隊列,依次添加連接,注冊和登陸任務。用runTask方法執行這些任務
在XmppManager類中有三個內部類,即連接(ConnectTask),注冊(RegisterTask),登陸(LoginTask)三個線程類。
連接類負責與服務端的連接。
注冊類中,即用UUID生成唯一的username和password,然后把它們保存到SharedPreferences中
final String newUsername = newRandomUUID();
final String newPassword = newRandomUUID();
.....
Editor editor = sharedPrefs.edit();
editor.putString(Constants.XMPP_USERNAME, newUsername);
editor.putString(Constants.XMPP_PASSWORD, newPassword);
editor.commit();
而在登陸類中,首先進行連接登陸,把客戶端的信息更新到服務端,即
xmppManager.getConnection().login(
xmppManager.getUsername(),
xmppManager.getPassword(), XMPP_RESOURCE_NAME);
這個操作可能執行多次,直到真正更新到服務器。
執行連接登陸時,服務端就會收到信息。
在服務端,接受消息的類是router包(org.androidpn.server.xmpp.router)下的PacketRouter類,在這里分析消息的類型是什么類型,然后在調用具體的Router,如響應登陸的IQRouter。
如果是登陸(即通過唯一的客戶端標識獲取的session就是為null的),那么就要對這個包進行處理。處理消息包的操作是在 org.androidpn.server.xmpp.handler包下進行的。把消息包處理完后就在維護連接的 org.androidpn.server.xmpp.net包下的Connection類中傳遞消息包到客戶端
XMLWriter xmlSerializer = new XMLWriter(new IoBufferWriter(
buffer, (CharsetEncoder) encoder.get()),
new OutputFormat());
xmlSerializer.write(packet.getElement());
xmlSerializer.flush();
buffer.flip();
ioSession.write(buffer);
如果登陸失敗,就獲取這個異常,重新進行登陸連接直到登陸成功。
注冊登錄的流程就如下所述,下面再講一下,在服務端怎么發送消息到客戶端,客戶端怎么發消息到服務端,客戶端怎么接收來自服務端的消息(服務端接收來自客戶端的消息在如下登陸時已經講了)
在服務端的推送消息的頁面中(form.jsp),是通過notification.do?action=send來跳轉后臺的,那么這個后臺是哪個類 呢,在web.xml中,我們可以看到,攔截器都是spring的類,即這些都通過spring來托管了,那么我們再打開dispatcher- servlet.xml的spring的配置文件,可以看到
class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
/index.do=filenameController
/user.do=userController
/session.do=sessionController
/notification.do=notificationController
notification.do跳轉的頁面就是notificationController即org.androidpn.server.console.controller.NotificationController這個類
class="org.androidpn.server.console.controller.NotificationController">
打開NotificationController類發現它是調用了NotificationManager
if (broadcast.equalsIgnoreCase("Y")) {
notificationManager.sendBroadcast(apiKey, title, message, uri);
} else {
notificationManager.sendNotifcationToUser(apiKey, username, title,
message, uri);
}
一路跟進,可以發現最終發送消息的類還是Connection的deliver方法。而中間的過程就是解析和生成消息的操作
那么客戶端怎么接受消息呢,這個類應該是一個監聽器,從類名和在客戶端一路跟進的過程中,我們大概可以知道是NotificationPacketListener類,在這個類中獲取各個節點的值,然后在客戶端上發送一個通知
那么客戶端發送消息的類又是在哪個類中呢,我們可以參考服務端的發送消息的類是在哪里,沒錯,是在Connection類中,那么我們在客戶端的連接類中 尋找一下是否有發送消息的類。果然,在org.jivesoftware.smack包下的XMPPConection這個類中有個發送消息的方法 sendPacket。我們可以通過xmppManager.getConnection()來獲取連接。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。