最新公司的項目比較趕,國慶期間也在趕項目。很久沒有發(fā)表新的動態(tài)了。由于公司要求一定要使用阿里百川的即時通訊,一起分享下經(jīng)驗。下周再分享環(huán)信SDK

一.即時通訊簡介
1.1 XMPP簡介
-
XMPP一個即時通訊的協(xié)議,它規(guī)范了用于即時通信在網(wǎng)絡(luò)上數(shù)據(jù)傳輸格式的,比如登錄,獲取好友列表等等的格式,XMPP在網(wǎng)絡(luò)傳輸?shù)臄?shù)據(jù)是XML格式 -
XMPP是一個基于Socket通過的網(wǎng)絡(luò)協(xié)議,目的就是為了保護(hù)長連接,以實現(xiàn)即時通訊功能 -
XMPP的客戶端是使用一個XMPPFramework框架實現(xiàn) -
XMPP的服務(wù)器是使用Openfire,一個開源的服務(wù)器
1.2 第三方即時通訊SDK
- 不需要公司內(nèi)部搭建服務(wù)器
- 可使公司可以節(jié)約時間成本
- 客戶端的開發(fā),使用第三方SDK比XMPPFramework更簡潔方便
- 是在
XMPP的基礎(chǔ)上進(jìn)行二次開發(fā),對服務(wù)器Openfire和客戶端進(jìn)行功能模型的添加和客戶端SDK的封裝,本質(zhì)還是使用XMPP,基于Socket的網(wǎng)絡(luò)通信 - 內(nèi)部實現(xiàn)了數(shù)據(jù)緩存,會把聊天記錄添加到數(shù)據(jù)庫,把附件(如音頻文件,圖片文件)下載到本地,使程序員更多時間是花到用戶即時體驗上
只要你使用第三方的即時通訊,無論你是使用環(huán)信還是融云還是阿里的,首先第一步就是集成,集成千篇一律,對著官方文檔完成集成即可,集成問題則不再細(xì)說
二.阿里百川SDK準(zhǔn)備工作
2.1 注冊賬號
2.2 根據(jù)build id創(chuàng)建應(yīng)用,集成的時候需要替換阿里AppKey值

三. 集成與核心功能(主要針對單聊)
1 集成阿里百川即時通訊SDK集成
2 查看示例demo并熟悉阿里百川的示例demo下載
3 讓示例demo變成你的東西,根據(jù)項目需求,對其進(jìn)行增刪改減。把
SPKitExample類名改成SPKitManager這樣意思更明確,再者把SPKitExample類里面所有的example全部清除
整理好之后剩下如下文件

四. 步驟具體化
1.初始化IMSDK
在AppDelegate中導(dǎo)入#import "SPKitManager.h"頭文件,并在didFinishLaunchingWithOptions方法中初始化IMSDK
[[SPKitManager sharedInstance] callThisInDidFinishLaunching];
2.設(shè)置SPKitManager
首先在SPKitManager.h添加一個block塊來檢查登錄狀態(tài)
-(void)checkLoginRun:(void(^)())callback;
其次在SPKitManager.m聲明一個BOOL屬性判斷用戶是否登錄,并實現(xiàn)checkLoginRun方法,為了保護(hù)用戶賬號密碼的安全性,我們對用戶的賬號密碼進(jìn)行MD5加密處理。XXXX一般是以項目名稱做其前綴進(jìn)行加密,不過具體還是得看公司要求。
@property(nonatomic)BOOL isLogined;
-(void)checkLoginRun:(void(^)())callback{
[self login:callback];
}
-(void)login:(void(^)())callback{
if(self.isLogined){
if (callback) {
callback();
}
}else{
@synchronized(self){
if(self.isLogined) {
if (callback) {
callback();
}
return;
}
YISUserModel<Optional>* user = [YISUserManager shareInstance].user.user;
if(user == nil || user.id == nil){return;}
NSString *uid = [YISTools MD5String: user.id];
NSString *pwd = [YISTools MD5String:[NSString stringWithFormat:@"XXXX%@",user.id]];
[self callThisAfterISVAccountLoginSuccessWithYWLoginId:uid passWord:pwd preloginedBlock:^{}
successBlock:^{
self.isLogined = YES;
if (callback) {
callback();
} } failedBlock:^(NSError *aError) {
DDLogInfo(@"aError:%@",aError);
}]; }
}
}
3.創(chuàng)建會話列表
- 3.1導(dǎo)入頭文件3個
#import <WXOUIModule/YWConversationListViewController.h>
#import "SPKitManager.h"
#import <WXOpenIMSDKFMWK/YWConversation.h>
- 3.2聲明屬性
@property(nonatomic, strong) SPKitManager* spkit;//聊天Manager
@property (weak, nonatomic) IBOutlet UIView *msgListView;
@implementation YISMessageViewController{
NSString *currentId;
YWConversationListViewController *conversationListController;
}
- 3.3設(shè)置會話列表
viewDidLoad->調(diào)用[self setupIMList](判斷用戶是否登錄以及是否切換賬號等問題的處理)->[self _setupIMList](設(shè)置會話列表)
-(void)setupIMList{
BOOL isLogin = [YISUserManager shareInstance].isLogin;
if (!isLogin) {
[[NSNotificationCenter defaultCenter] postNotificationName:kLoginNotification object:nil];
return;
}
NSString *uid = [YISUserManager shareInstance].user.user.id;
if(currentId != nil && ![currentId isEqualToString: uid]){
[self.msgListView removeFromSuperview];
[conversationListController removeFromParentViewController];
DDLogDebug(@"currentId%@--userid:%@",currentId,uid);
}else if (currentId != nil){
return;
}
self.spkit = [SPKitManager sharedInstance];
[self.spkit checkLoginRun:^{
[self _setupIMList];
}];
}
-(void)_setupIMList{
conversationListController = [self.spkit.ywIMKit makeConversationListViewController];
conversationListController.view.frame = [UIScreen mainScreen].bounds;
conversationListController.view.backgroundColor =[UIColor clearColor];
__weak __typeof(conversationListController) weakConversationListController;
weakConversationListController = conversationListController;
YWConversationsListDidSelectItemBlock selectItemBlock;
selectItemBlock = ^(YWConversation *aConversation) {
if ([aConversation isKindOfClass:[YWCustomConversation class]]) {
YWCustomConversation *customConversation = (YWCustomConversation *)aConversation;
[customConversation markConversationAsRead];
}
else {
[[SPKitManager sharedInstance] openConversationViewControllerWithConversation:aConversation
fromNavigationController:weakConversationListController.navigationController];
} };
[conversationListController setDidSelectItemBlock:selectItemBlock];
[self.spkit CustomizeConversationCellWithConversationListController:conversationListController];
conversationListController.didDeleteItemBlock = ^ (YWConversation *aConversation) {};
self.msgListView = conversationListController.view;
[self.view addSubview:self.msgListView];
[self addChildViewController:conversationListController];
[self didMoveToParentViewController:conversationListController];
__weak typeof(self.navigationController) weakController = self.navigationController;
[self.spkit.ywIMKit setUnreadCountChangedBlock:^(NSInteger aCount) {
NSString *badgeValue = aCount > 0 ?[ @(aCount) stringValue] : nil;
weakController.tabBarItem.badgeValue = badgeValue;
}];
}
4.退出登錄
上面有有提到賬號切換問題,而在app退出登錄時阿里也要退出,否則會導(dǎo)致此種情況,登錄新的賬號時還殘留著上一個賬號的聊天列表。如果程序每次卸載再重新安裝不會發(fā)現(xiàn)此問題,但是沒有必要這樣,用戶體驗會及其不好。
例如:
[[YISUserManager shareInstance]logout];
[[SPKitManager sharedInstance]Logout];
額外補(bǔ)充
替換阿里的默認(rèn)頭像
WXFrameworks->WXOUIModuleResources.bundle->pub_ico_single_120@2x/pub_ico_single_120@3x