Jetfire是OC版本;Starscream是swift版本。 Jetfire--github地址
當(dāng)初老大讓我把github上的開(kāi)源項(xiàng)目Rocketchat-swift翻譯成OC時(shí)可把我這個(gè)小菜鳥(niǎo)愁死了,一沒(méi)文檔啼染,二找不到資源。幸好機(jī)智如我,去cocopods查了下他們使用的websocket協(xié)議的封裝三方是Starscream,github上還附加了OC版的(這個(gè)真要贊一下)权埠。
下面上干貨
先導(dǎo)入類(lèi)庫(kù),可在github上下載拖入煎谍,也可cocopods search jetfire攘蔽。這個(gè)不贅述。
JFRWebSocket提供了簡(jiǎn)單的發(fā)送方法以及連接呐粘、斷開(kāi)满俗、收消息代理方法,而實(shí)際運(yùn)用的時(shí)候業(yè)務(wù)邏輯要復(fù)雜的多,因此再做一層封裝作岖。
新建一個(gè)Socket類(lèi) 引入 JFRWebSocket.h
聲明socket屬性
@property (strong, nonatomic) JFRWebSocket *socket;
聲明一個(gè)init方法 用于app剛啟動(dòng)時(shí)獲得url
- (void)initWithToken:(NSString *)token {
if (token == nil) {
//跳轉(zhuǎn)注冊(cè)頁(yè)面
} else {
_url = deaultUrl;?? //發(fā)送請(qǐng)求唆垃,獲得URL
self.socket = [[JFRWebSocket alloc]initWithURL:[NSURL URLWithString:_url] protocols:@[@"chat",@"superchat"]];
self.socket.delegate = self;
[self.socket connect];
}
}
然后是連接方法與斷開(kāi)方法
#pragma mark-----連接方法-----------
- (void)connect {
if (self.isConnected) {
if (_timer != nil) {
[_timer invalidate];//該定時(shí)器用于自動(dòng)重連
}
}else{
[self.socket connect];
}
}
#pragma mark-----斷開(kāi)連接方法-----------
- (void)disconnect {
[self.socket disconnect];
}
設(shè)置 自動(dòng)重連
#pragma mark-----設(shè)置自動(dòng)重連-----------
-(void)setTYSocketAutoConnect:(NSTimeInterval)timeInterval{
if (!_isConnected) {
[self connect];
}
_isAutoConnect = YES;
_timeInterval = timeInterval;
}
然后在連接斷開(kāi)的代理里進(jìn)行重連
-(void)websocketDidDisconnect:(JFRWebSocket*)socket error:(NSError*)error{
_isConnected = NO;
if ([self.delegate respondsToSelector:@selector(socketDidDisconnect:error:)]) {
[self.delegate socketDidDisconnect:self error:error];
}
if (_isAutoConnect) {
[_timer invalidate];
_timer = [NSTimer scheduledTimerWithTimeInterval:_timeInterval target:self selector:@selector(connect) userInfo:nil repeats:YES];
[_timer fire];[self connect];
}
}
接下來(lái)是發(fā)送消息的方法 ( JFRWebSocket提供了發(fā)送字符串與發(fā)送二進(jìn)制流的方法 本文中因?yàn)闃I(yè)務(wù)關(guān)系 封裝了一個(gè)消息類(lèi)用于通信? ) 為了方便我們得到發(fā)送之后的反饋 這里用了一個(gè)block???
聲明一個(gè)block
@property (nonatomic, copy) void (^sendBack)();
發(fā)送方法
#pragma mark-----Message發(fā)送消息-----------
- (void)sendMessage:(Message *)message callBack:(void (^)(NSString* string))callBack{
if (callBack) {
self.sendBack = ^(NSString *string){
callBack(string);
};
}
if (self.socket.isConnected) {
NSDictionary *dict = [message getDictionaryFromMessage:message];
NSLog(@"發(fā)送消息%@", dict);
NSData *data = [NSJSONSerialization dataWithJSONObject:dict options:NSJSONWritingPrettyPrinted error:nil];
[self.socket writeData:data];
}
}
}
然后在JFRWebSocket 收消息的代理里 調(diào)用callBack
-(void)websocket:(JFRWebSocket*)socket didReceiveData:(NSData*)data {NSDictionary *dictionary = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:nil];
if (dictionary) {
Message *messageObject = [[Message alloc]init];
[messageObject setValuesForKeysWithDictionary:dictionary];
//這此處判斷消息類(lèi)型來(lái)進(jìn)行不同操作 本文只舉一個(gè)栗子
if ([messageObject.type isEqualToString:@"SystemMsgOrder"]) {
if ([self.delegate respondsToSelector:@selector(socket:didReceiveMessage:)]) {
[self.delegate socket:self didReceiveOrderMessage:messageObject];
}
}
}else{
NSString *str = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];//本文后臺(tái)返回的消息是字符串形式
if ([str hasPrefix:@"sendback"]) {//判斷是發(fā)送回調(diào)
if (self.sendBack) {
self.sendBack(str);
}
}
}
}
到此完成了基本業(yè)務(wù)封裝。如有問(wèn)題歡迎交流