222 lines
5.8 KiB
JavaScript
222 lines
5.8 KiB
JavaScript
|
|
/**
|
|||
|
|
* NIM 用户信息管理器
|
|||
|
|
* 负责同步用户头像和昵称到 NIM SDK
|
|||
|
|
*/
|
|||
|
|
|
|||
|
|
const app = getApp();
|
|||
|
|
|
|||
|
|
class NIMUserManager {
|
|||
|
|
constructor() {
|
|||
|
|
this.initialized = false;
|
|||
|
|
this.userInfoCache = new Map(); // 用户信息缓存
|
|||
|
|
this.cacheExpiry = 30 * 60 * 1000; // 缓存30分钟
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/**
|
|||
|
|
* 初始化用户管理器
|
|||
|
|
*/
|
|||
|
|
init() {
|
|||
|
|
if (this.initialized) {
|
|||
|
|
console.log('NIM 用户管理器已初始化');
|
|||
|
|
return;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
console.log('📋 初始化 NIM 用户管理器');
|
|||
|
|
this.initialized = true;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/**
|
|||
|
|
* 更新自己的用户信息到 NIM
|
|||
|
|
* @param {Object} userInfo - 用户信息对象
|
|||
|
|
* @param {string} userInfo.avatar - 头像 URL
|
|||
|
|
* @param {string} userInfo.nickname - 昵称
|
|||
|
|
* @returns {Promise<boolean>} 是否更新成功
|
|||
|
|
*/
|
|||
|
|
async updateSelfUserInfo(userInfo = {}) {
|
|||
|
|
try {
|
|||
|
|
const nim = app.globalData?.nim;
|
|||
|
|
if (!nim) {
|
|||
|
|
console.warn('⚠️ NIM 实例未初始化,跳过用户信息同步');
|
|||
|
|
return false;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
// 🔥 正确的访问方式:nim.V2NIMUserService (小程序/Web平台)
|
|||
|
|
const userService = nim.V2NIMUserService;
|
|||
|
|
if (!userService) {
|
|||
|
|
console.warn('⚠️ NIM V2NIMUserService 未注册');
|
|||
|
|
return false;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
// 构建更新参数
|
|||
|
|
const updateParams = {};
|
|||
|
|
|
|||
|
|
if (userInfo.avatar) {
|
|||
|
|
updateParams.avatar = userInfo.avatar;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
if (userInfo.nickname) {
|
|||
|
|
updateParams.name = userInfo.nickname;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
// 如果没有需要更新的字段,直接返回
|
|||
|
|
if (Object.keys(updateParams).length === 0) {
|
|||
|
|
console.log('没有需要更新的用户信息');
|
|||
|
|
return true;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
console.log('🔄 同步用户信息到 NIM:', updateParams);
|
|||
|
|
|
|||
|
|
// 🔥 调用 NIM SDK 更新用户资料
|
|||
|
|
// 参考文档:https://doc.yunxin.163.com/messaging2/client-apis/jc0MTUyODY?platform=client#updateSelfUserProfile
|
|||
|
|
await userService.updateSelfUserProfile(updateParams);
|
|||
|
|
|
|||
|
|
console.log('✅ NIM 用户信息同步成功');
|
|||
|
|
return true;
|
|||
|
|
} catch (error) {
|
|||
|
|
console.error('❌ NIM 用户信息同步失败:', error);
|
|||
|
|
// 不抛出错误,避免影响主流程
|
|||
|
|
return false;
|
|||
|
|
}
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/**
|
|||
|
|
* 批量获取用户信息(从 NIM 或 API)
|
|||
|
|
* @param {Array<string>} accountIds - 用户账号 ID 列表
|
|||
|
|
* @returns {Promise<Map<string, Object>>} 用户信息 Map
|
|||
|
|
*/
|
|||
|
|
async getUserInfoBatch(accountIds = []) {
|
|||
|
|
if (!Array.isArray(accountIds) || accountIds.length === 0) {
|
|||
|
|
return new Map();
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
try {
|
|||
|
|
const nim = app.globalData?.nim;
|
|||
|
|
if (!nim) {
|
|||
|
|
console.warn('⚠️ NIM 实例未初始化');
|
|||
|
|
return new Map();
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
// 🔥 正确的访问方式:nim.V2NIMUserService
|
|||
|
|
const userService = nim.V2NIMUserService;
|
|||
|
|
if (!userService) {
|
|||
|
|
console.warn('⚠️ NIM V2NIMUserService 未注册');
|
|||
|
|
return new Map();
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
// 过滤掉已缓存且未过期的用户
|
|||
|
|
const now = Date.now();
|
|||
|
|
const needFetch = accountIds.filter(id => {
|
|||
|
|
const cached = this.userInfoCache.get(id);
|
|||
|
|
return !cached || (now - cached.timestamp > this.cacheExpiry);
|
|||
|
|
});
|
|||
|
|
|
|||
|
|
if (needFetch.length === 0) {
|
|||
|
|
// 全部从缓存返回
|
|||
|
|
const result = new Map();
|
|||
|
|
accountIds.forEach(id => {
|
|||
|
|
const cached = this.userInfoCache.get(id);
|
|||
|
|
if (cached) {
|
|||
|
|
result.set(id, cached.data);
|
|||
|
|
}
|
|||
|
|
});
|
|||
|
|
return result;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
console.log(`📡 从 NIM 获取 ${needFetch.length} 个用户信息`);
|
|||
|
|
|
|||
|
|
// 从 NIM 获取用户信息
|
|||
|
|
const users = await userService.getUserList(needFetch);
|
|||
|
|
|
|||
|
|
const result = new Map();
|
|||
|
|
|
|||
|
|
if (Array.isArray(users)) {
|
|||
|
|
users.forEach(user => {
|
|||
|
|
const userInfo = {
|
|||
|
|
accountId: user.accountId,
|
|||
|
|
avatar: user.avatar || '',
|
|||
|
|
nickname: user.name || '',
|
|||
|
|
createTime: user.createTime,
|
|||
|
|
updateTime: user.updateTime
|
|||
|
|
};
|
|||
|
|
|
|||
|
|
result.set(user.accountId, userInfo);
|
|||
|
|
|
|||
|
|
// 更新缓存
|
|||
|
|
this.userInfoCache.set(user.accountId, {
|
|||
|
|
data: userInfo,
|
|||
|
|
timestamp: now
|
|||
|
|
});
|
|||
|
|
});
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
// 补充缓存中的数据
|
|||
|
|
accountIds.forEach(id => {
|
|||
|
|
if (!result.has(id)) {
|
|||
|
|
const cached = this.userInfoCache.get(id);
|
|||
|
|
if (cached) {
|
|||
|
|
result.set(id, cached.data);
|
|||
|
|
}
|
|||
|
|
}
|
|||
|
|
});
|
|||
|
|
|
|||
|
|
return result;
|
|||
|
|
} catch (error) {
|
|||
|
|
console.error('❌ 批量获取用户信息失败:', error);
|
|||
|
|
return new Map();
|
|||
|
|
}
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/**
|
|||
|
|
* 获取单个用户信息
|
|||
|
|
* @param {string} accountId - 用户账号 ID
|
|||
|
|
* @returns {Promise<Object|null>} 用户信息对象
|
|||
|
|
*/
|
|||
|
|
async getUserInfo(accountId) {
|
|||
|
|
if (!accountId) {
|
|||
|
|
return null;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
const userMap = await this.getUserInfoBatch([accountId]);
|
|||
|
|
return userMap.get(accountId) || null;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/**
|
|||
|
|
* 清除用户信息缓存
|
|||
|
|
* @param {string} accountId - 可选,指定用户 ID,不传则清除全部
|
|||
|
|
*/
|
|||
|
|
clearCache(accountId = null) {
|
|||
|
|
if (accountId) {
|
|||
|
|
this.userInfoCache.delete(accountId);
|
|||
|
|
console.log(`🗑️ 清除用户 ${accountId} 的缓存`);
|
|||
|
|
} else {
|
|||
|
|
this.userInfoCache.clear();
|
|||
|
|
console.log('🗑️ 清除所有用户信息缓存');
|
|||
|
|
}
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/**
|
|||
|
|
* 获取缓存统计信息
|
|||
|
|
* @returns {Object} 缓存统计
|
|||
|
|
*/
|
|||
|
|
getCacheStats() {
|
|||
|
|
const now = Date.now();
|
|||
|
|
let expired = 0;
|
|||
|
|
|
|||
|
|
this.userInfoCache.forEach(item => {
|
|||
|
|
if (now - item.timestamp > this.cacheExpiry) {
|
|||
|
|
expired++;
|
|||
|
|
}
|
|||
|
|
});
|
|||
|
|
|
|||
|
|
return {
|
|||
|
|
total: this.userInfoCache.size,
|
|||
|
|
expired: expired,
|
|||
|
|
valid: this.userInfoCache.size - expired
|
|||
|
|
};
|
|||
|
|
}
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
// 导出单例
|
|||
|
|
const nimUserManager = new NIMUserManager();
|
|||
|
|
module.exports = nimUserManager;
|