IM 即时通讯
Windows/macOS
产品介绍
简介
主要功能
产品优势
海外数据中心
IM平滑迁移方案
接口及业务限制
功能介绍
帐号集成与登录
基础消息功能
群组功能
聊天室功能
聊天室标签功能
圈组功能
多端登录与互踢策略
质量数据监控台
更新日志
Demo 更新日志
NIM SDK 更新日志
快速开始
实现单聊消息收发(不含 UI)
实现圈组消息收发(不含 UI)
开发指南
概要介绍
集成方式(当前版本)
集成方式(Windows旧版本)
集成方式(macOS旧版本)
初始化
登录登出
消息收发
最近会话
历史记录
用户资料托管
好友关系托管
事件订阅
系统通知
系统通知概述
内置系统通知管理
内置系统通知未读数
自定义系统通知收发
群组功能
群组概述
群组管理
群成员管理
群消息管理
超大群功能
开通聊天室功能
聊天室
圈组功能
初始化
登录圈组
圈组服务器管理
圈组服务器成员管理
游客功能
频道相关
频道管理
频道分组
频道分组黑白名单
频道未读数管理
搜索服务器和频道
身份组相关
身份组概述
身份组应用场景
服务器身份组
频道身份组
频道分组身份组
频道用户定制权限
自定义权限项
成员权限判定
身份组相关查询
圈组订阅机制
圈组消息相关
圈组消息收发
圈组消息撤回
圈组消息更新
圈组消息删除
会话消息回复(Thread)
圈组快捷评论
获取频道最后一条消息
消息正在输入
圈组消息搜索
圈组消息查询
查询@我的消息
服务器未读数
圈组系统通知
圈组系统通知概述
圈组系统通知收发
圈组系统通知更新
圈组各端接口命名差异
语音录制与播放
NOS云存储服务
文档转换
反垃圾(内容审核)
API 参考
Windows/macOS API 参考
状态码
IM 控制台指南
创建应用
注册 IM 账号
升级服务
配置应用客户端标识
参考文档
升级指引
开发示例
UI库指南
Demo源码导读
打包发布
类与常量定义说明
常见问题
FAQ
服务协议

历史记录

更新时间: 2023/02/24 16:33:33

本地记录

  • 获取聊天对象的本地消息记录

通过传入指定的消息历史记录的参数(会话id,会话类型,指定消息的时间戳)作为锚点,向前或向后查询本地消息记录。

void nim_msglog_query_msg_async(const char *account_id //会话id,对方的account id或者群组tid
						, NIMSessionType to_type //会话类型
						, int limit_count //一次查询数量,建议20
						, __int64 anchor_msg_time //指定消息的时间戳
						, const char *json_extension
						, nim_msglog_query_cb_func cb
						, const void *user_data);

例:

C++

void OnQueryMsgCallback(nim::NIMResCode code, const std::string& query_id, nim::NIMSessionType query_type, const nim::QueryMsglogResult& result)
{
	std::vector<nim::IMMessage> vec;
	for each (auto msg in result.msglogs_)
	{
		vec.push_back(msg);
	}
}

void foo()
{
	nim::MsgLog::QueryMsgAsync("session_id", nim::kNIMSessionTypeTeam, 20, 0, &OnQueryMsgCallback);
}

C#

NIM.Messagelog.MessagelogAPI.QueryMsglogLocally("session_id", NIM.Session.NIMSessionType.kNIMSessionTypeP2P, 20, 0, (code, accountId, sType, result) =>
{
	foreach(var i in result.MsglogCollection)
	{
		···
	}
});

C

//按时间逆序查询,逆序排列
void CallbackQueryMsgCb(int res_code, const char* id, const char* type, const char* str, const char *json_exten, const void *user_data)
{
	Json::Value values;
	Json::Reader reader;
	if (reader.parse(str, values) && values.isObject())
	{
		int count = values[kNIMMsglogQueryKeyCount].asInt();
		if (count > 0)
			...
	}
}

typedef void(*nim_msglog_query_msg_async)(const char* account_id, nim::NIMSessionType to_type, int limit_count, __int64 last_time, const char *json_extension, nim_msglog_query_cb_func cb, const void* user_data);

void foo()
{
	//设置搜索方向为向前
	Json::Value json_extension_value;
	json_extension_value[kNIMMsglogQueryJsonExtensionKeyDirection] = kForward;
	Json::FastWriter fw;

	nim_msglog_query_msg_async func = (nim_msglog_query_msg_async) GetProcAddress(hInst, "nim_msglog_query_msg_async");
	func("acount_id", is_team ? kNIMSessionTypeTeam : kNIMSessionTypeP2P, 20, 0, fw.write(json_extension_value).c_str(), &CallbackQueryMsgCb, nullptr);
}
  • 删除消息记录:

C++

void foo()
{
	//删除单条消息
	nim::MsgLog::DeleteAsync("session_id", nim::kNIMSessionTypeTeam, client_msg_id_, nim::MsgLog::DeleteCallback());

	//删除与某个聊天对象的全部消息记录
	nim::MsgLog::BatchStatusDeleteAsync("session_id", nim::kNIMSessionTypeTeam, nim::MsgLog::BatchStatusDeleteCallback());

	//删除指定会话类型的所有消息
	nim::MsgLog::DeleteBySessionTypeAsync(true, nim::kNIMSessionTypeTeam, nim::MsgLog::DeleteBySessionTypeCallback());

	//删除所有消息记录
	nim::MsgLog::DeleteAllAsync(true, nim::MsgLog::DeleteAllCallback());
}

C#

void foo()
{
	//删除单条消息
	NIM.Messagelog.MessagelogAPI.DeleteSpecifiedMsglog("session_id", NIM.Session.NIMSessionType.kNIMSessionTypeP2P, msg_id, (code, msgId) =>
	{
	});

	//删除与某个聊天对象的全部消息记录
	NIM.Messagelog.MessagelogAPI.BatchDeleteMeglog("session_id", NIM.Session.NIMSessionType.kNIMSessionTypeP2P, (code, uid, sType) =>
	{
	});

	//删除指定会话类型的所有消息
	NIM.Messagelog.MessagelogAPI.DeleteMsglogsBySessionType(NIM.Session.NIMSessionType.kNIMSessionTypeP2P, true, (code, uid, sType) =>
	{
	});

	//删除所有消息记录
	NIM.Messagelog.MessagelogAPI.ClearAll(true, (code) =>
	{
	});
}

C

void CallbackModifyMsglog(int res_code, const char *msg_id, const char *json_extension, const void user_data)
{
	if (user_data)
	{
		···
	}
}

typedef void(*nim_msglog_delete_async)(const char *account_id, NIMSessionType to_type, const char *msg_id, const char *json_extension, nim_msglog_res_cb_func cb, const void *user_data);
typedef void(*nim_msglog_batch_status_delete_async)(const char* account_id, nim::NIMSessionType to_type, const char *json_extension, nim_msglog_res_ex_cb_func cb, const void* user_data);
typedef void(*nim_msglog_delete_by_session_type_async)(bool delete_sessions, NIMSessionType to_type, const char *json_extension, nim_msglog_res_ex_cb_func cb, const void *user_data);
typedef void(*nim_msglog_delete_all_async)(bool delete_sessions, const char *json_extension, nim_msglog_modify_res_cb_func cb, const void *user_data);

void foo()
{
	nim_msglog_delete_async func = (nim_msglog_delete_async) GetProcAddress(hInst, "nim_msglog_delete_async");
	nim_msglog_batch_status_delete_async func_batch_statuc = (nim_msglog_batch_status_delete_async) GetProcAddress(hInst, "nim_msglog_batch_status_delete_async");
	nim_msglog_delete_by_session_type_async func_session = (nim_msglog_delete_by_session_type_async) GetProcAddress(hInst, "nim_msglog_delete_by_session_type_async");
	nim_msglog_delete_all_async func_all = (nim_msglog_delete_all_async) GetProcAddress(hInst, "nim_msglog_delete_all_async");

	//删除单条消息
	func("acount_id", is_team ? kNIMSessionTypeTeam : kNIMSessionTypeP2P, msg_id, nullptr, &CallbackModifyMsglog, nullptr);

	//删除与某个聊天对象的全部消息记录
	func_batch_statuc("acount_id", is_team ? kNIMSessionTypeTeam : kNIMSessionTypeP2P, nullptr, &CallbackModifyMsglog, nullptr);

	//删除指定会话类型的所有消息
	func_session(true, is_team ? kNIMSessionTypeTeam : kNIMSessionTypeP2P, nullptr, &CallbackModifyMsglog, nullptr);

	//删除所有消息记录
	func_all(delete_sessions, nullptr, &CallbackModifyMsglog, nullptr);
}
  • 插入聊天记录

C++

接口:

static bool WriteMsglogToLocalAsync(const std::string& talk_id , const IMMessage& msg , bool need_update_session , const WriteMsglogCallback& cb , const std::string& json_extension = "");

示例:

void foo()
{
	std::wstring notify_text = GetRecallNotifyTextEx(talk_id, notify.session_type_, notify.from_id_, notify.operator_id_,notify.from_nick_);
	nim::IMMessage msg;
	msg.timetag_ = notify.msglog_timetag_;
	msg.client_msg_id_ = QString::GetGUID();
	msg.receiver_accid_ = talk_id;
	msg.session_type_ = notify.session_type_;
	msg.sender_accid_ = notify.from_id_;
	msg.status_ = nim::kNIMMsgLogStatusSent;
	msg.type_ = nim::kNIMMessageTypeText;
	Json::Value values;
	values["comment"] = "is_recall_notification";
	values["notify_from"] = notify.from_id_;
	values["operator_id"] = notify.operator_id_;
	values["from_nick"] = notify.from_nick_;
	msg.attach_ = values.toStyledString();
	msg.content_ = nbase::UTF16ToUTF8(notify_text);
	msg.msg_setting_.push_need_badge_ = nim::BS_FALSE; //设置会话列表不需要计入未读数
	nim::MsgLog::WriteMsglogToLocalAsync(talk_id, msg, true, nim::MsgLog::WriteMsglogCallback());
}

nim_msglog.h 文件中的接口提供了比较完善的消息记录管理功能,开发者可本地查阅、在线查阅、删除和清空聊天记录,还可以调用nim_msglog_write_db_only_async 接口只往本地消息历史数据库里写入一条消息(通常是APP 的本地自定义消息,并不会发给服务器)。详见API 文档。此外,还要注意:本地消息历史操作(如删除)及状态变化(如发送失败或成功)会与会话列表里的消息状态自动同步,App 上层需要根据nim_session_reg_change_cb 注册好的会话列表通知回调进行相应通知事件的处理。

导入导出

  • 导入消息历史记录(不包括系统通知,且不允许拿别人的消息历史记录文件来导入):
void nim_msglog_import_db_async(const char *src_path, const char *json_extension, nim_msglog_modify_res_cb_func res_cb, const void *res_user_data, nim_msglog_import_prg_cb_func prg_cb, const void *prg_user_data);

例:

C++

void OnImportProgressCallback(int64_t imported_count, int64_t total_count)
{
	···
}

void OnImportCompeleteCallback(nim::NIMResCode res_code)
{
	if (res_code == nim::kNIMResSuccess)
	{
		//导入完成
	}
	else
	{
		//导入失败
	}
}

void foo()
{
	nim::MsgLog::ImportDbAsync(path, &OnImportCompeleteCallback, &OnImportProgressCallback);
}

C#

NIM.Messagelog.MessagelogAPI.ImportDatabase(path, (code) =>
{
}
, (importedCount, totalCount) =>
{
});

C

void CallbackMsglogRes(int res, const char* msg_id, const char *json_exten, const void *user_data)
{
	...
}

void CallbackMsgImportPrg(int res_code, const char* id, const char* type, const char* str, const char *json_exten, const void *user_data)
{
	...
}

typedef void(*nim_msglog_import_db_async)(const char *src_path, const char *json_extension, nim_msglog_modify_res_cb_func res_cb, const void *res_user_data, nim_msglog_import_prg_cb_func prg_cb, const void *prg_user_data);

void foo()
{
	nim_msglog_import_db_async func = (nim_msglog_import_db_async) GetProcAddress(hInst, "nim_msglog_import_db_async");
	func("src_path", "", &CallbackMsglogRes, nullptr, &CallbackMsgImportPrg, nullptr);
}
  • 导出整个消息历史DB文件(不包括系统通知):

C++

void OnExportCompeleteCallback(nim::NIMResCode res_code)
{
	if (res_code == nim::kNIMResSuccess)
	{
		//导出完成
	}
	else
	{
		//导出失败
	}
}

void foo()
{
	nim::MsgLog::ExportDbAsync(path, &OnExportCompeleteCallback);
}

C#

NIM.Messagelog.MessagelogAPI.ExportDatabaseFile(path, (code) =>
{
});

C

void CallbackMsglogRes(int res, const char* msg_id, const char *json_exten, const void *user_data)
{
	...
}

typedef void(*nim_msglog_export_db_async)(const char *dst_path, const char *json_extension, nim_msglog_modify_res_cb_func cb, const void *user_data);

void foo()
{
	nim_msglog_export_db_async func = (nim_msglog_export_db_async) GetProcAddress(hInst, "nim_msglog_export_db_async");
	func("src_path", "", &CallbackMsglogRes, nullptr);
}

云端记录

  • 在线查询聊天对象的消息历史记录:
void nim_msglog_query_msg_online_async(const char *id //会话id,对方的account id或者群组tid
								, NIMSessionType to_type //会话类型
								, int limit_count //本次查询的消息条数上限(最多100条)
								, __int64 from_time //起始时间点,单位:毫秒
								, __int64 end_time //结束时间点,单位:毫秒
								, __int64 end_msg_id //结束查询的最后一条消息的server_msg_id(不包含在查询结果中) 
								, bool reverse //true:反向查询(按时间正序起查,正序排列),false:按时间逆序起查,逆序排列(建议默认为false)
								, bool need_save_to_local //true: 将在线查询结果保存到本地,false: 不保存
								, const char *json_extension
								, nim_msglog_query_cb_func cb
								, const void *user_data);

例:

C++

void QueryMsgOnlineCb(nim::NIMResCode code, const std::string& id, nim::NIMSessionType type, const nim::QueryMsglogResult& result)
{
	if (code == nim::kNIMResSuccess)
	{
		std::vector<nim::IMMessage> vec;
		for (auto& msg : result.msglogs_)
		{
			···
		}
	}
}

void foo()
{
	nim::MsgLog::QueryMsgOnlineAsync("session_id", nim::kNIMSessionTypeP2P, 20, 0, farst_msg_time_, last_server_id_, false, true, &QueryMsgOnlineCb);
}

C#

NIM.Messagelog.MessagelogAPI.QueryMsglogOnline("session_id", NIM.Session.NIMSessionType.kNIMSessionTypeTeam, 20, 0, 0, 0, false, false,
(ResponseCode code, string accountId, NIM.Session.NIMSessionType sType, MsglogQueryResult result) =>
{
	···
});

C

void CallbackQueryMsgCb(int res_code, const char* id, const char* type, const char* str, const char *json_exten, const void *user_data)
{
	...
}

typedef void(*nim_msglog_query_msg_online_async)(const char *id, nim::NIMSessionType to_type, int limit_count, __int64 from_time, __int64 end_time, __int64 end_msg_id, bool reverse,	bool need_save_to_local, const char *json_extension, nim_msglog_query_cb_func cb, const void *user_data);

void foo()
{
	nim_msglog_query_msg_online_async func = (nim_msglog_query_msg_online_async) GetProcAddress(hInst, "nim_msglog_query_msg_online_async");
	func("acount_id", is_team ? kNIMSessionTypeTeam : kNIMSessionTypeP2P, 20, 0, msg_time, first_msg_server_msg_id, false, false, nullptr, &CallbackQueryMsgCb, nullptr);
}

动态查询某段时间内的历史消息

当离线阶段收取大量消息,再次登录或切换设备时,往往容易出现历史消息拉取不完整的情况。

为了获取完整的历史消息记录,您可以使用全云端方案,即用户每次进入时都通过查询云端历史记录并将查到的消息同步至本地。但是在会话多、消息多的场景下,使用全云端方案,会导致耗时长,耗能大等问题。

为解决上述问题,云信 IM 提供本地+云端智能调度方案,通过调用动态查询连续的历史消息接口,利用完整的内部逻辑保证历史消息的连续性和完整性。您仅需要选择开始或结束时间戳以及对应的消息条数即可按需获取历史消息。

  • 若用户的业务场景需要调用该接口,请先在云信控制台开通漫游消息功能,然后联系商务经理单独开通动态查询历史消息功能,否则该接口只会从本地数据库获取消息。
  • 该接口为完整独立的历史消息查询接口,与其他历史消息查询接口互不影响。
C++

通过调用 GetMessagesDynamically 方法动态查询连续的历史消息。

参数说明:

参数 说明
session_id 会话 ID
to_type 会话类型,具体请及参见NIMSessionType
from_time 开始时间
to_time 结束时间,大于开始时间,0 表示当前时间
limit_count 查询的历史消息数量,最大 100
anchor_client_msg_id 查询起始的客户端消息 ID,查询结果不包括这条消息
anchor_server_msg_id 查询起始的服务端消息 ID,查询结果不包括这条消息
direction 查询方向,具体请参见NIMMsglogSearchDirection ,默认kForward,即从新往旧查询
cb 查询历史消息的回调函数

示例代码:

std::string session_id = "session_id";
uint64_t from_time = 0;
uint64_t to_time = 0;
uint32_t limit = 100;
std::string anchor_client_msg_id = "";
uint64_t anchor_server_msg_id = 0;.
MsgLog::GetMessagesDynamically(session_id, kNIMSessionTypeP2P, from_time, to_time, limit, anchor_client_msg_id, anchor_server_msg_id, kForward, [](const GetMessagesResult& result) {
	// process result
	// ......
});
C

用户可通过 nim_msglog_get_messages_dynamically 方法动态查询连续的历史消息。

示例代码:

static void CallbackGetMessages(int res_code,
    const char* id,
    nim::NIMSessionType to_type,
    const char* result,
    const char* json_extension,
    const void* callback) {
	// process messages
	// ......
}
nim_msglog_get_messages_dynamically("session_id", kNIMSessionTypeP2P, 0, 0, 100, "", 0, direction,json_extension.c_str(), &CallbackGetMessages, cb_pointer);

此文档是否对你有帮助?
有帮助
我要吐槽
  • 本地记录
  • 导入导出
  • 云端记录
  • 动态查询某段时间内的历史消息