iOS消息体系架构详解-融云即时通讯云
iOS SDK 体系架构
本文档将详细介绍融云的 SDK 产品架构和消息体系,以便于您更深入的了解融云并更快速的开发自己的产品。

IMKit
IMKit 的功能主要是封装各种界面对象,服务于开发者快速实现自己的产品,主要特点是是支持快速集成,支持丰富的界面定制功能。
IMLib
IMLib 的功能是提供基本通信能力库,封装了通信能力和 Conversation,Message 等各种对象,服务于需要根据自己的产品去自己实现界面的开发者。主要特点是封装清晰,轻量,便于使用。
Protocol
Protocol 是融云的核心协议栈,使用融云自定义的私有二进制协议。主要特点是是轻量化,有序可靠,不丢消息。Protocol 部分使用 Native 语言开发,在 Android 和 iOS 平台上保证业务一致性,便于开发者商用化自己的产品。
IMLib 体系架构
首先介绍 IMLib 的体系,对于真正使用融云 SDK 的用户,不管您选择 IMLib 还是 IMKit,您都需要了解一下体系概念。

核心类
RCIMClinet 是 IMLib 的核心类,您可以直接使用它的方法,如 init,connect,setdevicetoken,sendMessage, sendImageMessage 等。您需要详细的了解所有接口的用法,请参考 API 文档。
会话实体类
RCConversation 是会话实体类,首先您需要充分的了解 Conversation(会话) 和 Message(消息) 两个实体类的关系。
会话实体类和消息实体类是用来存储本地会话和消息的容器类,除了包含会话内容和消息内容外,还包括了保存在本地的各种状态,您在客户端读取消息时,获取的对象都和这两个类相关。会话有多种类型,可以是私聊会话,也可以是群组会话等,每一个 Conversation(会话)包含多条 Message(消息),关系如下图所示:

通过 conversationType 和 targetId,可以唯一确定一个会话。ConversationType 枚举值意义和对应的 targetId 意义为:
| 会话类型枚举 ConversationType | 说明 | 对应的 targetId | 
|---|---|---|
| PRIVATE | 单聊 | 用户的 Id(userId)。 | 
| GROUP | 群组 | 群组的 Id(groupId)。 | 
| DISCUSSION | 讨论组 | 讨论组的 Id(discussionId)。 | 
| CHATROOM | 聊天室 | 聊天室的 Id(chatroomId)。 | 
| CUSTOMER_SERVICE | 客服 | 客服的 Id(customerServiceId)。 | 
| SYSTEM | 系统会话 | 系统账户 Id。可以理解为 QQ 的 10000 号的角色。 | 
| APP_PUBLIC_SERVICE | 应用公众服务 | 应用公众服务的 Id(publicServiceId)。 | 
| PUBLIC_SERVICE | 公众服务 | 公众服务的 Id(publicServiceId)。 | 
另:系统会话类型并不一定代表是“系统消息”,本质上与单聊会话类型没有区别,只是逻辑上做了不同的区分,便于展开不同的产品业务逻辑。
通过一个 conversationType 和 targetId 组合,您可以确定一个唯一的会话。如当您需要发起单聊会话时,您需要传入 ConversationType_PRIVATE 和 userId,当您需要发起群组聊天时,您需要传入 ConversationType_GROUP 和 groupId,当您需要发起讨论组会话时,您需要传入 ConversationType_DISCUSSION 和 discussionId。
消息实体类
RCMessage 是消息实体类,消息实体类是消息类的外层容器,消息实体对象是消息对象在本地存储的外层对象,消息实体对象封装了消息的基本信息如类型、 ID、消息的方向、接收状态、接收时间、发送者等。您可能需要先了解其中两个成员参数的概念。
objectName
代表消息内容的类型,是一个标示符(Identifier),融云内置消息类型以 RC: 开头,如 RC:TxtMsg,RC:ImgMsg,RC:VcMsg 等。
content
消息类,一个 RCMessageContent 类型的对象,代表着实际的消息。
消息类
MessageContent 是消息类,他也是所有消息的基类,文本、图片等消息都继承于它,如您要自定义消息,也要继承它实现。
消息类不同于消息实体类(RCMessage),消息类代表一条具体的消息内容,消息实体类是消息类的外层容器,消息实体对象是消息对象在本地存储的外层对象,消息实体对象除了包含消息对象外,还包括消息的方向、接收状态、接收时间、发送者等。
每一条消息内容都一个标示符(Identifier),用来标识自己的类型,该标示符必须唯一。消息内容类的重要函数是 encode ,每一个消息都需要实现自己的 encode 方法来封装消息内容。
当前版本的消息分两种,普通的内容类消息,和通知类消息,接下来将分别仔细介绍。
| 消息分类 | 消息行为状态标识 | 
|---|---|
| 内容类消息 | 表示一个用户间发送的包含具体内容的消息,需要展现在聊天界面上,如文字消息、语音消息等。 | 
| 通知类消息 | 表示一个通知信息,可能展现在聊天界面上,如提示条通知。 | 
内置内容类消息
文字消息类
RCTextMessage。用来发送文字类消息,其中可以包括超链接,会自动识别。继承自RCMessageContent,是一个普通内容类消息。
消息类名:RCTextMessage
消息 ObjectName:RC:TxtMsg
消息状态行为标识:MessageTag.ISPERSISTED | MessageTag.ISCOUNTED
消息的结构:{"content":"Hello world!","extra":""}
其中 content 为文字消息的文字内容,extra 可以放置任意的数据内容,也可以去掉此属性。
语音消息类
RCVoiceMessage。用来发送语音片段消息,其中可以包括超链接,会自动识别。
消息类名:RCVoiceMessage
消息 ObjectName:RC:VcMsg
消息状态行为标识:MessageTag.ISPERSISTED | MessageTag.ISCOUNTED
消息的结构:{"content":"bhZPzJXimRwrtvc=","duration":7,"extra":""}
其中 content 为语音消息录制转码成 AMR 格式后,进行 Base64 编码的结果值,duration 为语音消息的时长(单位:秒),extra 可以放置任意的数据内容,也可以去掉此属性。
图片消息类
RCImageMessage。用来发送图片类消息。
消息类名:RCImageMessage
消息 ObjectName:RC:ImgMsg
消息状态行为标识:MessageTag.ISPERSISTED | MessageTag.ISCOUNTED
消息的结构:{"content":"bhZPzJXimRwrtvc=","imageUri":"http://p1.cdn.com/fds78ruhi.jpg","extra":""}
图片消息包括两个主要部分:缩略图和大图,缩略图直接 Base64 编码后放入 content 中,大图首先上传到文件服务器(融云 SDK 中默认上传到七牛云存储),然后将云存储上的大图地址放入消息体中。流程示意如下:
其中 content 为图片内容进行 Base64 编码的结果值,imageUri 为图片上传到图片存储服务器后的地址,extra 可以放置任意的数据内容,也可以去掉此属性。
缩略图尺寸为:240 x 240 像素,以宽度和高度中较长的边不超过 240 像素等比压缩。
大图尺寸为:960 x 960 像素,以宽度和高度中较长的边不超过 960 像素等比压缩。
图文消息类
RCRichContentMessage。用来发送图文消息,包含一个标题,一段文字内容和一张图片。
消息类名:RCRichContentMessage
消息 ObjectName:RC:ImgTextMsg
消息状态行为标识:MessageTag.ISPERSISTED | MessageTag.ISCOUNTED
消息的结构: {"title":"Big News","content":"I'm Ironman.","imageUri":"http://p1.cdn.com/fds78ruhi.jpg","url":"http://www.rongcloud.cn","extra":""}
其中 title 为消息的标题,content 为消息的文字内容,imageUri 为图片的地址,url 为跳转的地址,extra 可以放置任意的数据内容,也可以去掉此属性。
图片尺寸为:120 x 120 像素。
地理位置消息类
RCLocationMessage。用来发送地理位置消息。
消息类名:RCLocationMessage
消息 ObjectName:RC:LBSMsg
消息状态行为标识:MessageTag.ISPERSISTED | MessageTag.ISCOUNTED
消息的结构:{"content":"bhZPzJXimRwrtvc=","latitude":39.9139,"longitude":116.3917,"poi":"北京市朝阳区北苑路北辰泰岳大厦","extra":""}
其中 content 为地图缩略图内容进行 Base64 编码的结果值,latitude 为位置的纬度值,longitude 为位置的经度值,poi 为位置兴趣点名称,extra 可以放置任意的数据内容,也可以去掉此属性。
文件消息
消息类名:RCFileMessage
消息 ObjectName:RC:FileMsg
消息状态行为标识:MessageTag.ISPERSISTED | MessageTag.ISCOUNTED
消息的结构:{"name”:”a.txt","size":190184,"type":"txt","fileUrl":"http://rongcloud-image.ronghub.com/text_plain_242002?e=2147483647"}
其中 name 为文件名,size 为文件大小,type 为文件类型,fileUrl 为文件地址,extra 可以放置任意的数据内容,也可以去掉此属性。
内置通知类消息
提示条(小灰条)通知消息
RCInformationNotificationMessage。用来发送在聊天会话页面显示的提示条(小灰条)通知。
消息类名:RCInformationNotificationMessage
消息 ObjectName:RC:InfoNtf
消息状态行为标识:MessageTag.ISPERSISTED
消息的结构:{"message":"请在聊天中注意人身财产安全",extra:""}
其中 message 为提示条消息内容,extra 可以放置任意的数据内容,也可以去掉此属性。
联系人(好友)通知消息
RCContactNotificationMessage。用来发送联系人操作(加好友等)的通知消息。
消息类名:RCContactNotificationMessage
消息 ObjectName:RC:ContactNtf
消息状态行为标识:MessageTag.ISPERSISTED
消息的结构:{"operation":"Request","sourceUserId":"123","targetUserId":"456","message":"我是小艾,能加一下好友吗?","extra":""}
其中 operation 为联系人操作的指令,sourceUserId 为发出通知的用户 Id,targetUserId 为接收通知的用户 Id,message 为通知附带的消息内容,extra 可以放置任意的数据内容,也可以去掉此属性。
官方针对 operation 属性定义了 "Request", "AcceptResponse", "RejectResponse" 几个常量,也可以由开发者自行扩展。
资料通知消息
RCProfileNotificationMessage。用来发送用户资料变更通知消息。
消息类名:RCProfileNotificationMessage
消息 ObjectName:RC:ProfileNtf
消息状态行为标识:MessageTag.ISPERSISTED
消息的结构:{"operation":"Update","data":"{\"nickname\":\"韩梅梅\", \"hometown\":\"beijing\"}","extra":""}
其中 operation 为资料通知操作,可以自行定义,data 为操作的数据,extra 可以放置任意的数据内容,也可以去掉此属性。
通用命令通知消息
RCCommandNotificationMessage。用来发送通用的指令通知消息,消息内可以定义任意 JSON 内容。
消息类名:RCCommandNotificationMessage
消息 ObjectName:RC:CmdNtf
消息状态行为标识:MessageTag.ISPERSISTED
消息的结构:{"name":"AtPerson","data":"{\"sourceId\":\"9527\"}"}
其中 name 为命令名称,可以自行定义,data 为命令的内容。
群组通知消息
用来发送群组操作的通知消息。
消息类名:RCGroupNotificationMessage
消息 ObjectName:RC:GrpNtf
消息状态行为标识:MessageTag.ISPERSISTED
消息的结构:{"operatorUserId":"4324","operation":"Rename","data":"本地生活","message":"修改本群名为本地生活","extra":""}
其中 operatorUserId 为操作人用户 Id,operation 为操作名,data 为操作数据如:目标用户 Id 或修改后群名称,详细可参见内置消息类型说明,message 为消息内容,extra 可以放置任意的数据内容,也可以去掉此属性。
讨论组通知消息
用来发送讨论组操作的通知消息。
消息类名:RCDiscussionNotificationMessage
消息 ObjectName:RC:DizNtf
消息状态行为标识:MessageTag.ISPERSISTED
消息的结构:{"type":1,"extension":"3213,4332","operator":"5435"}
其中 type 为讨论组操作类型 1:加入讨论组 2:退出讨论组 3:讨论组改名 4:讨论组管理员踢人,extension 为被加入讨论组用户 Id,多个用户 Id 以逗号分割,operator 为当前操作用户 Id。
命令消息
RCCommandMessage。用来发送通用的指令通知消息,消息内可以定义任意 JSON 内容,与通用命令通知消息的区别是不存储、不计数。
消息类名:RCCommandMessage
消息 ObjectName:RC:CmdMsg
消息的结构:{"name":"AtPerson","data":"{\"sourceId\":\"9527\"}"}
其中 name 为命令名称,可以自行定义,data 为命令的内容。
内置状态类消息
对方正在输入状态消息
用来发送对方正在输入时的状态消息,不存储、不计数。
消息 ObjectName:RC:TypSts
消息的结构:{"typingContentType":"RC:TxtMsg"}
typingContentType 为正在输入消息类型。
IMKit 体系架构
IMKit界面组件是融云产品的核心特色,开发者使用 IMKit,不需要从头开发自己的界面,只需要通过简短的代码即可集成到您的 App 产品中。会话列表、聊天窗口、消息内容选择、表情库、好友选择、会话设置这些最复杂的功能,融云 IMKit 已经替您完成。您在启动聊天会话列表之后,所有的界面融云已经替您完成。
对于进一步有丰富自定义需求的用户,融云IMkit支持会话列表、聊天窗口、输入框、消息内容的自定义,你可以通过继承和重写界面的方法完成自己独特的界面。

IMKit主要有两个界面,会话列表( Conversation List )和会话( Conversation ),在融云IMKit的实现中,前者是一个 UITableView,后者是一个 UICollectionView。
在会话界面中,其中的每一条消息是一个 UICollectionViewCell,支持自动布局。目前融云替开发者实现了五种普通内容的消息的界面展现:文本,图像,语音,图文,位置,相关接口也全部开放,您可以使用也可以继承 RCMessageCell 自定义自己的消息展现。
RCConversationModel 是会话模型,包含了每一条具体会话的数据;RCMessageModel 是消息模型,包含了每一条具体消息的数据,开放给 App 根据自己的需求访问和使用。
RCConversationListViewController 和 RCConversationViewController 都继承于 RCBaseViewController,您可以继承他们并实现自己的自定义会话列表。
iOS消息体系架构详解-融云即时通讯云的更多相关文章
- HDFS追本溯源:体系架构详解
		
Hadoop是一个开发和运行处理大规模数据的软件平台,是Apache的一个用Java语言实现开源软件框架,实现在大量计算机组成的集群中对海量数据进行分布式计算.用户可以在不了解分布式底层细节的情况下, ...
 - Android体系架构详解
		
Andriod是什么? 首先,就像Android开源和兼容性技术负责人Dan Morrill在Android开发手册兼容性部分所解释的,“Android并不是传统的Linux风格的一个规范或分发版本, ...
 - iOS的消息转发机制详解
		
iOS开发过程中,有一类的错误会经常遇到,就是找不到所调用的方法,当然这类问题比较好解决,给当前对象或其父类对象添加该方法即可,使得编译器在编译时能正确找到该方法:或者,还有另外的方法,由于Objec ...
 - Android高效率编码-第三方SDK详解系列(二)——Bmob后端云开发,实现登录注册,更改资料,修改密码,邮箱验证,上传,下载,推送消息,缩略图加载等功能
		
Android高效率编码-第三方SDK详解系列(二)--Bmob后端云开发,实现登录注册,更改资料,修改密码,邮箱验证,上传,下载,推送消息,缩略图加载等功能 我的本意是第二篇写Mob的shareSD ...
 - Hyperledger Fabric架构详解
		
区块链开源实现HYPERLEDGER FABRIC架构详解 区块链开源实现HYPERLEDGER FABRIC架构详解 2018年5月26日 陶辉 Comments 10 Comments hyper ...
 - IOS—UITextFiled控件详解
		
IOS—UITextFiled控件详解 //初始化textfield并设置位置及大小 UITextField *text = [[UITextField alloc]initWithFrame:CGR ...
 - iOS开发融云即时通讯集成详细步骤
		
1.融云即时通讯iOS SDK下载地址 http://rongcloud.cn/downloads 选择iOS SDK下载 2.进行应用开发之前,需要先在融云开发者平台创建应用,如果您已经注 ...
 - iOS中—触摸事件详解及使用
		
iOS中--触摸事件详解及使用 (一)初识 要想学好触摸事件,这第一部分的基础理论是必须要学会的,希望大家可以耐心看完. 1.基本概念: 触摸事件 是iOS事件中的一种事件类型,在iOS中按照事件划分 ...
 - NopCommerce源码架构详解--初识高性能的开源商城系统cms
		
很多人都说通过阅读.学习大神们高质量的代码是提高自己技术能力最快的方式之一.我觉得通过阅读NopCommerce的源码,可以从中学习很多企业系统.软件开发的规范和一些新的技术.技巧,可以快速地提高我们 ...
 
随机推荐
- 《精通Spring4.X企业应用开发实战》读后感第四章
 - 基于Go实现的秒杀系统
			
这是基于Go语言的一个秒杀系统,这个系统分三层,接入层.逻辑层.管理层.项目源码:https://github.com/BlueSimle/SecKill 系统架构图 秒杀接入层 从Etcd中加载秒杀 ...
 - 使用Postman测试请求
			
Postman是什么 在开发或者调试网络程序或者是网页B/S模式的程序的时候,需要一些方法来跟踪网页请求,用户可以使用一些网络的监视工具比如著名的Firebug等网页调试工具. 网页调试工具Postm ...
 - 小议Python3的原生协程机制
			
此文已由作者张耕源授权网易云社区发布. 欢迎访问网易云社区,了解更多网易技术产品运营经验. 在最近发布的 Python 3.5 版本中,官方正式引入了 async/await关键字.在 asyncio ...
 - 将Date转换成 yyyy-MM-dd 格式的字符串
			
// 方法1 原型Date.prototype.format = function (format) { var o = { "M+": this.getMon ...
 - Unity surface shader 2
			
UV滚动 Shader "Nafio/ScrollUV" { Properties { _Tex("T",2D) = "white" {} ...
 - UOJ #32. 【UR #2】跳蚤公路【Floydbellman-ford】
			
首先看这个范围很夸张但是其实有限制的也就在1e18*n范围里(走完一圈的边权),然后限制一定是有负环 用Floyd传递闭包,然后设f[i][j][k]为从1走了i步到j并且有k个x的最短路,用B-F处 ...
 - nodejs 从helloworld到高质量的后台服务server的一点思考
			
---恢复内容开始--- 新公司用的nodejs作为app和网站的后台服务server,所以最近对nodejs一直在学习,加上之前简单的学习了一点,看了两天后台接口源码,所以就直接上手干活了,下面是我 ...
 - JAVA之动态编译
			
通过Java动态生成class文件 今天说下JAVA中的动态编译,这个功能根据我现在的了解好像没有见到过用的,我Jio的吧,现在的一些在线代码编缉器可以用到了,这个具体我也不是很清楚.感兴趣的大家可以 ...
 - 教程 | Linux常用命令大全
			
Linux常用命令 目录操作命令 ls 命令名称:ls 命令英文原意:list 命令所在路径:/bin/ls 执行权限:所有用户 功能描述:显示目录文件 ls (显示当前目录下文件) ls 目录名 ( ...