本篇文章翻譯XMPP Framework中的Overview of the XMPP Framework部分 css
The framework is divided into 2 parts:
1. xmpp核心部分
2. xmpp擴展(roster,XEP's,可選的支持工具等)html
xmpp核心部分實現了xmpp規範(RFC 3920)git
請不要把聊天與xmpp混淆,xmpp全稱是」可擴展消息與存在協議」,它是一種可以用於多種用途的通用協議,其實眼下有很是多公司使用這個框架好比家庭本身主動化,在醫院傳達警報給護士。github
可擴展包含好比支持花名冊。本身主動重連與多種xmpp擴展實現(XEP's).。objective-c
XMPP核心文件在本地命名爲」Core」的目錄中。這些文件包含:數據庫
這個框架的核心是XMPPStream
類,這是你將要交互使用的基本的類。它是所有的擴展與定義代碼插入的類,它具備一些使框架靈活,可擴展,易於在上面開發有趣的功能。安全
這些將在稍後的文檔中更深刻的討論。markdown
XMPPParser 是XMPPStream使用的內部類。你或許已經猜出它是作什麼的了,你不需要以不論什麼方式形式與這個解析器交互。網絡
XMPPJID 提供了一個不變的JID (Jabber Identifier)實現,它支持解析JID's,並以各類形式提取JID的各個部分。它遵照NSCopying協議。一邊JID's可以當作NSDictionary的key。它也遵照NSCoding協議。架構
XMPPElement 是3個主要XMPP元素的基類:XMPPIQ, XMPPMessage & XMPPPresence. XMPPElement擴展NSXMLElement類,所以你有所有的NSXML的功能。檢查不論什麼xml元素。在這個章節有不少其它具體的描寫敘述Elements: IQ, Message, & Presence。
XMPPModule 提供可選植入擴展的基礎類,假設你正在寫你本身應用執行的代碼。
你很是可能只建立你本身的類。註冊接受代理調用。但是假設你正在實現一個標準的XEP。
或者你想你的應用指定擴展是可被植入,那麼你要在XMPPModule上建立,Module在後面更具體的被介紹。
XMPPLogging 提供一個很是快,強大靈活的日誌框架,它會在XMPP Logging 章節中討論。
XMPPInternal 不過關於核心和各類高級底層擴展內部的東西。
XMPPElement擴展NSXMLElement類。所以你有所有的NSXML的功能,檢查不論什麼xml元素。
除了NSXML基礎功能外,還提供了NSXMLElement+XMPP 類別。
這個類別提供各類方便的方法讓你的代碼更簡潔易讀。
好比:
[element attributeIntValueForName:@"age"];
不少其它的信息請看Working With Elements頁面
一個xmpp stream配置初始化被分爲多個部分:
對於大部分人來講。這僅涉及一個步驟 - 設置stream的myJID屬性。
好比:
xmppStream.myJID = [XMPPJID jidWithString:@"user@gmail.com"];
該xmpp stream 將查找遵循XMPP RFC的剩餘信息,這包含正在進行的SRV查找_xmpp-client._tcp.domain。在上面的樣例中,使用Gmail,谷歌server可能會返回類似"talk.google.com"。而後xmpp stream將會連接到該server,假設SRV查找查找失敗,那麼xmpp stream 將會簡單連接到JID's domain。
假設你知道你正在鏈接到不具備xmpp SRV記錄的xmppserver。你可以告訴xmpp stream 經過指定的主機名跳過SRV查找,好比:
xmppStream.myJID = [XMPPJID jidWithString:@"user@myCompany.com"];
xmppStream.hostName = @"myCompany.com";
主機名也會派上用場,當你使用一個開發xmppserver。可能server是在背地網絡可用的,或者不具備DNS地址等,好比:
xmppStream.myJID = [XMPPJID jidWithString:@"user@dev1.myCompany.com"];
xmppStream.hostName = @"192.168.2.27";
還有一個可選的屬性是主機port,默認狀況下,並依照xmpp規範。差點兒所有的server上的port都在5222執行。假設你的server在不一樣的port上執行。那可以設置主機port的屬性。
XMPPStream有一些旨在使框架靈活,可擴展,易於在上面開發有趣的功能。當中之中的一個使用MulticastDelegate。
什麼是MulticastDelegate?
xmpp framework需要支持擴展的數量不受限制,這包含對這個框架的官方擴展,以及不論什麼數量的擴展或你想要插入這個框架的本身定義代碼。所以傳統的代理模式是行不通的。xmpp 模塊和擴展需要分開到本身單獨的類。但每個類都需要接受代理方法。而標準NSNotification架構將沒法勝任,一些代理要求返回變量。(加上它真的很是煩人要從userInfo字典的通知中提取參數)。
所以一個MulticastDelegate贊成你使用一個標準的代理模式插入框架中。但它贊成多個類接受想用的代理通知。這樣作的優勢是,你沒必要把所有的xmpp處理代碼在一個類中。你可以以爲你合適的方法分開處理在不一樣的類中。
你可以不論什麼時間加入/刪除XMPPStream的代理對象:
[xmppStream addDelegate:self delegateQueue:dispatch_get_main_queue()];
...
[xmppStream removeDelegate:self];
不少其它關於MulticastDelegate的討論可以在這裏找到。
線程和隊列更具體的討論可以在這裏找到。
這有一些關於這個框架的擴展,固然。你可以如你所願寫儘量多的擴展。
咱們不會檢查所有可用的擴展,但咱們會列出幾個在這裏演示樣例。
做爲樣例,咱們將會插入XMPPReconnect模塊在咱們的stream:
xmppReconnect = [ [XMPPReconnect alloc] init];
// Optional configuration of xmppReconnect could go here.
// The defaults are fine for our purposes.
[xmppReconnect activate:xmppStream];
// You can also optionally add delegates to the module.
[xmppReconnect addDelegate:self delegateQueue:dispatch_get_main_queue()];
// And that's all that is needed.
// The module will receive any delegate methods it needs automatically
// from the xmpp stream, and will continue to do its thing unless you deactivate it.
當你準備好,你可以開始鏈接進程:
NSError *error = nil;
if (![xmppStream connect:&error])
{
NSLog(@"Oops, I probably forgot something: %@", error);
}
假設你忘記設置必需的屬性。好比myJID,那麼connect方法會返回NO,錯誤消息會通知你的問題。
在鏈接過程當中。client和server通過一個xmpp握手。
在此期間,server通知各類它支持以及需要的各類協議給client。有些server可能需要鏈接經過SSL/TLS。假設是這種狀況下,xmpp stream將本身主動保護鏈接,假設你正在鏈接server以不對X509證書。你可能需要實現xmppStream:willSecureWithSettings: 代理方法來改變默認的安全設置。
所有的鏈接握手結束後xmppStreamDidConnect: 代理方法被調用。這通常是大多數client應啓動驗證過程:
- (void)xmppStreamDidConnect:(XMPPStream *)sender { [xmppStream authenticateWithPassword:password error:NULL]; }
這有幾個目標對於整個XMPP架構日誌:
它必須支持多種日誌級別.
不是所有的日誌消息具備相同的優先級。有些是有關錯誤的,而其它都不過信息。日誌分級幫助開發人員保證他們的日誌信息完整的。可以打開和關閉他們沒有不論什麼困難。
它必須在每個文件基礎上可配置
一個全局日誌級別不會接受當這個框架包含了這麼多文件。
加上調試的問題每每開發人員只但願看到幾個文件的日誌語句。
它必須可配置於終端用戶
xmpp framework 需要對日誌語句全然控制,用戶有很是多不一樣的需求。一些想要日誌聲明到一個文件裏,一些可能想要日誌聲明到數據庫裏。或者可能他們需要針對日誌聲明在不一樣的地方,取決於日誌聲明來源於app中仍是xmpp framework。
我從事client多年來的工做。我看到第三方框架一遍又一遍發生相同的問題。
第三方庫自帶散落着的NSLog語句。終於需要用戶經過庫凝視掉NSLog語句,或者將它們轉換爲一些原始的本身定義宏的版本號。
xmpp framework 採用了專業的日誌框架CocoaLumberjack。
這個日誌框架實際上比的NSLog更快。作相同的事情時也是如此。此外,它還支持大量不一樣的配置,並贊成終端用戶甚至可以加入本身的本身定義日誌記錄,篩選和格式化。
如下是你需要知道的XMPPFramework有關日誌的設置:
對於在框架內部大多數文件頂部你會發現例如如下:
// Log levels: off, error, warn, info, verbose
static const int xmppLogLevel = XMPP_LOG_LEVEL_WARN;
如你所見有4個日誌級別(加上 XMPP_LOG_LEVEL_NONE):
您可以更改不論什麼文件的日誌級別。要它輸出不少其它的信息。
除了這一點。可啓用一個跟蹤標記。當啓用跟蹤,它輸出正在調用的方法。
請注意。跟蹤是從日誌等級分開的。好比,一個可以設置日誌級別設置爲警告。並啓用跟蹤像這樣:
// Log levels: off, error, warn, info, verbose
static const int xmppLogLevel = XMPP_LOG_LEVEL_WARN | XMPP_LOG_FLAG_TRACE;
就代碼而言意味着:
XMPPLogTrace(); // Enabled - Will spit out "<FileName>: <MethodName>"
XMPPLogError(@"I will get logged");
XMPPLogWarn(@"I will get logged");
XMPPLogInfo(@"I will NOT get logged");
XMPPLogVerbose(@"I will NOT get logged");
除此以外,XMPPStream有一個選項使你可以看到正在發送的原始XML sent/received。你可以把它放在XMPPStream.m像這樣:
// Log levels: off, error, warn, info, verbose
static const int xmppLogLevel = XMPP_LOG_LEVEL_INFO | XMPP_LOG_FLAG_SEND_RECV;
當你啓動應用程序。您需要配置lumberjack框架。
對於剛開始學習的人來講,你可以這樣簡單的設置在你的AppDelegate:
#import "DDLog.h"
#import "DDTTYLogger.h"
- (void)applicationDidFinishLaunching:(NSNotification *)aNotification
{
[DDLog addLogger:[DDTTYLogger sharedInstance] withLogLevel:XMPP_LOG_FLAG_SEND_RECV];
// All your other code...
}
不少其它關於Lumberjack信息參考這裏。
For more information about Lumberjack take a look at its project page.
想要立馬開始?
擴展你的知識!