From 9ef3edabcee7b9455a1d931551c306e4c6676be4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=89=8B=E7=93=9C=E4=B8=80=E5=8D=81=E9=9B=AA?= Date: Fri, 9 Aug 2024 13:33:58 +0800 Subject: [PATCH] chore: NTAPI --- src/common/utils/MessageUnique.ts | 142 ++++++++++++++++++++++++ src/core/apis/collection.ts | 5 +- src/core/apis/friend.ts | 14 +-- src/core/apis/group.ts | 66 +++++------ src/core/apis/msg.ts | 178 ++++++++++-------------------- src/core/apis/system.ts | 12 +- src/core/apis/user.ts | 104 ++++++++--------- src/core/core.ts | 17 ++- src/core/entities/msg.ts | 1 - src/core/index.ts | 3 +- src/core/wrapper/context.ts | 6 + 11 files changed, 319 insertions(+), 229 deletions(-) create mode 100644 src/common/utils/MessageUnique.ts diff --git a/src/common/utils/MessageUnique.ts b/src/common/utils/MessageUnique.ts new file mode 100644 index 00000000..c1ac73f7 --- /dev/null +++ b/src/common/utils/MessageUnique.ts @@ -0,0 +1,142 @@ +import { Peer } from '@/core'; +import crypto from 'crypto'; +export class LimitedHashTable { + private keyToValue: Map = new Map(); + private valueToKey: Map = new Map(); + private maxSize: number; + + constructor(maxSize: number) { + this.maxSize = maxSize; + } + resize(count: number) { + this.maxSize = count; + } + + set(key: K, value: V): void { + // const isExist = this.keyToValue.get(key); + // if (isExist && isExist === value) { + // return; + // } + this.keyToValue.set(key, value); + this.valueToKey.set(value, key); + while (this.keyToValue.size !== this.valueToKey.size) { + console.log('keyToValue.size !== valueToKey.size Error Atom'); + this.keyToValue.clear(); + this.valueToKey.clear(); + } + // console.log('---------------'); + // console.log(this.keyToValue); + // console.log(this.valueToKey); + // console.log('---------------'); + while (this.keyToValue.size > this.maxSize || this.valueToKey.size > this.maxSize) { + //console.log(this.keyToValue.size > this.maxSize, this.valueToKey.size > this.maxSize); + const oldestKey = this.keyToValue.keys().next().value; + this.valueToKey.delete(this.keyToValue.get(oldestKey)!); + this.keyToValue.delete(oldestKey); + } + } + + getValue(key: K): V | undefined { + return this.keyToValue.get(key); + } + + getKey(value: V): K | undefined { + return this.valueToKey.get(value); + } + + deleteByValue(value: V): void { + const key = this.valueToKey.get(value); + if (key !== undefined) { + this.keyToValue.delete(key); + this.valueToKey.delete(value); + } + } + + deleteByKey(key: K): void { + const value = this.keyToValue.get(key); + if (value !== undefined) { + this.keyToValue.delete(key); + this.valueToKey.delete(value); + } + } + + getKeyList(): K[] { + return Array.from(this.keyToValue.keys()); + } + //获取最近刚写入的几个值 + getHeads(size: number): { key: K; value: V }[] | undefined { + const keyList = this.getKeyList(); + if (keyList.length === 0) { + return undefined; + } + const result: { key: K; value: V }[] = []; + const listSize = Math.min(size, keyList.length); + for (let i = 0; i < listSize; i++) { + const key = keyList[listSize - i]; + result.push({ key, value: this.keyToValue.get(key)! }); + } + return result; + } +} + +class MessageUniqueWrapper { + private msgDataMap: LimitedHashTable; + private msgIdMap: LimitedHashTable; + constructor(maxMap: number = 1000) { + this.msgIdMap = new LimitedHashTable(maxMap); + this.msgDataMap = new LimitedHashTable(maxMap); + } + getRecentMsgIds(Peer: Peer, size: number): string[] { + const heads = this.msgIdMap.getHeads(size); + if (!heads) { + return []; + } + const data = heads.map((t) => MessageUnique.getMsgIdAndPeerByShortId(t.value)); + const ret = data.filter((t) => t?.Peer.chatType === Peer.chatType && t?.Peer.peerUid === Peer.peerUid); + return ret.map((t) => t?.MsgId).filter((t) => t !== undefined); + } + createMsg(peer: Peer, msgId: string): number | undefined { + const key = `${msgId}|${peer.chatType}|${peer.peerUid}`; + const hash = crypto.createHash('md5').update(key).digest(); + //设置第一个bit为0 保证shortId为正数 + hash[0] &= 0x7f; + const shortId = hash.readInt32BE(0); + //减少性能损耗 + // const isExist = this.msgIdMap.getKey(shortId); + // if (isExist && isExist === msgId) { + // return shortId; + // } + this.msgIdMap.set(msgId, shortId); + this.msgDataMap.set(key, shortId); + return shortId; + } + + getMsgIdAndPeerByShortId(shortId: number): { MsgId: string; Peer: Peer } | undefined { + const data = this.msgDataMap.getKey(shortId); + if (data) { + const [msgId, chatTypeStr, peerUid] = data.split('|'); + const peer: Peer = { + chatType: parseInt(chatTypeStr), + peerUid, + guildId: '', + }; + return { MsgId: msgId, Peer: peer }; + } + return undefined; + } + + getShortIdByMsgId(msgId: string): number | undefined { + return this.msgIdMap.getValue(msgId); + } + getPeerByMsgId(msgId: string) { + const shortId = this.msgIdMap.getValue(msgId); + if (!shortId) return undefined; + return this.getMsgIdAndPeerByShortId(shortId); + } + resize(maxSize: number): void { + this.msgIdMap.resize(maxSize); + this.msgDataMap.resize(maxSize); + } +} + +export const MessageUnique: MessageUniqueWrapper = new MessageUniqueWrapper(); \ No newline at end of file diff --git a/src/core/apis/collection.ts b/src/core/apis/collection.ts index bcaf8795..4858fd80 100644 --- a/src/core/apis/collection.ts +++ b/src/core/apis/collection.ts @@ -1,7 +1,6 @@ -import { napCatCore } from ".."; export class NTQQCollectionApi { - static async createCollection(authorUin: string, authorUid: string, authorName: string, brief: string, rawData: string) { + async createCollection(authorUin: string, authorUid: string, authorName: string, brief: string, rawData: string) { let param = { commInfo: { bid: 1, @@ -38,7 +37,7 @@ export class NTQQCollectionApi { }; return napCatCore.session.getCollectionService().createNewCollectionItem(param); } - static async getAllCollection(category: number = 0, count: number = 50) { + async getAllCollection(category: number = 0, count: number = 50) { let param = { category: category, groupId: -1, diff --git a/src/core/apis/friend.ts b/src/core/apis/friend.ts index d9f853fe..5d02aea4 100644 --- a/src/core/apis/friend.ts +++ b/src/core/apis/friend.ts @@ -4,7 +4,7 @@ import { NTEventDispatch } from '@/common/utils/EventTask'; import { LimitedHashTable } from '@/common/utils/MessageUnique'; import { CacheClassFuncAsyncExtend } from '@/common/utils/helper'; export class NTQQFriendApi { - static async getBuddyV2(refresh = false): Promise { + async getBuddyV2(refresh = false): Promise { let uids: string[] = []; const buddyService = napCatCore.session.getBuddyService(); const buddyListV2 = refresh ? await buddyService.getBuddyListV2('0', BuddyListReqType.KNOMAL) : await buddyService.getBuddyListV2('0', BuddyListReqType.KNOMAL); @@ -15,10 +15,10 @@ export class NTQQFriendApi { return Array.from(data.values()); } @CacheClassFuncAsyncExtend(3600 * 1000, 'getBuddyIdMap', () => true) - static async getBuddyIdMapCache(refresh = false): Promise> { + async getBuddyIdMapCache(refresh = false): Promise> { return await NTQQFriendApi.getBuddyIdMap(refresh); } - static async getBuddyIdMap(refresh = false): Promise> { + async getBuddyIdMap(refresh = false): Promise> { let uids: string[] = []; let retMap: LimitedHashTable = new LimitedHashTable(5000); const buddyService = napCatCore.session.getBuddyService(); @@ -33,7 +33,7 @@ export class NTQQFriendApi { //console.log('getBuddyIdMap', retMap.getValue); return retMap; } - static async getBuddyV2ExWithCate(refresh = false) { + async getBuddyV2ExWithCate(refresh = false) { let uids: string[] = []; let categoryMap: Map = new Map(); const buddyService = napCatCore.session.getBuddyService(); @@ -53,7 +53,7 @@ export class NTQQFriendApi { return category ? { ...value, categoryId: category.categoryId, categroyName: category.categroyName } : value; }); } - static async isBuddy(uid: string) { + async isBuddy(uid: string) { return napCatCore.session.getBuddyService().isBuddy(uid); } /** @@ -61,7 +61,7 @@ export class NTQQFriendApi { * @param forced * @returns */ - static async getFriends(forced = false): Promise { + async getFriends(forced = false): Promise { let [_retData, _BuddyArg] = await NTEventDispatch.CallNormalEvent <(force: boolean) => Promise, (arg: OnBuddyChangeParams) => void> ( @@ -81,7 +81,7 @@ export class NTQQFriendApi { return friends; } - static async handleFriendRequest(flag: string, accept: boolean) { + async handleFriendRequest(flag: string, accept: boolean) { let data = flag.split('|'); if (data.length < 2) { return; diff --git a/src/core/apis/group.ts b/src/core/apis/group.ts index 1ccf1e99..5b07046c 100644 --- a/src/core/apis/group.ts +++ b/src/core/apis/group.ts @@ -5,10 +5,10 @@ import { log } from '@/common/utils/log'; import { groupMembers } from '../data'; import { CacheClassFuncAsyncExtend, runAllWithTimeout } from '@/common/utils/helper'; export class NTQQGroupApi { - static async setGroupAvatar(gc: string, filePath: string) { + async setGroupAvatar(gc: string, filePath: string) { return napCatCore.session.getGroupService().setHeader(gc, filePath); } - static async getGroups(forced = false) { + async getGroups(forced = false) { type ListenerType = NodeIKernelGroupListener['onGroupListUpdate']; let [_retData, _updateType, groupList] = await NTEventDispatch.CallNormalEvent <(force: boolean) => Promise, ListenerType> @@ -24,7 +24,7 @@ export class NTQQGroupApi { } @CacheClassFuncAsyncExtend(3600 * 1000, "LastestSendTime", () => true) - static async getGroupMemberLastestSendTimeCache(GroupCode: string) { + async getGroupMemberLastestSendTimeCache(GroupCode: string) { return NTQQGroupApi.getGroupMemberLastestSendTime(GroupCode); } /** @@ -37,7 +37,7 @@ export class NTQQGroupApi { * console.log(uin, sendTime); * } */ - static async getGroupMemberLastestSendTime(GroupCode: string) { + async getGroupMemberLastestSendTime(GroupCode: string) { async function getdata(uid: string) { let NTRet = await NTQQGroupApi.getLastestMsgByUids(GroupCode, [uid]); if (NTRet.result != 0 && NTRet.msgList.length < 1) { @@ -65,7 +65,7 @@ export class NTQQGroupApi { } return ret; } - static async getLastestMsgByUids(GroupCode: string, uids: string[]) { + async getLastestMsgByUids(GroupCode: string, uids: string[]) { let ret = await napCatCore.session.getMsgService().queryMsgsWithFilterEx('0', '0', '0', { chatInfo: { peerUid: GroupCode, @@ -81,10 +81,10 @@ export class NTQQGroupApi { }); return ret; } - static async getGroupMemberAll(GroupCode: string, forced = false) { + async getGroupMemberAll(GroupCode: string, forced = false) { return napCatCore.session.getGroupService().getAllMemberList(GroupCode, forced); } - static async getLastestMsg(GroupCode: string, uins: string[]) { + async getLastestMsg(GroupCode: string, uins: string[]) { let uids: Array = []; for (let uin of uins) { let uid = await NTQQUserApi.getUidByUin(uin) @@ -107,19 +107,19 @@ export class NTQQGroupApi { }); return ret; } - static async getGroupRecommendContactArkJson(GroupCode: string) { + async getGroupRecommendContactArkJson(GroupCode: string) { return napCatCore.session.getGroupService().getGroupRecommendContactArkJson(GroupCode); } - static async CreatGroupFileFolder(groupCode: string, folderName: string) { + async CreatGroupFileFolder(groupCode: string, folderName: string) { return napCatCore.session.getRichMediaService().createGroupFolder(groupCode, folderName); } - static async DelGroupFile(groupCode: string, files: string[]) { + async DelGroupFile(groupCode: string, files: string[]) { return napCatCore.session.getRichMediaService().deleteGroupFile(groupCode, [102], files); } - static async DelGroupFileFolder(groupCode: string, folderId: string) { + async DelGroupFileFolder(groupCode: string, folderId: string) { return napCatCore.session.getRichMediaService().deleteGroupFolder(groupCode, folderId); } - static async addGroupEssence(GroupCode: string, msgId: string) { + async addGroupEssence(GroupCode: string, msgId: string) { // 代码没测过 // 需要 ob11msgid->msgId + (peer) -> msgSeq + msgRandom let MsgData = await napCatCore.session.getMsgService().getMsgsIncludeSelf({ chatType: 2, guildId: '', peerUid: GroupCode }, msgId, 1, false); @@ -131,7 +131,7 @@ export class NTQQGroupApi { // GetMsgByShoretID(ShoretID); -> MsgService.getMsgs(Peer,MsgId,1,false); -> 组出参数 return napCatCore.session.getGroupService().addGroupEssence(param); } - static async removeGroupEssence(GroupCode: string, msgId: string) { + async removeGroupEssence(GroupCode: string, msgId: string) { // 代码没测过 // 需要 ob11msgid->msgId + (peer) -> msgSeq + msgRandom let MsgData = await napCatCore.session.getMsgService().getMsgsIncludeSelf({ chatType: 2, guildId: '', peerUid: GroupCode }, msgId, 1, false); @@ -143,7 +143,7 @@ export class NTQQGroupApi { // GetMsgByShoretID(ShoretID); -> MsgService.getMsgs(Peer,MsgId,1,false); -> 组出参数 return napCatCore.session.getGroupService().removeGroupEssence(param); } - static async getSingleScreenNotifies(num: number) { + async getSingleScreenNotifies(num: number) { let [_retData, _doubt, _seq, notifies] = await NTEventDispatch.CallNormalEvent <(arg1: boolean, arg2: string, arg3: number) => Promise, (doubt: boolean, seq: string, notifies: GroupNotify[]) => void> ( @@ -158,7 +158,7 @@ export class NTQQGroupApi { ); return notifies; } - static async getGroupMemberV2(GroupCode: string, uid: string, forced = false) { + async getGroupMemberV2(GroupCode: string, uid: string, forced = false) { type ListenerType = NodeIKernelGroupListener['onMemberInfoChange']; type EventType = NodeIKernelGroupService['getMemberInfo']; // NTEventDispatch.CreatListenerFunction('NodeIKernelGroupListener/onGroupMemberInfoUpdate', @@ -177,7 +177,7 @@ export class NTQQGroupApi { ); return _members.get(uid); } - static async getGroupMembers(groupQQ: string, num = 3000): Promise> { + async getGroupMembers(groupQQ: string, num = 3000): Promise> { const groupService = napCatCore.session.getGroupService(); const sceneId = groupService.createMemberListScene(groupQQ, 'groupMemberList_MainWindow'); const result = await groupService.getNextMemberList(sceneId!, undefined, num); @@ -196,17 +196,17 @@ export class NTQQGroupApi { */ } - static async getGroupNotifies() { + async getGroupNotifies() { // 获取管理员变更 // 加群通知,退出通知,需要管理员权限 } - static async GetGroupFileCount(Gids: Array) { + async GetGroupFileCount(Gids: Array) { return napCatCore.session.getRichMediaService().batchGetGroupFileCount(Gids); } - static async getGroupIgnoreNotifies() { + async getGroupIgnoreNotifies() { } - static async getArkJsonGroupShare(GroupCode: string) { + async getArkJsonGroupShare(GroupCode: string) { let ret = await NTEventDispatch.CallNoListenerEvent <(GroupId: string) => Promise>( 'NodeIKernelGroupService/getGroupRecommendContactArkJson', @@ -216,11 +216,11 @@ export class NTQQGroupApi { return ret.arkJson; } //需要异常处理 - static async uploadGroupBulletinPic(GroupCode: string, imageurl: string) { + async uploadGroupBulletinPic(GroupCode: string, imageurl: string) { const _Pskey = (await NTQQUserApi.getPSkey(['qun.qq.com'])).domainPskeyMap.get('qun.qq.com')!; return napCatCore.session.getGroupService().uploadGroupBulletinPic(GroupCode, _Pskey, imageurl); } - static async handleGroupRequest(flag: string, operateType: GroupRequestOperateTypes, reason?: string) { + async handleGroupRequest(flag: string, operateType: GroupRequestOperateTypes, reason?: string) { let flagitem = flag.split('|'); let groupCode = flagitem[0]; let seq = flagitem[1]; @@ -239,41 +239,41 @@ export class NTQQGroupApi { }); } - static async quitGroup(groupQQ: string) { + async quitGroup(groupQQ: string) { return napCatCore.session.getGroupService().quitGroup(groupQQ); } - static async kickMember(groupQQ: string, kickUids: string[], refuseForever: boolean = false, kickReason: string = '') { + async kickMember(groupQQ: string, kickUids: string[], refuseForever: boolean = false, kickReason: string = '') { return napCatCore.session.getGroupService().kickMember(groupQQ, kickUids, refuseForever, kickReason); } - static async banMember(groupQQ: string, memList: Array<{ uid: string, timeStamp: number }>) { + async banMember(groupQQ: string, memList: Array<{ uid: string, timeStamp: number }>) { // timeStamp为秒数, 0为解除禁言 return napCatCore.session.getGroupService().setMemberShutUp(groupQQ, memList); } - static async banGroup(groupQQ: string, shutUp: boolean) { + async banGroup(groupQQ: string, shutUp: boolean) { return napCatCore.session.getGroupService().setGroupShutUp(groupQQ, shutUp); } - static async setMemberCard(groupQQ: string, memberUid: string, cardName: string) { + async setMemberCard(groupQQ: string, memberUid: string, cardName: string) { return napCatCore.session.getGroupService().modifyMemberCardName(groupQQ, memberUid, cardName); } - static async setMemberRole(groupQQ: string, memberUid: string, role: GroupMemberRole) { + async setMemberRole(groupQQ: string, memberUid: string, role: GroupMemberRole) { return napCatCore.session.getGroupService().modifyMemberRole(groupQQ, memberUid, role); } - static async setGroupName(groupQQ: string, groupName: string) { + async setGroupName(groupQQ: string, groupName: string) { return napCatCore.session.getGroupService().modifyGroupName(groupQQ, groupName, false); } // 头衔不可用 - static async setGroupTitle(groupQQ: string, uid: string, title: string) { + async setGroupTitle(groupQQ: string, uid: string, title: string) { } - static async publishGroupBulletin(groupQQ: string, content: string, picInfo: { id: string, width: number, height: number } | undefined = undefined, pinned: number = 0, confirmRequired: number = 0,) { + async publishGroupBulletin(groupQQ: string, content: string, picInfo: { id: string, width: number, height: number } | undefined = undefined, pinned: number = 0, confirmRequired: number = 0,) { const _Pskey = (await NTQQUserApi.getPSkey(['qun.qq.com'])).domainPskeyMap.get('qun.qq.com'); //text是content内容url编码 let data = { @@ -285,10 +285,10 @@ export class NTQQGroupApi { }; return napCatCore.session.getGroupService().publishGroupBulletin(groupQQ, _Pskey!, data); } - static async getGroupRemainAtTimes(GroupCode: string) { + async getGroupRemainAtTimes(GroupCode: string) { napCatCore.session.getGroupService().getGroupRemainAtTimes(GroupCode); } - static async getMemberExtInfo(groupCode: string, uin: string) { + async getMemberExtInfo(groupCode: string, uin: string) { // 仅NTQQ 9.9.11 24568测试 容易炸开谨慎使用 return napCatCore.session.getGroupService().getMemberExtInfo( { diff --git a/src/core/apis/msg.ts b/src/core/apis/msg.ts index 53c9ba88..644fcd04 100644 --- a/src/core/apis/msg.ts +++ b/src/core/apis/msg.ts @@ -1,82 +1,24 @@ -import { GetFileListParam, Peer, RawMessage, SendMessageElement, SendMsgElementConstructor } from '@/core/entities'; -import { friends, groups, selfInfo } from '@/core/data'; -import { log, logWarn } from '@/common/utils/log'; -import { sleep } from '@/common/utils/helper'; -import { napCatCore, NTQQUserApi } from '@/core'; +import { GetFileListParam, Peer, RawMessage, SendMessageElement } from '@/core/entities'; +import { InstanceContext, NapCatCore, NTApiContext } from '@/core'; import { onGroupFileInfoUpdateParamType } from '@/core/listeners'; import { GeneralCallResult } from '@/core/services/common'; -import { MessageUnique } from '../../../common/utils/MessageUnique'; -import { NTEventDispatch } from '@/common/utils/EventTask'; -import { requireMinNTQQBuild } from '@/common/utils/QQBasicInfo'; - -async function LoadMessageIdList(Peer: Peer, msgId: string) { - let msgList = await NTQQMsgApi.getMsgHistory(Peer, msgId, 50); - for (let j = 0; j < msgList.msgList.length; j++) { - let shortId = MessageUnique.createMsg(Peer, msgList.msgList[j].msgId); - } -} -async function loadMessageUnique() { - if (groups.size > 100) { - logWarn('[性能检测] 群数量大于100,可能会导致性能问题'); - } - let predict = (groups.size + friends.size / 2) / 5; - predict = predict < 20 ? 20 : predict; - predict = predict > 50 ? 50 : predict; - //let waitpromise: Array> = []; - predict = Math.floor(predict * 50); - MessageUnique.resize(predict); - let RecentContact = await NTQQUserApi.getRecentContactListSnapShot(predict); - let LoadMessageIdDo: Array> = new Array>(); - if (RecentContact?.info?.changedList && RecentContact?.info?.changedList?.length > 0) { - for (let i = 0; i < RecentContact.info.changedList.length; i++) { - let Peer: Peer = { chatType: RecentContact.info.changedList[i].chatType, peerUid: RecentContact.info.changedList[i].peerUid, guildId: '' }; - LoadMessageIdDo.push(LoadMessageIdList(Peer, RecentContact.info.changedList[i].msgId)); - } - } - await Promise.all(LoadMessageIdDo).then(() => { - log(`[消息序列] 加载 ${predict} 条历史消息记录完成`); - }); -} - -setTimeout(() => { - napCatCore.onLoginSuccess(async () => { - await sleep(100); - // NTQQMsgApi.CheckSendMode().then().catch(); - loadMessageUnique().then().catch(); - //下面的代码还没摸清 不要使用 - //let data = await napCatCore.session.getMsgService().sendSsoCmdReqByContend("LightAppSvc.mini_app_growguard.ReportExecute","1124343"); - //console.log(data); - }); -}, 100); -//歇菜LocalMsg压根不写Db -// setTimeout(async () => { -// let ele: MessageElement = { extBufForUI: '0x', ...SendMsgElementConstructor.text('测试消息') }; -// let MsgId = await NTQQMsgApi.getMsgUniqueEx(); -// let peer = { chatType: 2, peerUid: '', guildId: '' }; -// console.log(await napCatCore.session.getTestPerformanceService().insertMsg( -// { -// peer: peer, -// msgTime: Math.floor(Date.now() / 1000).toString(), -// msgId: MsgId, -// msgSeq: '56564', -// batchNums: 1, -// timesPerBatch: 1, -// numPerTime: 1 -// }, [ele] -// )); -// console.log(await NTQQMsgApi.multiForwardMsg(peer, peer, [MsgId])); -// }, 25000) export class NTQQMsgApi { - static async FetchLongMsg(peer: Peer, msgId: string) { - return napCatCore.session.getMsgService().fetchLongMsg(peer, msgId); + context: InstanceContext; + core: NapCatCore; + constructor(context: InstanceContext, core: NapCatCore) { + this.context = context; + this.core = core; } - static async getMsgEmojiLikesList(peer: Peer, msgSeq: string, emojiId: string, emojiType: string, count: number = 20) { + async FetchLongMsg(peer: Peer, msgId: string) { + return this.context.session.getMsgService().fetchLongMsg(peer, msgId); + } + async getMsgEmojiLikesList(peer: Peer, msgSeq: string, emojiId: string, emojiType: string, count: number = 20) { //console.log(peer, msgSeq, emojiId, emojiType, count); //注意此处emojiType 可选值一般为1-2 2好像是unicode表情dec值 大部分情况 Taged M likiowa - return napCatCore.session.getMsgService().getMsgEmojiLikesList(peer, msgSeq, emojiId, emojiType, "", false, 20) + return this.context.session.getMsgService().getMsgEmojiLikesList(peer, msgSeq, emojiId, emojiType, "", false, 20) } - // static napCatCore: NapCatCore | null = null; + // napCatCore: NapCatCore | null = null; // enum BaseEmojiType { // NORMAL_EMOJI, // SUPER_EMOJI, @@ -84,23 +26,23 @@ export class NTQQMsgApi { // CHAIN_SUPER_EMOJI, // EMOJI_EMOJI // } - static async setEmojiLike(peer: Peer, msgSeq: string, emojiId: string, set: boolean = true) { + async setEmojiLike(peer: Peer, msgSeq: string, emojiId: string, set: boolean = true) { // nt_qq//global//nt_data//Emoji//emoji-resource//sysface_res/apng/ 下可以看到所有QQ表情预览 // nt_qq\global\nt_data\Emoji\emoji-resource\face_config.json 里面有所有表情的id, 自带表情id是QSid, 标准emoji表情id是QCid // 其实以官方文档为准是最好的,https://bot.q.qq.com/wiki/develop/api-v2/openapi/emoji/model.html#EmojiType emojiId = emojiId.toString(); - return napCatCore.session.getMsgService().setMsgEmojiLikes(peer, msgSeq, emojiId, emojiId.length > 3 ? '2' : '1', set); + return this.context.session.getMsgService().setMsgEmojiLikes(peer, msgSeq, emojiId, emojiId.length > 3 ? '2' : '1', set); } - static async getMultiMsg(peer: Peer, rootMsgId: string, parentMsgId: string): Promise { - return napCatCore.session.getMsgService().getMultiMsg(peer, rootMsgId, parentMsgId); + return this.context.session.getMsgService().getMultiMsg(peer, rootMsgId, parentMsgId); } - static async ForwardMsg(peer: Peer, msgIds: string[]) { - return napCatCore.session.getMsgService().forwardMsg(msgIds, peer, [peer], new Map()); + async ForwardMsg(peer: Peer, msgIds: string[]) { + return this.context.session.getMsgService().forwardMsg(msgIds, peer, [peer], new Map()); } - static async getLastestMsgByUids(peer: Peer, count: number = 20, isReverseOrder: boolean = false) { - let ret = await napCatCore.session.getMsgService().queryMsgsWithFilterEx('0', '0', '0', { + async getLastestMsgByUids(peer: Peer, count: number = 20, isReverseOrder: boolean = false) { + let ret = await this.context.session.getMsgService().queryMsgsWithFilterEx('0', '0', '0', { chatInfo: peer, filterMsgType: [], filterSendersUid: [], @@ -112,20 +54,20 @@ export class NTQQMsgApi { }); return ret; } - static async getMsgsByMsgId(peer: Peer | undefined, msgIds: string[] | undefined) { + async getMsgsByMsgId(peer: Peer | undefined, msgIds: string[] | undefined) { if (!peer) throw new Error('peer is not allowed'); if (!msgIds) throw new Error('msgIds is not allowed'); //Mlikiowa: 参数不合规会导致NC异常崩溃 原因是TX未对进入参数判断 对应Android标记@NotNull AndroidJADX分析可得 - return await napCatCore.session.getMsgService().getMsgsByMsgId(peer, msgIds); + return await this.context.session.getMsgService().getMsgsByMsgId(peer, msgIds); } - static async getSingleMsg(peer: Peer, seq: string) { - return await napCatCore.session.getMsgService().getSingleMsg(peer, seq); + async getSingleMsg(peer: Peer, seq: string) { + return await this.context.session.getMsgService().getSingleMsg(peer, seq); } - static async fetchFavEmojiList(num: number) { - return napCatCore.session.getMsgService().fetchFavEmojiList("", num, true, true) + async fetchFavEmojiList(num: number) { + return this.context.session.getMsgService().fetchFavEmojiList("", num, true, true) } - static async queryMsgsWithFilterExWithSeq(peer: Peer, msgSeq: string) { - let ret = await napCatCore.session.getMsgService().queryMsgsWithFilterEx('0', '0', msgSeq, { + async queryMsgsWithFilterExWithSeq(peer: Peer, msgSeq: string) { + let ret = await this.context.session.getMsgService().queryMsgsWithFilterEx('0', '0', msgSeq, { chatInfo: peer,//此处为Peer 为关键查询参数 没有啥也没有 by mlik iowa filterMsgType: [], filterSendersUid: [], @@ -137,14 +79,14 @@ export class NTQQMsgApi { }); return ret; } - static async getMsgsBySeqAndCount(peer: Peer, seq: string, count: number, desc: boolean, z: boolean) { - return await napCatCore.session.getMsgService().getMsgsBySeqAndCount(peer, seq, count, desc, z); + async getMsgsBySeqAndCount(peer: Peer, seq: string, count: number, desc: boolean, z: boolean) { + return await this.context.session.getMsgService().getMsgsBySeqAndCount(peer, seq, count, desc, z); } - static async setMsgRead(peer: Peer) { - return napCatCore.session.getMsgService().setMsgRead(peer); + async setMsgRead(peer: Peer) { + return this.context.session.getMsgService().setMsgRead(peer); } - static async getGroupFileList(GroupCode: string, params: GetFileListParam) { - let data = await NTEventDispatch.CallNormalEvent< + async getGroupFileList(GroupCode: string, params: GetFileListParam) { + let data = await this.core.eventWrapper.CallNormalEvent< (GroupCode: string, params: GetFileListParam) => Promise, (groupFileListResult: onGroupFileInfoUpdateParamType) => void >( @@ -161,17 +103,17 @@ export class NTQQMsgApi { ); return data[1].item; } - static async getMsgHistory(peer: Peer, msgId: string, count: number, isReverseOrder: boolean = false) { + async getMsgHistory(peer: Peer, msgId: string, count: number, isReverseOrder: boolean = false) { // 消息时间从旧到新 - return napCatCore.session.getMsgService().getMsgsIncludeSelf(peer, msgId, count, isReverseOrder); + return this.context.session.getMsgService().getMsgsIncludeSelf(peer, msgId, count, isReverseOrder); } - static async recallMsg(peer: Peer, msgIds: string[]) { - await napCatCore.session.getMsgService().recallMsg({ + async recallMsg(peer: Peer, msgIds: string[]) { + await this.context.session.getMsgService().recallMsg({ chatType: peer.chatType, peerUid: peer.peerUid }, msgIds); } - static async sendMsgV2(peer: Peer, msgElements: SendMessageElement[], waitComplete = true, timeout = 10000) { + async sendMsgV2(peer: Peer, msgElements: SendMessageElement[], waitComplete = true, timeout = 10000) { function generateMsgId() { const timestamp = Math.floor(Date.now() / 1000); const random = Math.floor(Math.random() * Math.pow(2, 32)); @@ -186,13 +128,13 @@ export class NTQQMsgApi { // 谨慎采用 目前测试暂无问题 Developer.Mlikiowa let msgId: string; try { - msgId = await NTQQMsgApi.getMsgUnique(peer.chatType, await NTQQMsgApi.getServerTime()); + msgId = await this.getMsgUnique(peer.chatType, await this.getServerTime()); } catch (error) { //if (!napCatCore.session.getMsgService()['generateMsgUniqueId']) //兜底识别策略V2 msgId = generateMsgId().toString(); } - let data = await NTEventDispatch.CallNormalEvent< + let data = await this.core.eventWrapper.CallNormalEvent< (msgId: string, peer: Peer, msgElements: SendMessageElement[], map: Map) => Promise, (msgList: RawMessage[]) => void >( @@ -220,14 +162,14 @@ export class NTQQMsgApi { }); return retMsg; } - static sendMsgEx(peer: Peer, msgElements: SendMessageElement[], waitComplete = true, timeout = 10000) { + sendMsgEx(peer: Peer, msgElements: SendMessageElement[], waitComplete = true, timeout = 10000) { //return NTQQMsgApi.sendMsgV1(peer, msgElements, waitComplete, timeout); } - static async sendMsg(peer: Peer, msgElements: SendMessageElement[], waitComplete = true, timeout = 10000) { + async sendMsg(peer: Peer, msgElements: SendMessageElement[], waitComplete = true, timeout = 10000) { //唉? !我有个想法 - let msgId = await NTQQMsgApi.getMsgUnique(peer.chatType, await NTQQMsgApi.getServerTime()); + let msgId = await this.getMsgUnique(peer.chatType, await this.getServerTime()); peer.guildId = msgId; - let data = await NTEventDispatch.CallNormalEvent< + let data = await this.core.eventWrapper.CallNormalEvent< (msgId: string, peer: Peer, msgElements: SendMessageElement[], map: Map) => Promise, (msgList: RawMessage[]) => void >( @@ -255,26 +197,26 @@ export class NTQQMsgApi { }); return retMsg; } - static async getMsgUnique(chatType: number, time: string) { - if (requireMinNTQQBuild('26702')) { - return napCatCore.session.getMsgService().generateMsgUniqueId(chatType, time); + async getMsgUnique(chatType: number, time: string) { + if (this.context.basicInfoWrapper.requireMinNTQQBuild('26702')) { + return this.context.session.getMsgService().generateMsgUniqueId(chatType, time); } - return napCatCore.session.getMsgService().getMsgUniqueId(time); + return this.context.session.getMsgService().getMsgUniqueId(time); } - static async getServerTime() { - return napCatCore.session.getMSFService().getServerTime(); + async getServerTime() { + return this.context.session.getMSFService().getServerTime(); } - static async getServerTimeV2() { - return NTEventDispatch.CallNoListenerEvent<() => string>('NodeIKernelMsgService/getServerTime', 5000); + async getServerTimeV2() { + return this.core.eventWrapper.CallNoListenerEvent<() => string>('NodeIKernelMsgService/getServerTime', 5000); } - static async forwardMsg(srcPeer: Peer, destPeer: Peer, msgIds: string[]) { - return napCatCore.session.getMsgService().forwardMsg(msgIds, srcPeer, [destPeer], new Map()); + async forwardMsg(srcPeer: Peer, destPeer: Peer, msgIds: string[]) { + return this.context.session.getMsgService().forwardMsg(msgIds, srcPeer, [destPeer], new Map()); } - static async multiForwardMsg(srcPeer: Peer, destPeer: Peer, msgIds: string[]): Promise { + async multiForwardMsg(srcPeer: Peer, destPeer: Peer, msgIds: string[]): Promise { const msgInfos = msgIds.map(id => { return { msgId: id, senderShowName: selfInfo.nick }; }); - let data = await NTEventDispatch.CallNormalEvent< + let data = await this.core.eventWrapper.CallNormalEvent< (msgInfo: typeof msgInfos, srcPeer: Peer, destPeer: Peer, comment: Array, attr: Map,) => Promise, (msgList: RawMessage[]) => void >( @@ -311,7 +253,7 @@ export class NTQQMsgApi { } throw new Error('转发消息超时'); } - static async markallMsgAsRead() { - return napCatCore.session.getMsgService().setAllC2CAndGroupMsgRead(); + async markallMsgAsRead() { + return this.context.session.getMsgService().setAllC2CAndGroupMsgRead(); } } diff --git a/src/core/apis/system.ts b/src/core/apis/system.ts index 52d3f997..0a649819 100644 --- a/src/core/apis/system.ts +++ b/src/core/apis/system.ts @@ -3,21 +3,21 @@ import { NTEventDispatch } from '@/common/utils/EventTask'; import { GeneralCallResult, NTQQFileApi, NTQQUserApi, napCatCore } from '@/core'; export class NTQQSystemApi { - static async hasOtherRunningQQProcess() { + async hasOtherRunningQQProcess() { return napCatCore.util.hasOtherRunningQQProcess(); } - static async ORCImage(filePath: string) { + async ORCImage(filePath: string) { return napCatCore.session.getNodeMiscService().wantWinScreenOCR(filePath); } - static async translateEnWordToZn(words: string[]) { + async translateEnWordToZn(words: string[]) { return napCatCore.session.getRichMediaService().translateEnWordToZn(words); } //调用会超时 没灯用 (好像是通知listener的) onLineDev - static async getOnlineDev() { + async getOnlineDev() { return napCatCore.session.getMsgService().getOnLineDev(); } //1-2-162b9b42-65b9-4405-a8ed-2e256ec8aa50 - static async getArkJsonCollection(cid: string) { + async getArkJsonCollection(cid: string) { let ret = await NTEventDispatch.CallNoListenerEvent <(cid: string) => Promise>( 'NodeIKernelCollectionService/collectionArkShare', @@ -26,7 +26,7 @@ export class NTQQSystemApi { ); return ret; } - static async BootMiniApp(appfile: string, params: string) { + async BootMiniApp(appfile: string, params: string) { await napCatCore.session.getNodeMiscService().setMiniAppVersion('2.16.4'); let c = await napCatCore.session.getNodeMiscService().getMiniAppPath(); diff --git a/src/core/apis/user.ts b/src/core/apis/user.ts index b269874e..b6348f4b 100644 --- a/src/core/apis/user.ts +++ b/src/core/apis/user.ts @@ -2,10 +2,17 @@ import type { ModifyProfileParams, SelfInfo, User, UserDetailInfoByUin, UserDeta import { NodeIKernelProfileListener, ProfileListener } from '@/core/listeners'; import { RequestUtil } from '@/common/utils/request'; import { NodeIKernelProfileService, ProfileBizType, UserDetailSource } from '@/core/services'; +import { InstanceContext, NapCatCore } from '..'; export class NTQQUserApi { + context: InstanceContext; + core: NapCatCore; + constructor(context: InstanceContext, core: NapCatCore) { + this.context = context; + this.core = core; + } async getProfileLike(uid: string) { - return napCatCore.session.getProfileLikeService().getBuddyProfileLike({ + return this.context.session.getProfileLikeService().getBuddyProfileLike({ friendUids: [ uid ], @@ -19,16 +26,16 @@ export class NTQQUserApi { }); } async setLongNick(longNick: string) { - return napCatCore.session.getProfileService().setLongNick(longNick); + return this.context.session.getProfileService().setLongNick(longNick); } async setSelfOnlineStatus(status: number, extStatus: number, batteryStatus: number) { - return napCatCore.session.getMsgService().setStatus({ status: status, extStatus: extStatus, batteryStatus: batteryStatus }); + return this.context.session.getMsgService().setStatus({ status: status, extStatus: extStatus, batteryStatus: batteryStatus }); } async getBuddyRecommendContactArkJson(uin: string, sencenID = '') { - return napCatCore.session.getBuddyService().getBuddyRecommendContactArkJson(uin, sencenID); + return this.context.session.getBuddyService().getBuddyRecommendContactArkJson(uin, sencenID); } async like(uid: string, count = 1): Promise<{ result: number, errMsg: string, succCounts: number }> { - return napCatCore.session.getProfileLikeService().setBuddyProfileLike({ + return this.context.session.getProfileLikeService().setBuddyProfileLike({ friendUid: uid, sourceId: 71, doLikeCount: count, @@ -38,11 +45,11 @@ export class NTQQUserApi { async setQQAvatar(filePath: string) { type setQQAvatarRet = { result: number, errMsg: string }; - const ret = await napCatCore.session.getProfileService().setHeader(filePath) as setQQAvatarRet; + const ret = await this.context.session.getProfileService().setHeader(filePath) as setQQAvatarRet; return { result: ret?.result, errMsg: ret?.errMsg }; } async setGroupAvatar(gc: string, filePath: string) { - return napCatCore.session.getGroupService().setHeader(gc, filePath); + return this.context.session.getGroupService().setHeader(gc, filePath); } async fetchUserDetailInfos(uids: string[]) { @@ -50,7 +57,7 @@ export class NTQQUserApi { type EventService = NodeIKernelProfileService['fetchUserDetailInfo']; type EventListener = NodeIKernelProfileListener['onUserDetailInfoChanged']; let retData: User[] = []; - let [_retData, _retListener] = await NTEventDispatch.CallNormalEvent + let [_retData, _retListener] = await this.core.eventWrapper.CallNormalEvent ( 'NodeIKernelProfileService/fetchUserDetailInfo', @@ -86,7 +93,7 @@ export class NTQQUserApi { async fetchUserDetailInfo(uid: string) { type EventService = NodeIKernelProfileService['fetchUserDetailInfo']; type EventListener = NodeIKernelProfileListener['onUserDetailInfoChanged']; - let [_retData, profile] = await NTEventDispatch.CallNormalEvent + let [_retData, profile] = await this.core.eventWrapper.CallNormalEvent ( 'NodeIKernelProfileService/fetchUserDetailInfo', @@ -120,7 +127,7 @@ export class NTQQUserApi { return RetUser; } async getUserDetailInfo(uid: string) { - if (requireMinNTQQBuild('26702')) { + if (this.context.basicInfoWrapper.requireMinNTQQBuild('26702')) { return this.fetchUserDetailInfo(uid); } return this.getUserDetailInfoOld(uid); @@ -128,7 +135,7 @@ export class NTQQUserApi { async getUserDetailInfoOld(uid: string) { type EventService = NodeIKernelProfileService['getUserDetailInfoWithBizInfo']; type EventListener = NodeIKernelProfileListener['onProfileDetailInfoChanged']; - let [_retData, profile] = await NTEventDispatch.CallNormalEvent + let [_retData, profile] = await this.core.eventWrapper.CallNormalEvent ( 'NodeIKernelProfileService/getUserDetailInfoWithBizInfo', @@ -151,16 +158,16 @@ export class NTQQUserApi { } //需要异常处理 async getCookies(domain: string) { - const ClientKeyData = await NTQQUserApi.forceFetchClientKey(); + const ClientKeyData = await this.forceFetchClientKey(); const requestUrl = 'https://ssl.ptlogin2.qq.com/jump?ptlang=1033&clientuin=' + selfInfo.uin + '&clientkey=' + ClientKeyData.clientKey + '&u1=https%3A%2F%2F' + domain + '%2F' + selfInfo.uin + '%2Finfocenter&keyindex=19%27' let cookies: { [key: string]: string; } = await RequestUtil.HttpsGetCookies(requestUrl); return cookies; } async getPSkey(domainList: string[]) { - return await napCatCore.session.getTipOffService().getPskey(domainList, true); + return await this.context.session.getTipOffService().getPskey(domainList, true); } async getRobotUinRange(): Promise> { - const robotUinRanges = await napCatCore.session.getRobotService().getRobotUinRange({ + const robotUinRanges = await this.context.session.getRobotService().getRobotUinRange({ justFetchMsgConfig: '1', type: 1, version: 0, @@ -172,7 +179,7 @@ export class NTQQUserApi { //需要异常处理 async getQzoneCookies() { - const ClientKeyData = await NTQQUserApi.forceFetchClientKey(); + const ClientKeyData = await this.forceFetchClientKey(); const requestUrl = 'https://ssl.ptlogin2.qq.com/jump?ptlang=1033&clientuin=' + selfInfo.uin + '&clientkey=' + ClientKeyData.clientKey + '&u1=https%3A%2F%2Fuser.qzone.qq.com%2F' + selfInfo.uin + '%2Finfocenter&keyindex=19%27' let cookies: { [key: string]: string; } = await RequestUtil.HttpsGetCookies(requestUrl); return cookies; @@ -180,7 +187,7 @@ export class NTQQUserApi { //需要异常处理 async getSkey(): Promise { - const ClientKeyData = await NTQQUserApi.forceFetchClientKey(); + const ClientKeyData = await this.forceFetchClientKey(); if (ClientKeyData.result !== 0) { throw new Error('getClientKey Error'); } @@ -194,72 +201,58 @@ export class NTQQUserApi { } return skey; } - @CacheClassFuncAsyncExtend(3600 * 1000, 'Uin2Uid', (Uin: string, Uid: string | undefined) => { - if (Uid && Uid.indexOf('u_') != -1) { - return true - } - logWarn("uin转换到uid时异常", Uin, Uid); - return false; - }) async getUidByUin(Uin: string) { //此代码仅临时使用,后期会被废弃 - if (requireMinNTQQBuild('26702')) { - return await NTQQUserApi.getUidByUinV2(Uin); + if (this.context.basicInfoWrapper.requireMinNTQQBuild('26702')) { + return await this..getUidByUinV2(Uin); } - return await NTQQUserApi.getUidByUinV1(Uin); + return await this.getUidByUinV1(Uin); } - @CacheClassFuncAsyncExtend(3600 * 1000, 'Uid2Uin', (Uid: string | undefined, Uin: number | undefined) => { - if (Uin && Uin != 0 && !isNaN(Uin)) { - return true - } - logWarn("uid转换到uin时异常", Uid, Uin); - return false; - }) async getUinByUid(Uid: string) { //此代码仅临时使用,后期会被废弃 - if (requireMinNTQQBuild('26702')) { - return await NTQQUserApi.getUinByUidV2(Uid); + if (this.context.basicInfoWrapper.requireMinNTQQBuild('26702')) { + return await this.getUinByUidV2(Uid); } - return await NTQQUserApi.getUinByUidV1(Uid); + return await this.getUinByUidV1(Uid); } //后期改成流水线处理 async getUidByUinV2(Uin: string) { - let uid = (await napCatCore.session.getProfileService().getUidByUin('FriendsServiceImpl', [Uin])).get(Uin); + let uid = (await this.context.session.getProfileService().getUidByUin('FriendsServiceImpl', [Uin])).get(Uin); if (uid) return uid; - uid = (await napCatCore.session.getGroupService().getUidByUins([Uin])).uids.get(Uin); + uid = (await this.context.session.getGroupService().getUidByUins([Uin])).uids.get(Uin); if (uid) return uid; - uid = (await napCatCore.session.getUixConvertService().getUid([Uin])).uidInfo.get(Uin); + uid = (await this.context.session.getUixConvertService().getUid([Uin])).uidInfo.get(Uin); if (uid) return uid; console.log((await NTQQFriendApi.getBuddyIdMapCache(true))); uid = (await NTQQFriendApi.getBuddyIdMapCache(true)).getValue(Uin);//从Buddy缓存获取Uid if (uid) return uid; uid = (await NTQQFriendApi.getBuddyIdMap(true)).getValue(Uin); if (uid) return uid; - let unveifyUid = (await NTQQUserApi.getUserDetailInfoByUinV2(Uin)).detail.uid;//从QQ Native 特殊转换 + let unveifyUid = (await this.getUserDetailInfoByUinV2(Uin)).detail.uid;//从QQ Native 特殊转换 if (unveifyUid.indexOf("*") == -1) uid = unveifyUid; //if (uid) return uid; return uid; } //后期改成流水线处理 async getUinByUidV2(Uid: string) { - let uin = (await napCatCore.session.getProfileService().getUinByUid('FriendsServiceImpl', [Uid])).get(Uid); + let uin = (await this.context.session.getProfileService().getUinByUid('FriendsServiceImpl', [Uid])).get(Uid); if (uin) return uin; - uin = (await napCatCore.session.getGroupService().getUinByUids([Uid])).uins.get(Uid); + uin = (await this.context.session.getGroupService().getUinByUids([Uid])).uins.get(Uid); if (uin) return uin; - uin = (await napCatCore.session.getUixConvertService().getUin([Uid])).uinInfo.get(Uid); + uin = (await this.context.session.getUixConvertService().getUin([Uid])).uinInfo.get(Uid); if (uin) return uin; uin = (await NTQQFriendApi.getBuddyIdMapCache(true)).getKey(Uid);//从Buddy缓存获取Uin if (uin) return uin; uin = (await NTQQFriendApi.getBuddyIdMap(true)).getKey(Uid); if (uin) return uin; - uin = (await NTQQUserApi.getUserDetailInfo(Uid)).uin; //从QQ Native 转换 + uin = (await this.getUserDetailInfo(Uid)).uin; //从QQ Native 转换 return uin; } async getUidByUinV1(Uin: string) { // 通用转换开始尝试 - let uid = (await napCatCore.session.getUixConvertService().getUid([Uin])).uidInfo.get(Uin); + let uid = (await this.context.session.getUixConvertService().getUid([Uin])).uidInfo.get(Uin); // Uid 好友转 if (!uid) { Array.from(friends.values()).forEach((t) => { @@ -279,7 +272,7 @@ export class NTQQUserApi { } } if (!uid) { - let unveifyUid = (await NTQQUserApi.getUserDetailInfoByUin(Uin)).info.uid;//从QQ Native 特殊转换 方法三 + let unveifyUid = (await this.getUserDetailInfoByUin(Uin)).info.uid;//从QQ Native 特殊转换 方法三 if (unveifyUid.indexOf("*") == -1) { uid = unveifyUid; } @@ -287,7 +280,7 @@ export class NTQQUserApi { return uid; } async getUinByUidV1(Uid: string) { - let ret = await NTEventDispatch.CallNoListenerEvent + let ret = await this.core.eventWrapper.callNoListenerEvent <(Uin: string[]) => Promise<{ uinInfo: Map }>>( 'NodeIKernelUixConvertService/getUin', 5000, @@ -303,7 +296,7 @@ export class NTQQUserApi { }) } if (!uin) { - uin = (await NTQQUserApi.getUserDetailInfo(Uid)).uin; //从QQ Native 转换 + uin = (await this.getUserDetailInfo(Uid)).uin; //从QQ Native 转换 } // if (!uin) { @@ -315,19 +308,19 @@ export class NTQQUserApi { return uin; } async getRecentContactListSnapShot(count: number) { - return await napCatCore.session.getRecentContactService().getRecentContactListSnapShot(count); + return await this.context.session.getRecentContactService().getRecentContactListSnapShot(count); } async getRecentContactListSyncLimit(count: number) { - return await napCatCore.session.getRecentContactService().getRecentContactListSyncLimit(count); + return await this.context.session.getRecentContactService().getRecentContactListSyncLimit(count); } async getRecentContactListSync() { - return await napCatCore.session.getRecentContactService().getRecentContactListSync(); + return await this.context.session.getRecentContactService().getRecentContactListSync(); } async getRecentContactList() { - return await napCatCore.session.getRecentContactService().getRecentContactList(); + return await this.context.session.getRecentContactService().getRecentContactList(); } async getUserDetailInfoByUinV2(Uin: string) { - return await NTEventDispatch.CallNoListenerEvent + return await this.core.eventWrapper.callNoListenerEvent <(Uin: string) => Promise>( 'NodeIKernelProfileService/getUserDetailInfoByUin', 5000, @@ -335,15 +328,14 @@ export class NTQQUserApi { ); } async getUserDetailInfoByUin(Uin: string) { - return NTEventDispatch.CallNoListenerEvent + return this.core.eventWrapper.callNoListenerEvent <(Uin: string) => Promise>( 'NodeIKernelProfileService/getUserDetailInfoByUin', 5000, Uin ); } - @CacheClassFuncAsync(3600 * 1000, 'ClientKey') async forceFetchClientKey() { - return await napCatCore.session.getTicketService().forceFetchClientKey(''); + return await this.context.session.getTicketService().forceFetchClientKey(''); } } diff --git a/src/core/core.ts b/src/core/core.ts index c67937d2..b39c6b12 100644 --- a/src/core/core.ts +++ b/src/core/core.ts @@ -1,4 +1,4 @@ -import { WrapperNodeApi } from "@/core/wrapper"; +import { NTApiContext, WrapperNodeApi } from "@/core/wrapper"; import path from "node:path"; import fs from "node:fs"; import { InstanceContext } from "./wrapper"; @@ -7,7 +7,8 @@ import { proxiedListenerOf } from "@/common/utils/proxy-handler"; import { MsgListener, ProfileListener } from "./listeners"; import { sleep } from "@/common/utils/helper"; import { SelfInfo, LineDevice, SelfStatusInfo } from "./entities"; -import {LegacyNTEventWrapper} from "@/common/framework/event-legacy"; +import { LegacyNTEventWrapper } from "@/common/framework/event-legacy"; +import { NTQQGroupApi, NTQQMsgApi, NTQQUserApi } from "./apis"; export enum NapCatCoreWorkingEnv { Unknown = 0, @@ -27,6 +28,7 @@ export function loadQQWrapper(QQVersion: string): WrapperNodeApi { export class NapCatCore { readonly context: InstanceContext; + readonly ApiContext: NTApiContext; readonly eventWrapper: LegacyNTEventWrapper; // readonly eventChannel: NTEventChannel; @@ -38,8 +40,15 @@ export class NapCatCore { this.context = context; this.eventWrapper = new LegacyNTEventWrapper(context.wrapper, context.session); this.initNapCatCoreListeners().then().catch(console.error); + this.ApiContext = { + MsgApi: new NTQQMsgApi(this.context,this), + UserApi: new NTQQUserApi(this.context), + GroupApi: new NTQQGroupApi(this.context) + } + } + getApiContext() { + return this.ApiContext; } - // Renamed from 'InitDataListener' async initNapCatCoreListeners() { let msgListener = new MsgListener(); @@ -50,7 +59,7 @@ export class NapCatCore { this.context.session.getMsgService().addKernelMsgListener( new this.context.wrapper.NodeIKernelMsgListener(proxiedListenerOf(msgListener, this.context.logger)) ); - + const profileListener = new ProfileListener(); profileListener.onProfileDetailInfoChanged = (profile) => { if (profile.uid === this.selfInfo.uid) { diff --git a/src/core/entities/msg.ts b/src/core/entities/msg.ts index 3f5d1ab8..23fc931c 100644 --- a/src/core/entities/msg.ts +++ b/src/core/entities/msg.ts @@ -1,6 +1,5 @@ import { GroupMemberRole } from './group'; - export interface Peer { chatType: ChatType; peerUid: string; // 如果是群聊uid为群号,私聊uid就是加密的字符串 diff --git a/src/core/index.ts b/src/core/index.ts index 9e15dc13..88249339 100644 --- a/src/core/index.ts +++ b/src/core/index.ts @@ -1,2 +1,3 @@ export * from './core'; -export * from './wrapper' \ No newline at end of file +export * from './wrapper'; +export * from './entities'; \ No newline at end of file diff --git a/src/core/wrapper/context.ts b/src/core/wrapper/context.ts index 2074245c..8fc162c3 100644 --- a/src/core/wrapper/context.ts +++ b/src/core/wrapper/context.ts @@ -4,6 +4,7 @@ import { NapCatCoreWorkingEnv } from "@/core"; import { SelfInfo } from "../entities"; import { NodeIKernelLoginService } from "../services"; import { WrapperNodeApi, NodeIQQNTWrapperSession } from "@/core"; +import { NTQQGroupApi, NTQQMsgApi, NTQQUserApi } from "../apis"; export interface InstanceContext { readonly workingEnv: NapCatCoreWorkingEnv; @@ -13,3 +14,8 @@ export interface InstanceContext { readonly loginService: NodeIKernelLoginService; readonly basicInfoWrapper: QQBasicInfoWrapper; } +export interface NTApiContext { + MsgApi: NTQQMsgApi, + UserApi: NTQQUserApi, + GroupApi: NTQQGroupApi +} \ No newline at end of file