消息发送

更新时间: 2023/09/12 07:04:31

功能概述

SDK 中用于表示消息的结构为NIMMessage。消息属于云信即时通讯中最关键最重要的类,它是传递消息的基本模型。

消息接收、语音消息处理等相关说明请查看消息接收

部分重要属性列表:

参数 类型 说明
messageType 消息类型 消息的类型枚举,只读。当构造消息的时候,SDK 会根据传入的 messageObject 自动判断并填入消息类型
messageSubType 消息自定义子类型 默认为0。当需要自定义消息的子类型时,需要设置此项。本地消息检索时,可以通过设置NIMMessageSearchOption的messageSubTypes来查找指定的子类型
from 消息的发送者 为发送者 Id 。当发送消息的时候,SDK 会根据当前登录情况自动填写
session 消息的所属会话 为消息发送到对话的 Id 。当发送的是点对点消息时,此 Id 为接受者 Id;当发送的是群或聊天室消息时,此 Id 为群或聊天室 Id 。
messageId 消息客户端 Id 消息的唯一标识,在消息对象初始化后自动生成
serverID 消息服务端 Id 消息发送成功后在服务端生成
text 消息文本 用来做 UI 显示的消息文本,通常情况下,除了文本消息和提醒消息 外,其他消息 text 字段都为 nil
messageObject 消息附件对象 开发者需要重点关心的属性,附件需要实现 NIMMessageObject 协议。 开发者通过注入不同的消息附件使消息变为不同类型,并附上不同消息类型所需要的信息,如图片数据,地理位置等
rawAttachment 消息附件的字符串内容 其属性是只读
setting 消息设置 开发者通过在发送消息前注入一个消息设置对象,可以制定当前消息的各种设置,如是否需要计入未读,是否需要多端同步等
antiSpamOption 反垃圾选项 目前仅支持易盾,只有接入了易盾才可以设置这个配置
apnsContent 推送文案 APNs 推送文案,设置后,手机在后台将会收到相关文案的苹果推送
apnsPayload 消息推送 Payload 可以通过这个字段定义消息推送 Payload , 苹果内置字段目前只支持 sound 字段
apnsContent 推送文案 APNs 推送文案,设置后,手机在后台将会收到相关文案的苹果推送
apnsMemberOption 指定成员推送选项 开发者通过在发送消息前注入这个设置对象,可以进行一些更复杂的推送设定,比如强制推送,部分推送等。目前只能在群会话中使用
remoteExt 服务器扩展 客户端在发送消息前,可以设置这个字段,这个字段将在本地存储且发送至对端,上层需要保证 NSDictionary 可以转换为 JSON
localExt 客户端扩展 客户端可以设置这个字段,这个字段只在本地存储,不会发送至对端,上层需要保证 NSDictionary 可以转换为 JSON。如果在消息发送后设置,需要手动调用存储消息到本地的方法。
messageExt 消息拓展字段 服务器下发的消息拓展字段,不在本地做持久化,目前只有聊天室中的消息才有该字段 (NIMMessageChatroomExtension) 。
timestamp 消息发送时间 本地存储消息可以通过修改时间戳来调整其在会话列表中的位置,发完服务器的消息时间戳将被服务器自动修正。
yidunAntiSpamExt 易盾反垃圾扩展字段 透传给易盾的反垃圾增强版的检测参数,具体请参见易盾的反垃圾增强版用户可扩展参数,格式为json,长度限制1024 反作弊相关的email、phone、token、extension,抄送到yidunAntiCheating。其他用户增值信息,抄送到yidunAntiSpamExt。
yidunAntiCheating 易盾反作弊字段 透传给易盾的反作弊检测参数,格式为json,长度限制1024 ,具体请参见文本防刷版开发文档反作弊相关的email、phone、token、extension,抄送到yidunAntiCheating。其他用户增值信息,抄送到yidunAntiSpamExt。
yidunAntiSpamRes 易盾反垃圾结果 易盾反垃圾触发时返回的结果字段
locationX X坐标 X坐标,仅用于聊天室
locationY Y坐标 Y坐标,仅用于聊天室
locationZ Z坐标 Z坐标,仅用于聊天室
toAccIds 消息接受者列表 消息接受者列表,仅用于聊天室
isReceivedMsg 是否是收到的消息 由于有漫游消息的概念,所以自己发出的消息漫游下来后仍旧是"收到的消息",这个字段用于消息出错是时判断需要重发还是重收。
deliveryState 消息投递状态 仅针对发送的消息,这个字段才有效。默认是发送失败的状态,仅作参考;准确实时的消息状态,建议以后根据消息发送完成的回调来重新从本地数据库取消息记录用来展示。或者根据消息发送的生命周期(将要发送,发送完成等回调),自己在消息的扩展字段定义消息的发送状态,再通过 UI 展示
attachmentDownloadState 消息附件下载状态 仅针对收到的消息,这个字段才有效。
isOutgoingMsg 是否是往外发的消息 由于能对自己发消息,所以并不是所有来源是自己的消息都是往外发的消息,这个字段用于判断头像排版位置(是左还是右)。
isPlayed 消息是否被播放过 修改这个属性,SDK 会自动更新 db 中对应的数据。
isDeleted 消息是否标记为已删除 删除消息在本地存储时只会标记删除状态,已删除的消息在获取本地消息列表时会被过滤掉,只有根据 messageId 获取消息的接口可能会返回已删除消息。
isRemoteRead 对端是否已读 只有当当前消息为 P2P 消息且 isOutgoingMsg 为 YES 时这个字段才有效,需要对端调用过发送已读回执的接口。
senderName 消息发送者名字 当发送者是自己时,这个值可能为空,这个值表示的是发送者当前的昵称,而不是发送消息时的昵称。聊天室消息里,此字段无效。
senderClientType 发送者客户端类型 发送者当时所处的客户端种类,种类可能随着 SDK 版本更新增加,上层开发者需考虑新老版本带来的兼容问题。

上述消息的状态属性,推荐只在主线程对这些属性进行读写

目前提供如下几种消息类型,不同的消息类型对应不同的 MessageObject:

消息类型 MessageObject
文本消息 nil
图片消息 NIMImageObject
音频消息 NIMAudioObject
视频消息 NIMVideoObject
文件消息 NIMFileObject
位置消息 NIMLocationObject
通知消息 NIMNotificationObject
提醒消息 NIMTipObject
自定义消息 NIMCustomObject

yidunAntiSpamRes字段说明

yidunAntiSpamRes为json字符串格式,请自行解析或者反转成json对象使用,yidunAntiSpamRes字段定义如下:

名称类型说明
code Integer状态码:200,正常;404,易盾反垃圾结果为空,无其它字段;414,易盾反垃圾结果过长,无ext字段
type String易盾反垃圾类型:text,文本;image,图片
version String易盾反垃圾的version字段,详细请参考易盾文档
taskId String易盾反垃圾的taskId字段,详细请参考易盾文档
suggestion Integer易盾反垃圾的suggestion字段,详细请参考易盾文档
status Integer易盾反垃圾的status字段,详细请参考易盾文档
ext String易盾反垃圾的result字段,详细请参考易盾文档

易盾反垃圾

2021年9月28日前接入安全通的客户,需要升级到最新版安全通,才可使用此接口能力。升级安全通请联系商务经理

易盾反垃圾文档:

文本类反垃圾参考:
https://support.dun.163.com/documents/588434200783982592?docId=589310433773625344

图片类反垃圾参考:
https://support.dun.163.com/documents/588434277524447232?docId=588512292354793472

备注:考虑到易盾反垃圾相关字段后续的扩展性(一般为新增属性),请注意做好解析兼容

消息发送

开发者需要通过 NIMSDK 里的 NIMChatManager 协议进行消息发送。

一秒内默认最多调用该接口100次。如需上调上限,请在官网首页通过微信、在线消息或电话等方式咨询商务人员。

原型

objc@protocol NIMChatManager <NSObject>
/**
 *  发送消息
 *
 *  @param message 消息
 *  @param session 接受方会话
 *  @param error   错误 如果在准备发送消息阶段发生错误,这个error会被填充相应的信息
 *
 *  @return 发送完成后的回调,这里的回调完成只表示当前这个函数调用完成,需要后续的发送消息完成回调 – sendMessage:didCompleteWithError: 才能判断消息是否已经发送至服务器
 */
- (BOOL)sendMessage:(NIMMessage *)message
          toSession:(NIMSession *)session
              error:(NSError * __nullable *)error;
@end

关于会话NIMSession的具体信息,请参见最近会话章节。

此外,针对大文件还提供异步发送消息的方法:

objc@protocol NIMChatManager <NSObject>
/**
 *  异步发送消息,通常用于发送大文件
 *
 *  @param message 消息
 *  @param session 接收方
 *  @param completion 发送完成后的回调,这里的回调完成只表示当前这个函数调用完成,需要后续的发送消息完成回调 – sendMessage:didCompleteWithError: 才能判断消息是否已经发送至服务器
 */
- (void)sendMessage:(NIMMessage *)message
          toSession:(NIMSession *)session
         completion:(nullable void(^)(NSError * __nullable error))completion;    
@end

属性列表

参数 类型 说明
message NIMMessage 需要发送的消息,开发者构造出 message 后,需要选择构造对应的 messageObject 注入 (文本消息直接填入 text 即可,无须消息附件注入),即可传入此接口进行发送
session NIMSession 需要发送到的会话
error NSError * 开发者需要自己构造出一个 NSError 对象,并将对象引用传入。如果在准备发送消息阶段发生错误,这个对象会被填充相应的信息。通常为参数检查错误或者登录状态错误,可参考错误码说明定位具体的出错类型
completion void(^)(NSError *error) 该回调完成只代表接口调用成功

开发者需要通过 NIMChatManagerDelegate 协议进行消息发送结果的监听:

objc@protocol NIMChatManagerDelegate <NSObject>
/**
 *  发送消息完成回调
 *
 *  @param message 所发送的消息
 *  @param error 失败原因,如果发送成功则error为nil
 */
- (void)sendMessage:(NIMMessage *)message 
  didCompleteWithError:(nullable NSError *)error; 
@end

此外,开发者可以在以下回调里获取 消息发送的进度:

objc@protocol NIMChatManagerDelegate <NSObject>
/**
 *  发送消息进度回调
 *
 *  @param message 所发送的消息
 *  @param progress 进度
 */
- (void)sendMessage:(NIMMessage *)message 
           progress:(float)progress;
@end

文本消息发送

以发送一条文本消息 hello 至好友 Id 为 user的业务场景进行示例:

objc// 构造出具体会话:P2P单聊,对方账号为user
NIMSession *session = [NIMSession session:@"user" type:NIMSessionTypeP2P];
// 构造出具体消息
NIMMessage *message = [[NIMMessage alloc] init];
message.text        = @"hello";
// 错误反馈对象
NSError *error = nil;
// 发送消息
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];

图片消息发送

图片附件NIMImageObject参数列表

参数 类型 说明
path NSString 图片本地路径
thumbPath NSString 缩略图本地路径,缩略图在默认情况下由 SDK 自动下载,如果发现本地不存在缩略图,可手动调用 NIMChatManager 协议中的获取缩略图方法 fetchMessageAttachment:error: 进行下载
url NSString 大图的远程 URL 路径,开发者可通过这个属性自行下载大图
thumbUrl NSString 缩略图远程 URL 路径,仅适用于使用云信上传服务进行上传的资源,否则无效
size NSString 图片尺寸
option NIMImageOption 图片的压缩选项仅在发送时且通过 initWithImage: 方式初始化才有效
fileLength NSString 文件大小
md5 NSString 图片MD5

NIMImageOption 图片选项参数列表

参数 类型 说明
compressQuality float 压缩参数默认为 0 ,可传入 0.0 - 1.0 的值,如果值为 0 或者不合法参数时按照 0.5 进行压缩
format NIMImageFormat 图片压缩格式,可选 JPEG 和 PNG 两种。默认为 JPEG

普通图片附件初始化提供三种方式:

  • 以 UIImage 对象初始化
objc@interface NIMImageObject : NSObject<NIMMessageObject>
/**
 *  图片实例对象初始化方法
 *
 *  @param image 要发送的图片
 *
 *  @return 图片实例对象
 */
- (instancetype)initWithImage:(UIImage*)image;

/**
*  图片实例对象初始化方法
*
*  @param image 要发送的图片
*  @param scene 场景类别
*
*  @return 图片实例对象
*/
- (instancetype)initWithImage:(UIImage*)image scene:(NSString *)scene;
@end

示例:

objc// 构造出具体会话
NIMSession *session = [NIMSession session:@"user" type:NIMSessionTypeP2P];
// 获得图片附件对象
NIMImageObject *object = [[NIMImageObject alloc] initWithImage:image];
// 构造出具体消息并注入附件
NIMMessage *message = [[NIMMessage alloc] init];
message.messageObject = object;
// 错误反馈对象
NSError *error = nil;
// 发送消息
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];
  • 以图片路径初始化
objc@interface NIMImageObject : NSObject<NIMMessageObject>
/**
 *  图片实例对象初始化方法
 *
 *  @param filepath 要发送的图片路径
 *
 *  @return 图片实例对象
 */
 - (instancetype)initWithFilepath:(NSString *)filepath;
 
 /**
 *  图片实例对象初始化方法
 *
 *  @param filepath 要发送的图片路径
 *  @param scene 场景类别
 *
 *  @discussion 使用此方法上传是不做压缩转换的原图上传。iOS 11 苹果采用了新的图片格式 HEIC ,如果采用原图会导致其他设备的兼容问题,请开发者在上层做好格式的兼容转换。
 *
 *  @return 图片实例对象
 */
 - (instancetype)initWithFilepath:(NSString *)filepath scene:(NSString *)scene;
 @end

示例:

objc// 构造出具体会话
NIMSession *session = [NIMSession session:@"user" type:NIMSessionTypeP2P];
// 获得图片附件对象
NIMImageObject *object = [[NIMImageObject alloc] initWithFilepath:path];
// 构造出具体消息并注入附件
NIMMessage *message = [[NIMMessage alloc] init];
message.messageObject = object;
// 错误反馈对象
NSError *error = nil;
// 发送消息
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];
  • 以图片数据初始化
objc@interface NIMImageObject : NSObject<NIMMessageObject>
  /**
   *  图片实例对象初始化方法
   *
   *  @param data 图片数据
   *  @param extension 推荐使用的图片数据后缀名
   *
   *  @return 图片实例对象
   */
- (instancetype)initWithData:(NSData *)data
                   extension:(NSString *)extension;
                   
/**
*  图片实例对象初始化方法
*
*  @param data 图片数据
*  @param extension 推荐使用的图片数据后缀名
*  @param scene 场景类别
*
*  @return 图片实例对象
*/
- (instancetype)initWithData:(NSData *)data
                   extension:(NSString *)extension
                   scene:(NSString *)scene;
@end                    

示例:

objc// 构造出具体会话
NIMSession *session = [NIMSession session:@"user" type:NIMSessionTypeP2P];
// 获得图片附件对象
NIMImageObject *object = [[NIMImageObject alloc] initWithData:data extension:@"png"];
// 构造出具体消息并注入附件
NIMMessage *message = [[NIMMessage alloc] init];
message.messageObject = object;
// 错误反馈对象
NSError *error = nil;
// 发送消息
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];

若为Webp格式的图片时,需要使用下列方法初始化图片实例对象:

objc@interface NIMImageObject : NSObject<NIMMessageObject>
  /**
   *  图片实例对象初始化方法, 可用于发送Webp图片
   *  @param filepath 要发送的图片路径
   *  @param scene 场景类别
   *  @param size  图片宽高,当发送文件为Webp时须需要传入该图片尺寸大小
   *  @return 图片实例对象
   */
- (instancetype)initWithFilepath:(NSString *)
                  filepath scene:(NSString *)scene 
                            size:(CGSize)size
                   
/**
*  图片实例对象初始化方法, 可用于发送Webp图片
*  @param data 图片数据
*  @param extension 推荐使用的图片数据后缀名
*  @param scene 场景类别
*  @param size  图片宽高,当发送文件为Webp时须需要传入该图片尺寸大小
*  @return 图片实例对象
*/
- (instancetype)initWithData:(NSData *)data 
                   extension:(NSString *)extension 
                       scene:(NSString *)scene 
                        size:(CGSize)size
@end                    

语音消息发送

语音附件类NIMAudioObject参数列表

参数 类型 说明
path NSString 语音本地路径,语音在默认情况下由 SDK 自动下载,如果发现本地不存在语音文件,可手动调用 NIMChatManager 协议中的获取语音附件方法 fetchMessageAttachment:error: 进行下载
url NSString 语音的远程 URL 路径
duration NSInteger 语音时长,毫秒为单位,SDK会根据传入文件信息自动解析出音频的 duration, 开发者也可以自己计算设置这个值
md5 NSString 音频MD5
displayName NSString 文件显示名

语音附件初始化提供两种方式:

  • 以语音路径初始化
objc@interface NIMAudioObject : NSObject<NIMMessageObject>
/**
 *  语音附件初始化方法
 *
 *  @param sourcePath 语音路径
 *
 *  @return 语音实例对象
 */
 - (instancetype)initWithSourcePath:(NSString *)sourcePath;
 
 /**
 *  语音对象初始化方法
 *
 *  @param sourcePath 语音路径
 *  @param scene 场景类别
 *
 *  @return 语音实例对象
 */
 - (instancetype)initWithSourcePath:(NSString *)sourcePath scene:(NSString *)scene;
@end

示例:

objc// 构造出具体会话
NIMSession *session = [NIMSession session:@"user" type:NIMSessionTypeP2P];
// 获得语音附件对象
NIMAudioObject *object = [[NIMAudioObject alloc] initWithSourcePath:path];
// 构造出具体消息并注入附件
NIMMessage *message = [[NIMMessage alloc] init];
message.messageObject = object;
// 错误反馈对象
NSError *error = nil;
// 发送消息
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];
  • 以语音数据初始化
objc@interface NIMAudioObject : NSObject<NIMMessageObject>
/**
*  语音对象初始化方法
*
*  @param data 语音数据
*  @param extension 语音数据文件后缀名
*
*  @return 语音实例对象
*/ 
- (instancetype)initWithData:(NSData *)data
                extension:(NSString *)extension;
                
/**
*  语音对象初始化方法
*
*  @param data 语音数据
*  @param extension 语音数据文件后缀名
*  @param scene 场景类别
*
*  @return 语音实例对象
*/
- (instancetype)initWithData:(NSData *)data
                   extension:(NSString *)extension
                       scene:(NSString *)scene;
@end

示例:

objc// 构造出具体会话
NIMSession *session = [NIMSession session:@"user" type:NIMSessionTypeP2P];
// 获得语音附件对象
NIMAudioObject *audioObject = [[NIMAudioObject alloc] initWithData:data extension:@"aac"];
// 构造出具体消息并注入附件
NIMMessage *message = [[NIMMessage alloc] init];
message.messageObject = object;
// 错误反馈对象
NSError *error = nil;
// 发送消息
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];

视频消息发送

视频附件类NIMVideoObject参数列表

参数 类型 说明
displayName NSString 视频的显示名, 由开发者自行定义,供上层 UI 使用
md5 NSString 根据视频数据生成的 MD5
path NSString 视频的本地路径。
url NSString 视频的远程路径
coverUrl NSString 视频封面的远程路径,只有是上传到云信服务器上的视频才支持封面地址,否则地址无效
coverPath NSString 视频封面的本地路径。视频封面在默认情况下由 SDK 自动下载,如果发现本地不存在封面文件,可手动调用 NIMChatManager 协议中的获取封面方法 fetchMessageAttachment:error: 进行下载
coverSize CGSize 视频封面的大小,由 SDK 自行计算
duration NSInteger 视频时长,毫秒为单位, SDK 会根据传入文件信息自动解析出 duration ,但上层也可以自己设置这个值

视频消息附件初始化提供两种方式:

  • 以路径初始化
objc@interface NIMVideoObject : NSObject<NIMMessageObject>
/**
 *  视频实例对象的初始化方法
 *
 *  @param sourcePath 视频的文件路径
 *
 *  @return 视频实例对象
 */
- (instancetype)initWithSourcePath:(NSString *)sourcePath;

/**
*  视频实例对象的初始化方法
*
*  @param sourcePath 视频的文件路径
*  @param scene 场景类别
*
*  @return 视频实例对象
*/
- (instancetype)initWithSourcePath:(NSString *)sourcePath scene:(NSString *)scene;
@end 

示例:

objc// 构造出具体会话
NIMSession *session = [NIMSession session:@"user" type:NIMSessionTypeP2P];
// 获得视频附件对象
NIMVideoObject *object = [[NIMVideoObject alloc] initWithSourcePath:path];
// 构造出具体消息并注入附件
NIMMessage *message = [[NIMMessage alloc] init];
message.messageObject = object;
// 错误反馈对象
NSError *error = nil;
// 发送消息
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];
  • 以数据对象初始化
objc@interface NIMVideoObject : NSObject<NIMMessageObject>
/**
 *  视频实例对象的初始化方法
 *
 *  @param data 视频数据
 *  @param extension 视频文件后缀
 *
 *  @return 视频实例对象
 */
- (instancetype)initWithData:(NSData *)data
                extension:(NSString *)extension;
                
/**
*  视频实例对象的初始化方法
*
*  @param data 视频数据
*  @param extension 视频文件后缀
*  @param scene 场景类别
*
*  @return 视频实例对象
*/
- (instancetype)initWithData:(NSData *)data
                   extension:(NSString *)extension
                       scene:(NSString *)scene;
@end

示例:

objc// 构造出具体会话
NIMSession *session = [NIMSession session:@"user" type:NIMSessionTypeP2P];
// 获得视频附件对象
NIMVideoObject *object = [[NIMVideoObject alloc] initWithData:data extension:@"mp4"];
// 构造出具体消息并注入附件
NIMMessage *message = [[NIMMessage alloc] init];
message.messageObject = object;
// 错误反馈对象
NSError *error = nil;
// 发送消息
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];

文件消息发送

文件附件类NIMFileObject参数列表

参数 类型 说明
displayName NSString 文件的显示名, 由开发者自行定义,供上层 UI 使用
md5 NSString 根据文件数据生成的 MD5
path NSString 文件的本地路径。目前 SDK 并不提供文件下载功能,但是建议 APP 使用这个 path 作为文件的下载地址,以便后期 SDK 提供缓存清理等功能
url NSString 文件的远程路径
fileLength long long 文件的大小

文件附件初始化提供两种方式:

  • 以路径初始化
objc@interface NIMFileObject : NSObject<NIMMessageObject>
/**
 *  文件对象初始化方法(根据文件路径)
 *
 *  @param sourcePath 文件路径
 *
 *  @return 文件实例对象
 */
 - (instancetype)initWithSourcePath:(NSString *)sourcePath;
 
 /**
 *  文件对象初始化方法(根据文件路径)
 *
 *  @param sourcePath 文件路径
 *  @param scene 场景类别
 *
 *  @return 文件实例对象
 */
 - (instancetype)initWithSourcePath:(NSString *)sourcePath scene:(NSString *)scene;
@end 

示例:

objc// 构造出具体会话
NIMSession *session = [NIMSession session:@"user" type:NIMSessionTypeP2P];
// 获得文件附件对象
NIMFileObject *object = [[NIMFileObject alloc] initWithSourcePath:path];
// 构造出具体消息并注入附件
NIMMessage *message = [[NIMMessage alloc] init];
message.messageObject = object;
// 错误反馈对象
NSError *error = nil;
// 发送消息
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];
  • 以数据对象初始化
objc@interface NIMFileObject : NSObject<NIMMessageObject>
/**
 *  文件实例对象的初始化方法
 *
 *  @param data 文件数据
 *  @param extension 文件后缀
 *
 *  @return 文件实例对象
 */
- (instancetype)initWithData:(NSData *)data
                    extension:(NSString *)extension;
                    
/**
*  文件对象初始化方法(根据文件数据)
*
*  @param data 文件数据
*  @param extension 文件拓展名
*  @param scene 场景类别
*  @return 文件实例对象
*/

- (instancetype)initWithData:(NSData*)data extension:(NSString*)extension scene:(NSString *)scene;
@end

示例:

objc// 构造出具体会话
NIMSession *session = [NIMSession session:@"user" type:NIMSessionTypeP2P];
// 获得视频附件对象
NIMFileObject *audioObject = [[NIMFileObject alloc] initWithData:data extension:@"data"];
// 构造出具体消息并注入附件
NIMMessage *message = [[NIMMessage alloc] init];
message.messageObject = object;
// 错误反馈对象
NSError *error = nil;
// 发送消息
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];

位置消息发送

位置附件类NIMLocationObject参数列表参数列表

参数 类型 说明
latitude double 维度位置,由初始化时传入
longitude double 经度位置,由初始化时传入
title NSString 位置标题信息,由初始化时传入

-初始化方法原型

objc@interface NIMLocationObject : NSObject<NIMMessageObject>
/**
 *  位置实例对象初始化方法
 *
 *  @param latitude  纬度
 *  @param longitude 经度
 *  @param title   地理位置描述
 *  @return 位置实例对象
 */
- (instancetype)initWithLatitude:(double)latitude
                        longitude:(double)longitude
                            title:(nullable NSString *)title;
@end 

以发送一条位置消息, 经纬度为 (30.27415,120.15515) ,地点名为 address , 至好友 Id 为 user 的业务场景进行示例:

objc// 构造出具体会话
NIMSession *session = [NIMSession session:@"user" type:NIMSessionTypeP2P];
// 获得位置附件对象
NIMLocationObject *object = [[NIMLocationObject alloc] initWithLatitude:120.15515 longitude:30.27415 title:@"address"];
// 构造出具体消息并注入附件
NIMMessage *message = [[NIMMessage alloc] init];
message.messageObject = object;
// 错误反馈对象
NSError *error = nil;
// 发送消息
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];

提示消息发送

提示消息主要用于会话内的通知提醒,消息使用场景例如:进入会话时出现的欢迎消息,或是会话过程中命中敏感词后的提示消息等场景,当然也可以用自定义消息实现,只是相对复杂一些。

提示消息附件内部没有额外的信息字段,提示内容建议放入 NIMMessage 中的 text 字段,额外信息可以存储在 NIMMessageremoteExtlocalExt 字段中。

附件原型:

objc@interface NIMTipObject : NSObject<NIMMessageObject>
@end

以发送一条提示消息, 文案内容为 welcome , 至好友 Id 为 user 的业务场景进行示例:

objc// 构造出具体会话
NIMSession *session  = [NIMSession session:@"user" type:NIMSessionTypeP2P];
// 获得文件附件对象
NIMTipObject *object = [[NIMTipObject alloc] init];
// 构造出具体消息并注入附件
NIMMessage *message = [[NIMMessage alloc] init];
message.messageObject = object;
message.text = @"welcome";
// 错误反馈对象
NSError *error = nil;
// 发送消息
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];

自定义消息发送

序列化与发送

除了 SDK 预定义的几种消息类型外,若开发者如果想要实现更多的消息类型(如图文消息、红包消息等),不可避免地需要使用自定义消息这种类型。自定义消息附件的原型是 NIMCustomObject。SDK 只负责发送和收取由 NIMCustomObject 中 id attachment 序列化和反序列化后的字节流。

在发送端,SDK 将 encodeAttachment 后得到的字节流发送出去;在接收端,SDK 读取字节流,并通过开发者设置的反序列化对象进行解析。

NIMCustomObject 附件原型:

objc@interface NIMCustomObject : NSObject<NIMMessageObject>

/**
 *  用户自定义附件
 *  @discussion SDK负责将attachment通过encodeAttachment接口序列化后的结果进行透传
 */
@property(nullable, nonatomic, strong) id<NIMCustomAttachment>  attachment;


/**
 *  注册自定义消息解析器
 *
 *  @param decoder 自定义消息解析器
 *  @disucssion 如果用户使用自定义消息类型,就需要注册自定义消息解析器,负责将透传过来的自定义消息反序列化成上层应用可识别的对象
 */
+ (void)registerCustomDecoder:(id<NIMCustomAttachmentCoding>)decoder;

@end

参数列表

参数 类型 说明
attachment id 用户自定义的附件类封装,需要实现NIMCustomAttachment,在发送的时候将对象赋值到这个属性。SDK负责将 attachment 通过encodeAttachment 接口序列化后的结果进行透传

下面,以发送一条商品信息(含商品名与链接)消息为例,介绍自定义消息的序列化与发送流程。

  • 创建商品信息消息封装类
objc// Attachment.h
@interface Attachment : NSObject<NIMCustomAttachment>
// 商品名
@property (nonatomic,copy) NSString *goodsName;
// 商品链接
@property (nonatomic,copy) NSString *goodsURL;
@end

// Attachment.m
@implementation Attachment

// 实现 NIMCustomAttachment 的 encodeAttachment 方法
- (NSString *)encodeAttachment
{
    // 商品信息内容以字典封装
    NSDictionary *dict = @{
                            @"goodsName" :  self.goodsName,
                            @"goodsURL"  :  self.goodsURL,
                          };

    // 进一步序列化得到 content 并返回
    NSData *jsonData = [NSJSONSerialization dataWithJSONObject:dict  options:0  error:nil];
    NSString *content = nil;

    if (jsonData) {
        content = [[NSString alloc] initWithData:jsonData
                                        encoding:NSUTF8StringEncoding];
    }

    return content;
}
@end

此外,NIMCustomAttachment 还提供文件上传下载相关接口,详见API文档。

  • 将商品信息消息发送出去
objc// 构造出具体会话,以发给用户user为例
NIMSession *session  = [NIMSession session:@"user" type:NIMSessionTypeP2P];

// 构造自定义消息附件
NIMCustomObject *object = [[NIMCustomObject alloc] init];
Attachment *attachment = [[Attachment alloc] init];
object.attachment = attachment;

// 构造出具体消息并注入附件
NIMMessage *message = [[NIMMessage alloc] init];
message.messageObject = object;

// 错误反馈对象
NSError *error = nil;

// 发送消息
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];

至此,序列化与发送流程已经介绍完毕。

反序列化

从本地数据库中读取自定义消息与接收方收到自定义消息等情况下,都需要经过解析才能获取到自定义消息附件的具体内容。以上例中的商品信息为例,介绍自定义消息的反序列化流程。

  • 创建自定义消息反序列解码类
objc// CustomAttachmentDecoder.h
@interface CustomAttachmentDecoder : NSObject<NIMCustomAttachmentCoding>
@end


// CustomAttachmentDecoder.m
@implementation CustomAttachmentDecoder
// 所有的自定义消息都会走这个解码方法,如有多种自定义消息请在该方法中扩展,并自行做好类型判断和版本兼容。
- (id<NIMCustomAttachment>)decodeAttachment:(NSString *)content{
    id<NIMCustomAttachment> attachment;
    NSData *data = [content dataUsingEncoding:NSUTF8StringEncoding];
    if (data) {
        NSDictionary *dict = [NSJSONSerialization JSONObjectWithData:data options:0 error:nil];
        if ([dict isKindOfClass:[NSDictionary class]]) {
            NSString *goodsName = dict[@"goodsName"];
            NSString *goodsURL = dict[@"goodsURL"]; 
            Attachment *myAttachment = [[Attachment alloc] init];
            myAttachment.goodsName = goodsName;
            myAttachment.goodsURL = goodsURL;
            attachment = myAttachment;
        }
    }
    return attachment;
}
@end
  • 注册自定义消息的解析器

- (BOOL)application: didFinishLaunchingWithOptions: 中注入解析器:

objc- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
...
// NIM SDK初始化
[NIMCustomObject registerCustomDecoder:[[CustomAttachmentDecoder alloc] init]];
... 
}
  • 接收自定义消息

接收消息时,需要判断是否是自定义消息,并进一步判断自定义消息类型,然后获取对应的内容:

objcif (message.messageType == NIMMessageTypeCustom) {
    
    NIMCustomObject *object = message.messageObject;
    if ([object.attachment isKindOfClass:[Attachment class]]) {
        Attachment *attachment = (Attachment *)object.attachment;
        
        // 通过 attachment.goodsName 与 attachment.goodsURL 获取到的内容,在UI上做进一步展示。
        ...
        
        }
        
    }

消息属性设置

发送消息时可以设置消息配置选项 NIMMessage - NIMMessageSetting,主要用于设定该消息是否存入云端、是否写入漫游等。

objc/**
 *  消息配置
 */
@interface NIMMessageSetting : NSObject
/**
 *  消息是否存入云端。
 *  @discussion 默认为YES。 
 */
@property (nonatomic,assign)    BOOL        historyEnabled;
/**
 *  消息是否支持漫游
 *  @discussion 默认为YES。 
 */
@property (nonatomic,assign)    BOOL        roamingEnabled;
/**
 *  当发送方在多个客户端同时登录时,其中一端发送一条消息后,客户端是否需要在收消息的回调抛出该条消息。
 *  @discussion 默认为YES。
 */
@property (nonatomic,assign)    BOOL        syncEnabled;
/**
 *  消息是否需要被计入未读计数
 *  @discussion 默认为YES。默认情况下,用户收到的所有消息都会被计入未读。设置这个为NO后,对应的消息被对端接受后将不计入未读消息计数内。
 */
@property (nonatomic,assign)    BOOL        shouldBeCounted;
/**
 *  消息是否需要推送
 *  @discussion 默认为YES。将这个字段设为NO,消息将不再有推送通知。
 */
@property (nonatomic,assign)    BOOL        apnsEnabled;
/**
 *  推送是否需要带前缀(一般为昵称)
 *  @discussion 默认为YES。将这个字段设为NO,推送消息将不带有前缀(xx:)。
 */
@property (nonatomic,assign)    BOOL        apnsWithPrefix;

/**
 *  是否需要抄送
 *  @discussion 默认为YES,即默认会抄送消息给开发者的服务器(如果有配置的话)
 */
@property (nonatomic,assign)    BOOL        routeEnabled;

/**
 *  该消息是否要存离线,若设置为false,将不会存入离线库与云端历史消息库。
 *  @discussion 默认为YES
 */
@property (nonatomic,assign)    BOOL        persistEnable;
@end

文件资源场景

SDK支持对图片、语音、视频与文件等设置对应的存活时间。

  • 预设 NOS 资源场景

原型

objc@interface NIMSDK : NSObject

/**
*  资源场景配置
*  @discussion nos 预设场景和自定义场景规则
*  可以覆盖设置,如果预设场景不设置,为系统默认设置
*  sceneDict key-value,系统默认预设场景为3种,自定义场景不超过10种
*  key 是场景,nsstring类型;value 是资源存活时间,nsnumber类型,精确到天,0为永久存活
*/
@property (nonatomic,strong)         NSMutableDictionary *sceneDict;
@end

例如,设置为@{@"nim_icon":@0,@"nim_msg":@0,@"nim_system":@0}代表:

头像等用户资料(nim_icon)的 NOS 资源存活时间为 永久。

图片、音频、视频等各类文件(nim_msg)的 NOS 资源存活时间为 永久。

nim_system为SDK内部使用。

sceneDict-key NIMNOSSceneType枚举值
nim_icon NIMNOSSceneTypeAvatar
nim_msg NIMNOSSceneTypeMessage
  • 文件类初始化设置

在各种附件类型消息(图片、语音、视频等)初始化方法中定义,例如:

objcNIMSession *session = [NIMSession session:@"user" type:NIMSessionTypeP2P];
// 获得图片附件对象,并设置对应的scene为nim_msg
NIMImageObject *imageObject = [[NIMImageObject alloc] initWithImage:image scene:NIMNOSSceneTypeMessage];
// 构造出具体消息并注入附件
NIMMessage *message = [[NIMMessage alloc] init];
message.messageObject = imageObject;
...
[[NIMSDK sharedSDK].chatManager sendMessage:message toSession:session error:&error];

本地消息插入

当有业务场景需要单纯插入一条消息至本地数据库内,而不发出时,可以使用插入本地消息的方法来实现。

目前支持本地插入的类型为:

  • 文本消息 ( NIMMessageTypeText )
  • 提示消息 ( NIMMessageTypeTip )
  • 自定义消息 ( NIMMessageTypeCustom )
objc@protocol NIMConversationManager <NSObject>
/**
 *  写入消息
 *
 *  @param message 需要更新的消息
 *  @param session 需要更新的会话
 *  @param completion 完成后的回调
 *  @discussion 当保存消息成功之后,会收到 NIMChatManagerDelegate 中的 onRecvMessages: 回调。目前支持消息类型:NIMMessageTypeText,NIMMessageTypeTip,NIMMessageTypeCustom
 */
- (void)saveMessage:(NIMMessage *)message
         forSession:(NIMSession *)session
         completion:(nullable NIMUpdateMessageBlock)completion;
@end

属性列表

参数 类型 说明
message NIMMessage 需要写入的没有被发送的消息,支持类型见上文
session NIMSession 消息所在的会话
completion NIMUpdateMessageBlock 完成后的回调

方法为异步写入,无须开发者在上层单独开线程,直接在当前线程调用即可。

不允许插入已存在的消息。当保存消息成功之后,会收到NIMChatManagerDelegate中的onRecvMessages:回调。

构造NIMMessage消息对象时,可以通过from字段设置消息发送者的accid,通过timestamp字段设置保存消息的时间。

消息更新

消息的部分属性支持在本地更新,目前可更新的字段为本地扩展字段 LocalExt 以及自定义消息的附件对象 NIMCustomObject

原型

objc@protocol NIMConversationManager <NSObject>
/**
 *  更新本地已存的消息记录
 *
 *  @param message 需要更新的消息
 *  @param session 需要更新的会话
 *  @param completion 完成后的回调
 *  @discussion 为了保证存储消息的完整性,提供给上层调用的消息更新接口只允许更新如下字段:所有消息的本地拓展字段(LocalExt)和自定义消息的消息对象(messageObject)
 */
- (void)updateMessage:(NIMMessage *)message
           forSession:(NIMSession *)session
           completion:(nullable NIMUpdateMessageBlock)completion;
@end

属性列表

参数 类型 说明
message NIMMessage 需要被更新的消息,支持的更新属性见上文
session NIMSession 消息所在的会话
completion NIMUpdateMessageBlock 完成后的回调

方法为异步写入,无须开发者在上层单独开线程,直接在当前线程调用即可。

消息取消发送

开发者需要通过 NIMSDK 里的 NIMChatManager 协议进行消息取消发送,只能取消正在发送中的消息(如大文件发送),通常配合异步发送消息接口,接口返回值成功时消息的状态为发送失败状态。

接口原型

objc@protocol NIMChatManager <NSObject>

/**
 *  取消正在发送的消息
 *
 *  @param message 目标消息
 *
 *  @return 是否调用成功
 */
- (BOOL)cancelSendingMessage:(NIMMessage *)message;

@end
参数 类型 说明
message NIMMessage 正在发送中的消息

消息重发

如网络原因导致的发送消息失败时,可以调用重发消息的接口重试发送。

原型

objc@protocol NIMChatManager <NSObject>
/**
 *  更新本地已存的消息记录
 *
 *  @param message 需要重发的消息
 *  @param error 
 * 
 *  @return 发送完成后的回调,这里的回调完成只表示当前这个函数调用完成,需要后续的发送消息完成回调 – sendMessage:didCompleteWithError: 才能判断消息是否已经发送至服务器
 */
- - (BOOL)resendMessage:(NIMMessage *)message 
                  error:(NSError *__nullable *)error
@end

消息转发

除了 通知消息 之外,其他类型消息均支持转发给其他会话。

objc@protocol NIMChatManager <NSObject>
/**
 *  转发消息至其他联系人
 *
 *  @param message 需要转发的消息
 *  @param session 会话
 *  @param error 发送完成后的回调,这里的回调完成只表示当前这个函数调用完成,需要后续的发送消息完成回 调 – sendMessage:didCompleteWithError: 才能判断消息是否已经发送至服务器
 */
- (BOOL)forwardMessage:(NIMMessage *)message
             toSession:(NIMSession *)session
                 error:(NSError **)error
@end
参数 类型 说明
message NIMMessage 需要转发的消息
session NIMSession 需要转发到的会话
error NSError 出错原因

文件传输过程管理

SDK提供文件传输管理功能,开发可以通过以下方法来管控文件传输。

  • 主动获取指定消息的传输情况:
objc@protocol NIMChatManager <NSObject>
/** 
* 消息是否正在传输 (发送/接受附件)
*/
- (BOOL)messageInTransport:(NIMMessage *)message;

/** 
* 传输消息的进度 (发送/接受附件)
*/
- (float)messageTransportProgress:(NIMMessage *)message;
@end
  • 监听文件传输情况:
objc@protocol NIMChatManagerDelegate <NSObject>
/** 
* 上传资源文件成功的回调
*/
- (void)uploadAttachmentSuccess:(NSString *)urlString 
                     forMessage:(NIMMessage *)message;

/** 
* 监听下载进度
* @param progress 下载进度,范围为 0 ~ 1
*/
- (void)fetchMessageAttachment:(NIMMessage *)message
                      progress:(float)progress;

/** 
* 监听下载进度
*/
- (void)fetchMessageAttachment:(NIMMessage *)message 
          didCompleteWithError:(nullable NSError *)error
@end

消息撤回

消息撤回

允许用户撤回一定时间内发送过的消息,客户端可允许撤回时长默认2分钟,可在网易云信控制台配置。

objc@protocol NIMChatManager <NSObject>
/**
* 撤回消息
*/
- (void)revokeMessage:(NIMMessage *)message
           completion:(NIMRevokeMessageBlock)completion;
           
/**
* 撤回消息,并触发推送。同时指定推送文案与附加信息apnsPayload,以及撤回通知本身是否计入未读。
*/
- (void)revokeMessage:(NIMMessage *)message
          apnsContent:(nullable NSString *)apnsContent
          apnsPayload:(nullable NSDictionary *)apnsPayload
      shouldBeCounted:(BOOL)should
           completion:(nullable NIMRevokeMessageBlock)completion;

/**
*  撤回消息
*
*  @param message    需要被撤回的消息
*  @param option     撤回的配置选项
*  @param completion 完成回调
*  @discussion 消息计入未读数
*/
- (void)revokeMessage:(NIMMessage *)message
               option:(NIMRevokeMessageOption *)option
           completion:(nullable NIMRevokeMessageBlock)completion;
@end
参数 类型 说明
message NIMMessage 需要撤回的消息
apnsContent NSDictionary 推送内容
apnsPayload NSDictionary 推送附加信息
should BOOL 撤回通知本身是否计入未读
completion NIMRevokeMessageBlock 完成回调

NIMRevokeMessageOption成员:

参数 类型 说明
postscript NSString 撤回的附言
apnsContent NSDictionary 推送内容
apnsPayload NSDictionary 推送附加信息
shouldBeCounted BOOL 撤回通知本身是否计入未读

在撤回消息请求调用成功后, SDK 会先回调给上层成功,再自动将本地的这条消息删除。如果需要在撤回后显示一条本方已撤回的提示,开发者可以自行构造一条提醒消息并调用插入本地消息的方法。

以下情况消息撤回会失败:

  • 消息并没有投递到对端
  • 消息超过撤回时限
  • 消息对象不是从本地数据库获取

此外,若被撤消息已经通过APNs推送到达客户端,可以通过设置apnsPayload来实现将原通知栏文案替换为apnsContent的效果。具体参见通知栏内容覆盖

监听消息撤回

当对方撤回消息成功时,被撤回方 SDK 会触发回调:

objc@protocol NIMChatManagerDelegate <NSObject>
- (void)onRecvRevokeMessageNotification: (NIMRevokeMessageNotification *)notification
@end

NIMRevokeMessageNotification属性一览:

属性 含义
notificationType 通知类型,如点对点消息撤回、群聊消息撤回等
fromUserId 撤回动作的执行者
messageFromUserId 被撤回的消息的发送者
session 被撤回消息所属的会话
timestamp 被撤回消息的时间戳
message 被撤回的消息
roaming 该条撤回通知是否属于漫游通知(即之前是否在其他端收到过)
postscript 撤回的附言

SDK 在收到消息撤回后,会先从本地数据库中找到对应消息并进行删除。如果需要在撤回后显示一条对方已撤回的提示 ,开发者可以自行构造一条提醒消息并调用插入本地消息的方法。

当被撤回消息时,支持配置如下属性来重新计算未读数:

objc@interface NIMSDKConfig : NSObject
/**
* 是否需要将被撤回的消息计入未读计算考虑。默认为 NO。设置成 YES 的情况下,如果被撤回的消息本地还未读,那么当消息发生撤回时,对应会话的未读计数将减 1 以保持最近会话未读数的一致性。
*/
@property (nonatomic,assign) BOOL shouldConsiderRevokedMessageUnreadCount;
@end

已读回执

当发送方需要知道接收方是否已经阅读了自己发送的消息时,需要使用已读回执的功能。

单聊消息已读回执

在会话界面中调用发送已读回执的接口并传入当前会话的最后一条消息,即表示这之前的消息本方都已读。

发送已读回执:

objc@protocol NIMChatManager <NSObject>
- (void)sendMessageReceipt:(NIMMessageReceipt *)receipt
                completion:(NIMSendMessageReceiptBlock)completion;
@end
参数 类型 说明
receipt NIMMessageReceipt 消息回执
completion NIMSendMessageReceiptBlock 完成回调

监听已读回执:

objc@protocol NIMChatManagerDelegate <NSObject>
- (void)onRecvMessageReceipts:(NSArray<NIMMessageReceipt *> *)receipts
@end

此外,可以通过 NIMMessage 中的 isRemoteRead 来得知该消息对方是否已读。

群聊消息已读回执

群消息已读回执功能,需要联系商务顾问申请开通后才能使用。同时,使用该功能时需要将群成员控制在100人以内。

  • 启用群消息已读回执功能
objc@interface NIMSDKConfig : NSObject
/**
 *  是否开启群回执功能
 *  @discussion 默认为NO,设置成 YES 之后所有群回执相关操作才会生效
 */
@property (nonatomic,assign) BOOL teamReceiptEnabled
@end
  • 设置其他群成员收到此消息需要发送已读回执
objc@interface NIMMessageSetting : NSObject
/**
 *  其他群成员收到此消息是否需要发送已读回执
 */
@property (nonatomic, assign) BOOL teamReceiptEnabled
@end
  • 消息接收方发送群消息已读回执
objc@protocol NIMChatManager <NSObject>
- (void)sendTeamMessageReceipts:(NSArray<NIMMessageReceipt*> *)receipts 
                     completion:(nullable NIMSendTeamMessageReceiptsBlock)completion
@end

参数列表

参数 类型 说明
receipt NIMMessageReceipt 消息回执
completion NIMSendTeamMessageReceiptsBlock 完成回调
  • 消息发送方监听群消息已读回执,来获取该条消息已读、未读数的变化
objc@protocol NIMChatManagerDelegate <NSObject>
- (void)onRecvMessageReceipts:(NSArray<NIMMessageReceipt *> *)receipts;
@end

参数列表

参数 类型 说明
receipts NSArray<NIMMessageReceipt *> * 消息回执数组
  • 主动刷新消息的群已读回执信息
objc@protocol NIMChatManager <NSObject>

/**
 *  刷新群组消息已读、未读数量
 *
 *  @param messages      要查询的消息集合
 *  @discussion          消息已读变化后,会通过 NIMChatManager 的代理 onRecvMessageReceipts: 回调给上层
 *                       刷新的消息必须为群组消息
 */
- (void)refreshTeamMessageReceipts:(NSArray<NIMMessage *> *)messages;

@end

参数列表

参数 类型 说明
message NSArray<NIMMessage *> * 要更新的消息集合
  • 查询群已读回执详情

包括已读人数的 id 和 未读人数的 id 列表。需要注意查询详情对象不会跟着回执人数变化而变化,如果要获取最新的详情,必须再次调用此接口。

objc@protocol NIMChatManager <NSObject>

/**
 *  查询群组消息回执详情
 *
 *  @param NIMMessage    要查询的消息
 *  @discussion          详情包括已读人数的 id 列表和未读人数的 id 列表
 *                       查询详情对象不会跟着回执人数变化而变化,如果要获取最新的详情,必须再次调用此接口
 *
 */
- (void)queryMessageReceiptDetail:(NIMMessage *)message
                       completion:(NIMQueryReceiptDetailBlock)completion;

/**
 * 查询群组消息指定用户的回执详情
 *
 * @param message 待查询的消息
 * @param accountSet 指定的用户的账号组成的NSSet
 * @return 该消息的已读、未读账号列表
 */
- (void)queryMessageReceiptDetail:(NIMMessage *)message
                     accountSet:(NSSet *)accountSet
                       completion:(NIMQueryReceiptDetailBlock)completion;
@end                     

参数列表

参数 类型 说明
message NIMMessage 要查询的消息
accountSet NSSet 指定的用户的账号组成的NSSet
completion NIMQueryReceiptDetailBlock 查询群组消息回执详情回调
  • 从本地查询已读回执详情

注意:直接从本地获取已读回执详情,很可能不是最新

objc@protocol NIMChatManager <NSObject>
/**
* 从本地查询单条群组消息已读、未读账号列表
* 注意!!!:这里获取的数据通常比离线前的列表信息更陈旧
*
* @param message 要查询的消息
* @return 该消息的已读、未读账号列表
*/
- (nullable NIMTeamMessageReceiptDetail *)localMessageReceiptDetail:(NIMMessage *)message;

/**
* 从本地数据库查询单条群组消息在指定用户中的已读、未读账号列表(同步接口)
* 注意!!!:这里获取的数据通常比离线前的列表信息更陈旧
*
* @param message 待查询的消息
* @param accountSet 指定的用户的账号组成的NSSet
* @return 该消息的已读、未读账号列表
*/
- (nullable NIMTeamMessageReceiptDetail *)localMessageReceiptDetail:(NIMMessage *)message
                                                       accountSet:(NSSet *)accountSet;
@end

参数列表

参数 类型 说明
message NIMMessage 要查询的消息
accountSet NSSet 指定的用户的账号组成的NSSet

此外,可以通过NIMMessageteamReceiptInfo来获取当前消息的群已读回执信息。

常见问题

此文档是否对你有帮助?
有帮助
去反馈
  • 功能概述
  • yidunAntiSpamRes字段说明
  • 易盾反垃圾
  • 消息发送
  • 文本消息发送
  • 图片消息发送
  • 语音消息发送
  • 视频消息发送
  • 文件消息发送
  • 位置消息发送
  • 提示消息发送
  • 自定义消息发送
  • 序列化与发送
  • 反序列化
  • 消息属性设置
  • 文件资源场景
  • 本地消息插入
  • 消息更新
  • 消息取消发送
  • 消息重发
  • 消息转发
  • 文件传输过程管理
  • 消息撤回
  • 消息撤回
  • 监听消息撤回
  • 已读回执
  • 单聊消息已读回执
  • 群聊消息已读回执
  • 常见问题