Compare commits

..

7 Commits

Author SHA1 Message Date
手瓜一十雪
c45f0dc289 Merge branch 'main' into newApi 2025-05-18 18:23:37 +08:00
手瓜一十雪
433ce9caef fix 2025-05-16 21:29:16 +08:00
手瓜一十雪
ba1acd624e feat: 迁移at 消息段 2025-05-16 21:21:22 +08:00
手瓜一十雪
a586796339 feat: 彻底扬了没用的 2025-05-16 21:19:04 +08:00
手瓜一十雪
2016a90198 feat: 测试代码 2025-05-16 21:12:28 +08:00
手瓜一十雪
b4bc4da7fc feat: 测试 2025-05-16 21:04:46 +08:00
手瓜一十雪
52c828192e feat: 斩杀快速操作 CQCode 调整消息和会话Id类型 2025-05-16 20:59:14 +08:00
161 changed files with 542 additions and 26181 deletions

View File

@@ -150,15 +150,3 @@ jobs:
NapCat.Shell.zip NapCat.Shell.zip
NapCat.Framework.Windows.Once.zip NapCat.Framework.Windows.Once.zip
draft: true draft: true
build-docker:
needs: release-napcat
runs-on: ubuntu-latest
steps:
- name: Dispatch Docker Build
run: |
curl -X POST \
-H "Authorization: Bearer ${{ secrets.NAPCAT_BUILD }}" \
-H "Accept: application/vnd.github.v3+json" \
https://api.github.com/repos/NapNeko/NapCat-Docker/actions/workflows/docker-publish.yml/dispatches \
-d '{"ref": "main"}'

1
.gitignore vendored
View File

@@ -1,5 +1,6 @@
# Develop # Develop
node_modules/ node_modules/
package-lock.json
pnpm-lock.yaml pnpm-lock.yaml
out/ out/
dist/ dist/

Binary file not shown.

View File

@@ -4,7 +4,7 @@
"name": "NapCatQQ", "name": "NapCatQQ",
"slug": "NapCat.Framework", "slug": "NapCat.Framework",
"description": "高性能的 OneBot 11 协议实现", "description": "高性能的 OneBot 11 协议实现",
"version": "4.8.93", "version": "4.7.63",
"icon": "./logo.png", "icon": "./logo.png",
"authors": [ "authors": [
{ {

File diff suppressed because it is too large Load Diff

View File

@@ -92,9 +92,7 @@ const MusicInsert = () => {
className="w-96" className="w-96"
fullWidth fullWidth
selectedKey={mode} selectedKey={mode}
onSelectionChange={(key) => { onSelectionChange={setMode}
if (key !== null) setMode(key)
}}
> >
<Tab title="主流平台" key="default" className="flex flex-col gap-2"> <Tab title="主流平台" key="default" className="flex flex-col gap-2">
<Select <Select

View File

@@ -26,7 +26,7 @@ const itemVariants = {
opacity: 1, opacity: 1,
scale: 1, scale: 1,
y: 0, y: 0,
transition: { type: 'spring' as const, stiffness: 300, damping: 20 } transition: { type: 'spring', stiffness: 300, damping: 20 }
} }
} }

View File

@@ -24,7 +24,9 @@ const oneBotHttpApiGroup = {
}, },
'/get_group_system_msg': { '/get_group_system_msg': {
description: '获取群系统消息', description: '获取群系统消息',
request: z.object({}), request: z.object({
group_id: z.union([z.string(), z.number()]).describe('群号')
}),
response: baseResponseSchema.extend({ response: baseResponseSchema.extend({
data: z.object({ data: z.object({
InvitedRequest: z InvitedRequest: z
@@ -35,7 +37,6 @@ const oneBotHttpApiGroup = {
invitor_uin: z.string().describe('邀请人 QQ 号'), invitor_uin: z.string().describe('邀请人 QQ 号'),
invitor_nick: z.string().describe('邀请人昵称'), invitor_nick: z.string().describe('邀请人昵称'),
group_id: z.string().describe('群号'), group_id: z.string().describe('群号'),
message: z.string().describe('入群回答'),
group_name: z.string().describe('群名称'), group_name: z.string().describe('群名称'),
checked: z.boolean().describe('是否已处理'), checked: z.boolean().describe('是否已处理'),
actor: z.string().describe('处理人 QQ 号') actor: z.string().describe('处理人 QQ 号')
@@ -49,7 +50,6 @@ const oneBotHttpApiGroup = {
requester_uin: z.string().describe('请求人 QQ 号'), requester_uin: z.string().describe('请求人 QQ 号'),
requester_nick: z.string().describe('请求人昵称'), requester_nick: z.string().describe('请求人昵称'),
group_id: z.string().describe('群号'), group_id: z.string().describe('群号'),
message: z.string().describe('入群回答'),
group_name: z.string().describe('群名称'), group_name: z.string().describe('群名称'),
checked: z.boolean().describe('是否已处理'), checked: z.boolean().describe('是否已处理'),
actor: z.string().describe('处理人 QQ 号') actor: z.string().describe('处理人 QQ 号')
@@ -604,7 +604,7 @@ const oneBotHttpApiGroup = {
response: baseResponseSchema.extend({ response: baseResponseSchema.extend({
data: z data: z
.object({ .object({
group_id: z.number().describe('群号'), group_id: z.string().describe('群号'),
current_talkative: z current_talkative: z
.object({ .object({
user_id: z.number().describe('QQ 号'), user_id: z.number().describe('QQ 号'),

View File

@@ -56,9 +56,9 @@ export default function TerminalPage() {
setTabs((prev) => [...prev, newTab]) setTabs((prev) => [...prev, newTab])
setSelectedTab(id) setSelectedTab(id)
} catch (error: unknown) { } catch (error) {
console.error('Failed to create terminal:', error) console.error('Failed to create terminal:', error)
toast.error((error as Error).message) toast.error('创建终端失败')
} }
} }

8301
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@@ -2,7 +2,7 @@
"name": "napcat", "name": "napcat",
"private": true, "private": true,
"type": "module", "type": "module",
"version": "4.8.93", "version": "4.7.63",
"scripts": { "scripts": {
"build:universal": "npm run build:webui && vite build --mode universal || exit 1", "build:universal": "npm run build:webui && vite build --mode universal || exit 1",
"build:framework": "npm run build:webui && vite build --mode framework || exit 1", "build:framework": "npm run build:webui && vite build --mode framework || exit 1",
@@ -18,14 +18,14 @@
}, },
"devDependencies": { "devDependencies": {
"@babel/preset-typescript": "^7.24.7", "@babel/preset-typescript": "^7.24.7",
"@eslint/compat": "^1.3.1", "@eslint/compat": "^1.2.2",
"@eslint/eslintrc": "^3.1.0", "@eslint/eslintrc": "^3.1.0",
"@eslint/js": "^9.30.1", "@eslint/js": "^9.14.0",
"@homebridge/node-pty-prebuilt-multiarch": "^0.12.0-beta.5", "@homebridge/node-pty-prebuilt-multiarch": "^0.12.0-beta.5",
"@log4js-node/log4js-api": "^1.0.2", "@log4js-node/log4js-api": "^1.0.2",
"@napneko/nap-proto-core": "^0.0.4", "@napneko/nap-proto-core": "^0.0.4",
"@rollup/plugin-node-resolve": "^16.0.0", "@rollup/plugin-node-resolve": "^16.0.0",
"@rollup/plugin-typescript": "^12.1.4", "@rollup/plugin-typescript": "^12.1.2",
"@sinclair/typebox": "^0.34.9", "@sinclair/typebox": "^0.34.9",
"@types/cors": "^2.8.17", "@types/cors": "^2.8.17",
"@types/express": "^5.0.0", "@types/express": "^5.0.0",
@@ -42,18 +42,18 @@
"async-mutex": "^0.5.0", "async-mutex": "^0.5.0",
"commander": "^13.0.0", "commander": "^13.0.0",
"cors": "^2.8.5", "cors": "^2.8.5",
"esbuild": "0.25.5", "esbuild": "0.25.4",
"eslint": "^9.14.0", "eslint": "^9.14.0",
"eslint-import-resolver-typescript": "^4.0.0", "eslint-import-resolver-typescript": "^4.0.0",
"eslint-plugin-import": "^2.29.1", "eslint-plugin-import": "^2.29.1",
"express-rate-limit": "^7.5.1", "express-rate-limit": "^7.5.0",
"fast-xml-parser": "^4.3.6", "fast-xml-parser": "^4.3.6",
"file-type": "^21.0.0", "file-type": "^20.0.0",
"globals": "^16.0.0", "globals": "^16.0.0",
"json5": "^2.2.3", "json5": "^2.2.3",
"multer": "^2.0.1", "multer": "^1.4.5-lts.1",
"typescript": "^5.3.3", "typescript": "^5.3.3",
"typescript-eslint": "^8.35.1", "typescript-eslint": "^8.13.0",
"vite": "^6.0.1", "vite": "^6.0.1",
"vite-plugin-cp": "^6.0.0", "vite-plugin-cp": "^6.0.0",
"vite-tsconfig-paths": "^5.1.0", "vite-tsconfig-paths": "^5.1.0",

View File

@@ -8,16 +8,12 @@ import { pipeline } from 'stream/promises';
import { fileURLToPath } from 'url'; import { fileURLToPath } from 'url';
import { LogWrapper } from './log'; import { LogWrapper } from './log';
const downloadOri = "https://github.com/NapNeko/ffmpeg-build/releases/download/v1.0.0/ffmpeg-7.1.1-win64.zip" const downloadOri = 'https://github.com/NapNeko/ffmpeg-build/releases/download/v1.0.0/ffmpeg-7.1.1-win64.zip';
const urls = [ const urls = [
"https://j.1win.ggff.net/" + downloadOri, 'https://github.moeyy.xyz/' + downloadOri,
"https://git.yylx.win/" + downloadOri, 'https://ghp.ci/' + downloadOri,
"https://ghfile.geekertao.top/" + downloadOri, 'https://gh.api.99988866.xyz/' + downloadOri,
"https://gh-proxy.net/" + downloadOri, 'https://gh.api.99988866.xyz/' + downloadOri,
"https://ghm.078465.xyz/" + downloadOri,
"https://gitproxy.127731.xyz/" + downloadOri,
"https://jiashu.1win.eu.org/" + downloadOri,
"https://github.tbedu.top/" + downloadOri,
downloadOri downloadOri
]; ];
@@ -354,11 +350,11 @@ export async function downloadFFmpegIfNotExists(log: LogWrapper) {
return { return {
path: path.join(currentPath, 'ffmpeg'), path: path.join(currentPath, 'ffmpeg'),
reset: true reset: true
} };
} }
return { return {
path: path.join(currentPath, 'ffmpeg'), path: path.join(currentPath, 'ffmpeg'),
reset: true reset: true
} };
} }

View File

@@ -182,28 +182,28 @@ export async function uriToLocalFile(dir: string, uri: string, filename: string
const filePath = path.join(dir, filename); const filePath = path.join(dir, filename);
switch (UriType) { switch (UriType) {
case FileUriType.Local: { case FileUriType.Local: {
const fileExt = path.extname(HandledUri); const fileExt = path.extname(HandledUri);
const localFileName = path.basename(HandledUri, fileExt) + fileExt; const localFileName = path.basename(HandledUri, fileExt) + fileExt;
const tempFilePath = path.join(dir, filename + fileExt); const tempFilePath = path.join(dir, filename + fileExt);
fs.copyFileSync(HandledUri, tempFilePath); fs.copyFileSync(HandledUri, tempFilePath);
return { success: true, errMsg: '', fileName: localFileName, path: tempFilePath }; return { success: true, errMsg: '', fileName: localFileName, path: tempFilePath };
} }
case FileUriType.Remote: { case FileUriType.Remote: {
const buffer = await httpDownload({ url: HandledUri, headers: headers ?? {} }); const buffer = await httpDownload({ url: HandledUri, headers: headers ?? {} });
fs.writeFileSync(filePath, buffer); fs.writeFileSync(filePath, buffer);
return { success: true, errMsg: '', fileName: filename, path: filePath }; return { success: true, errMsg: '', fileName: filename, path: filePath };
} }
case FileUriType.Base64: { case FileUriType.Base64: {
const base64 = HandledUri.replace(/^base64:\/\//, ''); const base64 = HandledUri.replace(/^base64:\/\//, '');
const base64Buffer = Buffer.from(base64, 'base64'); const base64Buffer = Buffer.from(base64, 'base64');
fs.writeFileSync(filePath, base64Buffer); fs.writeFileSync(filePath, base64Buffer);
return { success: true, errMsg: '', fileName: filename, path: filePath }; return { success: true, errMsg: '', fileName: filename, path: filePath };
} }
default: default:
return { success: false, errMsg: `识别URL失败, uri= ${uri}`, fileName: '', path: '' }; return { success: false, errMsg: `识别URL失败, uri= ${uri}`, fileName: '', path: '' };
} }
} }

View File

@@ -1,6 +1,4 @@
import { Peer } from '@/core'; import { Peer } from '@/core';
import crypto from 'crypto';
export class LimitedHashTable<K, V> { export class LimitedHashTable<K, V> {
private readonly keyToValue: Map<K, V> = new Map(); private readonly keyToValue: Map<K, V> = new Map();
private readonly valueToKey: Map<V, K> = new Map(); private readonly valueToKey: Map<V, K> = new Map();
@@ -78,65 +76,19 @@ export class LimitedHashTable<K, V> {
} }
class MessageUniqueWrapper { class MessageUniqueWrapper {
private readonly msgDataMap: LimitedHashTable<string, number>; constructor() {
private readonly msgIdMap: LimitedHashTable<string, number>;
constructor(maxMap: number = 5000) {
this.msgIdMap = new LimitedHashTable<string, number>(maxMap);
this.msgDataMap = new LimitedHashTable<string, number>(maxMap);
} }
getRecentMsgIds(Peer: Peer, size: number): string[] { getOutputData(peer: Peer, msg_id: string, seq: string): string {
const heads = this.msgIdMap.getHeads(size); return `${peer.chatType}|${msg_id}|${peer.peerUid}|${seq}`;
if (!heads) { }
return [];
getInnerData(shortId: string): { MsgId: string; Peer: Peer, seq: string } | undefined {
const [chatType, msgId, peerUid, seq] = shortId.split('|');
if (!chatType || !msgId || !peerUid || !seq) {
return undefined;
} }
const data = heads.map((t) => MessageUnique.getMsgIdAndPeerByShortId(t.value)); return { MsgId: msgId, Peer: { chatType: parseInt(chatType), peerUid, guildId: '' }, seq: seq };
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);
}
createUniqueMsgId(peer: Peer, msgId: string) {
const key = `${msgId}|${peer.chatType}|${peer.peerUid}`;
const hash = crypto.createHash('md5').update(key).digest();
if (hash[0]) {
//设置第一个bit为0 保证shortId为正数
hash[0] &= 0x7f;
}
const shortId = hash.readInt32BE(0);
//减少性能损耗
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 ?? '0'),
peerUid: peerUid ?? '',
guildId: '',
};
return { MsgId: msgId ?? '0', 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);
} }
} }

View File

@@ -13,15 +13,11 @@ export class NapCatPathWrapper {
constructor(mainPath: string = dirname(fileURLToPath(import.meta.url))) { constructor(mainPath: string = dirname(fileURLToPath(import.meta.url))) {
this.binaryPath = mainPath; this.binaryPath = mainPath;
let writePath: string; let writePath: string;
if (os.platform() === 'darwin') {
if (process.env['NAPCAT_WORKDIR']) {
writePath = process.env['NAPCAT_WORKDIR'];
} else if (os.platform() === 'darwin') {
writePath = path.join(os.homedir(), 'Library', 'Application Support', 'QQ', 'NapCat'); writePath = path.join(os.homedir(), 'Library', 'Application Support', 'QQ', 'NapCat');
} else { } else {
writePath = this.binaryPath; writePath = this.binaryPath;
} }
this.logsPath = path.join(writePath, 'logs'); this.logsPath = path.join(writePath, 'logs');
this.configPath = path.join(writePath, 'config'); this.configPath = path.join(writePath, 'config');
this.cachePath = path.join(writePath, 'cache'); this.cachePath = path.join(writePath, 'cache');

View File

@@ -1 +1 @@
export const napCatVersion = '4.8.93'; export const napCatVersion = '4.7.63';

View File

@@ -9,7 +9,7 @@ export async function runTask<T, R>(workerScript: string, taskData: T): Promise<
console.error('Worker Log--->:', (result as { log: string }).log); console.error('Worker Log--->:', (result as { log: string }).log);
} }
if ((result as any)?.error) { if ((result as any)?.error) {
reject(new Error("Worker error: " + (result as { error: string }).error)); reject(new Error('Worker error: ' + (result as { error: string }).error));
} }
resolve(result); resolve(result);
}); });

View File

@@ -45,7 +45,7 @@ export class NTQQFileApi {
'https://secret-service.bietiaop.com/rkeys', 'https://secret-service.bietiaop.com/rkeys',
'http://ss.xingzhige.com/music_card/rkey', 'http://ss.xingzhige.com/music_card/rkey',
], ],
this.context.logger this.context.logger
); );
} }
@@ -379,18 +379,18 @@ export class NTQQFileApi {
element.elementType === ElementType.FILE element.elementType === ElementType.FILE
) { ) {
switch (element.elementType) { switch (element.elementType) {
case ElementType.PIC: case ElementType.PIC:
element.picElement!.sourcePath = elementResults?.[elementIndex] ?? ''; element.picElement!.sourcePath = elementResults?.[elementIndex] ?? '';
break; break;
case ElementType.VIDEO: case ElementType.VIDEO:
element.videoElement!.filePath = elementResults?.[elementIndex] ?? ''; element.videoElement!.filePath = elementResults?.[elementIndex] ?? '';
break; break;
case ElementType.PTT: case ElementType.PTT:
element.pttElement!.filePath = elementResults?.[elementIndex] ?? ''; element.pttElement!.filePath = elementResults?.[elementIndex] ?? '';
break; break;
case ElementType.FILE: case ElementType.FILE:
element.fileElement!.filePath = elementResults?.[elementIndex] ?? ''; element.fileElement!.filePath = elementResults?.[elementIndex] ?? '';
break; break;
} }
elementIndex++; elementIndex++;
} }

View File

@@ -110,7 +110,7 @@ export class NTQQFriendApi {
time: item.reqTime, // 信息字段 time: item.reqTime, // 信息字段
type: 'doubt' //保留字段 type: 'doubt' //保留字段
}; };
})) }));
return requests; return requests;
} }
} }

View File

@@ -10,14 +10,11 @@ import {
GroupNotify, GroupNotify,
GroupInfoSource, GroupInfoSource,
ShutUpGroupMember, ShutUpGroupMember,
Peer,
ChatType,
} from '@/core'; } from '@/core';
import { isNumeric, solveAsyncProblem } from '@/common/helper'; import { isNumeric, solveAsyncProblem } from '@/common/helper';
import { LimitedHashTable } from '@/common/message-unique'; import { LimitedHashTable } from '@/common/message-unique';
import { NTEventWrapper } from '@/common/event'; import { NTEventWrapper } from '@/common/event';
import { CancelableTask, TaskExecutor } from '@/common/cancel-task'; import { CancelableTask, TaskExecutor } from '@/common/cancel-task';
import { createGroupDetailInfoV2Param, createGroupExtFilter, createGroupExtInfo } from '../data';
export class NTQQGroupApi { export class NTQQGroupApi {
context: InstanceContext; context: InstanceContext;
@@ -50,22 +47,6 @@ export class NTQQGroupApi {
this.initCache().then().catch(e => this.context.logger.logError(e)); this.initCache().then().catch(e => this.context.logger.logError(e));
} }
async createGrayTip(groupCode: string, tip: string) {
return this.context.session.getMsgService().addLocalJsonGrayTipMsg(
{
chatType: ChatType.KCHATTYPEGROUP,
peerUid: groupCode,
} as Peer,
{
busiId: 2201,
jsonStr: JSON.stringify({ "align": "center", "items": [{ "txt": tip, "type": "nor" }] }),
recentAbstract: tip,
isServer: false
},
true,
true
)
}
async initCache() { async initCache() {
for (const group of await this.getGroups(true)) { for (const group of await this.getGroups(true)) {
this.refreshGroupMemberCache(group.groupCode, false).then().catch(e => this.context.logger.logError(e)); this.refreshGroupMemberCache(group.groupCode, false).then().catch(e => this.context.logger.logError(e));
@@ -114,58 +95,6 @@ export class NTQQGroupApi {
return this.context.session.getGroupService().setHeader(groupCode, filePath); return this.context.session.getGroupService().setHeader(groupCode, filePath);
} }
// 0 0 无需管理员审核
// 0 2 需要管理员审核
// 1 2 禁止Bot入群( 最好只传一个1 )
async setGroupRobotAddOption(groupCode: string, robotMemberSwitch?: number, robotMemberExamine?: number) {
let extInfo = createGroupExtInfo(groupCode);
let groupExtFilter = createGroupExtFilter();
if (robotMemberSwitch !== undefined) {
extInfo.extInfo.inviteRobotMemberSwitch = robotMemberSwitch;
groupExtFilter.inviteRobotMemberSwitch = 1;
}
if (robotMemberExamine !== undefined) {
extInfo.extInfo.inviteRobotMemberExamine = robotMemberExamine;
groupExtFilter.inviteRobotMemberExamine = 1;
}
return this.context.session.getGroupService().modifyGroupExtInfoV2(extInfo, groupExtFilter);
}
async setGroupAddOption(groupCode: string, option: {
addOption: number;
groupQuestion?: string;
groupAnswer?: string;
}) {
let param = createGroupDetailInfoV2Param(groupCode);
// 设置要修改的目标
param.filter.addOption = 1;
if (option.addOption == 4 || option.addOption == 5) {
// 4 问题进入答案 5 问题管理员批准
param.filter.groupQuestion = 1;
param.filter.groupAnswer = option.addOption == 4 ? 1 : 0;
param.modifyInfo.groupQuestion = option.groupQuestion || '';
param.modifyInfo.groupAnswer = option.addOption == 4 ? option.groupAnswer || '' : '';
}
param.modifyInfo.addOption = option.addOption;
return this.context.session.getGroupService().modifyGroupDetailInfoV2(param, 0);
}
async setGroupSearch(groupCode: string, option: {
noCodeFingerOpenFlag?: number;
noFingerOpenFlag?: number;
}) {
let param = createGroupDetailInfoV2Param(groupCode);
if (option.noCodeFingerOpenFlag) {
param.filter.noCodeFingerOpenFlag = 1;
param.modifyInfo.noCodeFingerOpenFlag = option.noCodeFingerOpenFlag;
}
if (option.noFingerOpenFlag) {
param.filter.noFingerOpenFlag = 1;
param.modifyInfo.noFingerOpenFlag = option.noFingerOpenFlag;
}
return this.context.session.getGroupService().modifyGroupDetailInfoV2(param, 0);
}
async getGroups(forced: boolean = false) { async getGroups(forced: boolean = false) {
const [, , groupList] = await this.core.eventWrapper.callNormalEventV2( const [, , groupList] = await this.core.eventWrapper.callNormalEventV2(
'NodeIKernelGroupService/getGroupList', 'NodeIKernelGroupService/getGroupList',

View File

@@ -264,7 +264,7 @@ export class NTQQWebApi {
async getGroupHonorInfo(groupCode: string, getType: WebHonorType) { async getGroupHonorInfo(groupCode: string, getType: WebHonorType) {
const cookieObject = await this.core.apis.UserApi.getCookies('qun.qq.com'); const cookieObject = await this.core.apis.UserApi.getCookies('qun.qq.com');
let HonorInfo = { let HonorInfo = {
group_id: Number(groupCode), group_id: groupCode,
current_talkative: {}, current_talkative: {},
talkative_list: [], talkative_list: [],
performer_list: [], performer_list: [],

View File

@@ -1,245 +0,0 @@
import { GroupDetailInfoV2Param, GroupExtInfo, GroupExtFilter } from "../types";
export function createGroupDetailInfoV2Param(group_code: string): GroupDetailInfoV2Param {
return {
groupCode: group_code,
filter:
{
noCodeFingerOpenFlag: 0,
noFingerOpenFlag: 0,
groupName: 0,
classExt: 0,
classText: 0,
fingerMemo: 0,
richFingerMemo: 0,
tagRecord: 0,
groupGeoInfo:
{
ownerUid: 0,
setTime: 0,
cityId: 0,
longitude: 0,
latitude: 0,
geoContent: 0,
poiId: 0
},
groupExtAdminNum: 0,
flag: 0,
groupMemo: 0,
groupAioSkinUrl: 0,
groupBoardSkinUrl: 0,
groupCoverSkinUrl: 0,
groupGrade: 0,
activeMemberNum: 0,
certificationType: 0,
certificationText: 0,
groupNewGuideLines:
{
enabled: 0,
content: 0
},
groupFace: 0,
addOption: 0,
shutUpTime: 0,
groupTypeFlag: 0,
appPrivilegeFlag: 0,
appPrivilegeMask: 0,
groupExtOnly:
{
tribeId: 0,
moneyForAddGroup: 0
}, groupSecLevel: 0,
groupSecLevelInfo: 0,
subscriptionUin: 0,
subscriptionUid: "",
allowMemberInvite: 0,
groupQuestion: 0,
groupAnswer: 0,
groupFlagExt3: 0,
groupFlagExt3Mask: 0,
groupOpenAppid: 0,
rootId: 0,
msgLimitFrequency: 0,
hlGuildAppid: 0,
hlGuildSubType: 0,
hlGuildOrgId: 0,
groupFlagExt4: 0,
groupFlagExt4Mask: 0,
groupSchoolInfo: {
location: 0,
grade: 0,
school: 0
},
groupCardPrefix:
{
introduction: 0,
rptPrefix: 0
}, allianceId: 0,
groupFlagPro1: 0,
groupFlagPro1Mask: 0
},
modifyInfo: {
noCodeFingerOpenFlag: 0,
noFingerOpenFlag: 0,
groupName: "",
classExt: 0,
classText: "",
fingerMemo: "",
richFingerMemo: "",
tagRecord: [],
groupGeoInfo: {
ownerUid: "",
SetTime: 0,
CityId: 0,
Longitude: "",
Latitude: "",
GeoContent: "",
poiId: ""
},
groupExtAdminNum: 0,
flag: 0,
groupMemo: "",
groupAioSkinUrl: "",
groupBoardSkinUrl: "",
groupCoverSkinUrl: "",
groupGrade: 0,
activeMemberNum: 0,
certificationType: 0,
certificationText: "",
groupNewGuideLines: {
enabled: false,
content: ""
}, groupFace: 0,
addOption: 0,
shutUpTime: 0,
groupTypeFlag: 0,
appPrivilegeFlag: 0,
appPrivilegeMask: 0,
groupExtOnly: {
tribeId: 0,
moneyForAddGroup: 0
},
groupSecLevel: 0,
groupSecLevelInfo: 0,
subscriptionUin: "",
subscriptionUid: "",
allowMemberInvite: 0,
groupQuestion: "",
groupAnswer: "",
groupFlagExt3: 0,
groupFlagExt3Mask: 0,
groupOpenAppid: 0,
rootId: "",
msgLimitFrequency: 0,
hlGuildAppid: 0,
hlGuildSubType: 0,
hlGuildOrgId: 0,
groupFlagExt4: 0,
groupFlagExt4Mask: 0,
groupSchoolInfo: {
location: "",
grade: 0,
school: ""
},
groupCardPrefix:
{
introduction: "",
rptPrefix: []
},
allianceId: "",
groupFlagPro1: 0,
groupFlagPro1Mask: 0
}
}
}
export function createGroupExtInfo(group_code: string): GroupExtInfo {
return {
groupCode: group_code,
resultCode: 0,
extInfo: {
groupInfoExtSeq: 0,
reserve: 0,
luckyWordId: '',
lightCharNum: 0,
luckyWord: '',
starId: 0,
essentialMsgSwitch: 0,
todoSeq: 0,
blacklistExpireTime: 0,
isLimitGroupRtc: 0,
companyId: 0,
hasGroupCustomPortrait: 0,
bindGuildId: '',
groupOwnerId: {
memberUin: '',
memberUid: '',
memberQid: '',
},
essentialMsgPrivilege: 0,
msgEventSeq: '',
inviteRobotSwitch: 0,
gangUpId: '',
qqMusicMedalSwitch: 0,
showPlayTogetherSwitch: 0,
groupFlagPro1: '',
groupBindGuildIds: {
guildIds: [],
},
viewedMsgDisappearTime: '',
groupExtFlameData: {
switchState: 0,
state: 0,
dayNums: [],
version: 0,
updateTime: '',
isDisplayDayNum: false,
},
groupBindGuildSwitch: 0,
groupAioBindGuildId: '',
groupExcludeGuildIds: {
guildIds: [],
},
fullGroupExpansionSwitch: 0,
fullGroupExpansionSeq: '',
inviteRobotMemberSwitch: 0,
inviteRobotMemberExamine: 0,
groupSquareSwitch: 0,
}
}
}
export function createGroupExtFilter(): GroupExtFilter {
return {
groupInfoExtSeq: 0,
reserve: 0,
luckyWordId: 0,
lightCharNum: 0,
luckyWord: 0,
starId: 0,
essentialMsgSwitch: 0,
todoSeq: 0,
blacklistExpireTime: 0,
isLimitGroupRtc: 0,
companyId: 0,
hasGroupCustomPortrait: 0,
bindGuildId: 0,
groupOwnerId: 0,
essentialMsgPrivilege: 0,
msgEventSeq: 0,
inviteRobotSwitch: 0,
gangUpId: 0,
qqMusicMedalSwitch: 0,
showPlayTogetherSwitch: 0,
groupFlagPro1: 0,
groupBindGuildIds: 0,
viewedMsgDisappearTime: 0,
groupExtFlameData: 0,
groupBindGuildSwitch: 0,
groupAioBindGuildId: 0,
groupExcludeGuildIds: 0,
fullGroupExpansionSwitch: 0,
fullGroupExpansionSeq: 0,
inviteRobotMemberSwitch: 0,
inviteRobotMemberExamine: 0,
groupSquareSwitch: 0,
}
};

View File

@@ -1 +0,0 @@
export * from "./group";

View File

@@ -294,49 +294,5 @@
"9.9.19-35184": { "9.9.19-35184": {
"appid": 537291048, "appid": 537291048,
"qua": "V1_WIN_NQ_9.9.19_35184_GW_B" "qua": "V1_WIN_NQ_9.9.19_35184_GW_B"
},
"3.2.17-35341": {
"appid": 537291383,
"qua": "V1_LNX_NQ_3.2.17_35341_GW_B"
},
"9.9.19-35341": {
"appid": 537291347,
"qua": "V1_WIN_NQ_9.9.19_35341_GW_B"
},
"9.9.19-35469": {
"appid": 537291398,
"qua": "V1_WIN_NQ_9.9.19_35469_GW_B"
},
"3.2.18-35951": {
"appid": 537296013,
"qua": "V1_LNX_NQ_3.2.18_35951_GW_B"
},
"9.9.20-35951": {
"appid": 537295977,
"qua": "V1_WIN_NQ_9.9.20_35951_GW_B"
},
"3.2.18-36580": {
"appid": 537298509,
"qua": "V1_LNX_NQ_3.2.18_36580_GW_B"
},
"9.9.20-36580": {
"appid": 537298473,
"qua": "V1_WIN_NQ_9.9.20_36580_GW_B"
},
"9.9.20-37012": {
"appid": 537304071,
"qua": "V1_WIN_NQ_9.9.20_37012_GW_B"
},
"3.2.18-37012": {
"appid": 537304107,
"qua": "V1_LNX_NQ_3.2.18_37012_GW_B"
},
"3.2.18-37051": {
"appid": 537304158,
"qua": "V1_LNX_NQ_3.2.18_37051_GW_B"
},
"9.9.20-37051": {
"appid": 537304122,
"qua": "V1_WIN_NQ_9.9.20_37051_GW_B"
} }
} }

View File

@@ -378,65 +378,5 @@
"9.9.19-35184-x64": { "9.9.19-35184-x64": {
"send": "3BE5A10", "send": "3BE5A10",
"recv": "3BEA210" "recv": "3BEA210"
},
"9.9.19-35341-x64": {
"send": "3BF1D50",
"recv": "3BF6550"
},
"9.9.19-35469-x64": {
"send": "3BF1D50",
"recv": "3BF6550"
},
"3.2.17-35341-x64": {
"send": "AE2F700",
"recv": "AE33120"
},
"3.2.17-35341-arm64": {
"send": "778D840",
"recv": "7791170"
},
"9.9.20-35951-x64": {
"send": "3034BAC",
"recv": "3038354"
},
"3.2.18-35951-x64": {
"send": "AFBBB00",
"recv": "AFBF520"
},
"9.9.20-36580-x64": {
"send": "30824B8",
"recv": "3085C5C"
},
"3.2.18-36580-x64": {
"send": "B0853E0",
"recv": "B088E60"
},
"3.2.18-36580-arm64": {
"send": "793DAC8",
"recv": "7941458"
},
"3.2.18-37012-x64": {
"send": "B20F960",
"recv": "B2133E0"
},
"3.2.18-37012-arm64": {
"send": "7A19E00",
"recv": "7A1D790"
},
"9.9.20-37012-x64": {
"send": "30CC958",
"recv": "30D00FC"
},
"3.2.18-37051-x64": {
"send": "B20F960",
"recv": "B2133E0"
},
"3.2.18-37051-arm64": {
"send": "7A19E00",
"recv": "7A1D790"
},
"9.9.20-37051-x64": {
"send": "30CC958",
"recv": "30D00FC"
} }
} }

View File

@@ -40,8 +40,7 @@ export class NativePacketClient extends IPacketClient {
async init(_pid: number, recv: string, send: string): Promise<void> { async init(_pid: number, recv: string, send: string): Promise<void> {
const platform = process.platform + '.' + process.arch; const platform = process.platform + '.' + process.arch;
const isNewQQ = this.napcore.basicInfo.requireMinNTQQBuild("36580"); const moehoo_path = path.join(dirname(fileURLToPath(import.meta.url)), './moehoo/MoeHoo.' + platform + '.node');
const moehoo_path = path.join(dirname(fileURLToPath(import.meta.url)), './moehoo/MoeHoo.' + platform + (isNewQQ ? '.new' : '') + '.node');
process.dlopen(this.MoeHooExport, moehoo_path, constants.dlopen.RTLD_LAZY); process.dlopen(this.MoeHooExport, moehoo_path, constants.dlopen.RTLD_LAZY);
this.MoeHooExport.exports.InitHook?.(send, recv, (type: number, _uin: string, cmd: string, seq: number, hex_data: string) => { this.MoeHooExport.exports.InitHook?.(send, recv, (type: number, _uin: string, cmd: string, seq: number, hex_data: string) => {

View File

@@ -1,7 +1,6 @@
import { NapCatCore } from '@/core'; import { NapCatCore } from '@/core';
export interface NapCoreCompatBasicInfo { export interface NapCoreCompatBasicInfo {
readonly requireMinNTQQBuild: (buildVer: string) => boolean;
readonly uin: number; readonly uin: number;
readonly uid: string; readonly uid: string;
readonly uin2uid: (uin: number) => Promise<string>; readonly uin2uid: (uin: number) => Promise<string>;
@@ -22,7 +21,6 @@ export class NapCoreContext {
get basicInfo() { get basicInfo() {
return { return {
requireMinNTQQBuild: (buildVer: string) => this.core.context.basicInfoWrapper.requireMinNTQQBuild(buildVer),
uin: +this.core.selfInfo.uin, uin: +this.core.selfInfo.uin,
uid: this.core.selfInfo.uid, uid: this.core.selfInfo.uid,
uin2uid: (uin: number) => this.core.apis.UserApi.getUidByUinV2(String(uin)).then(res => res ?? ''), uin2uid: (uin: number) => this.core.apis.UserApi.getUidByUinV2(String(uin)).then(res => res ?? ''),

View File

@@ -30,8 +30,13 @@ export class PacketOperationContext {
return await this.context.client.sendOidbPacket(pkt, rsp); return await this.context.client.sendOidbPacket(pkt, rsp);
} }
async SendPoke(is_group: boolean, peer: number, target?: number) { async GroupPoke(groupUin: number, uin: number) {
const req = trans.SendPoke.build(is_group, peer, target ?? peer); const req = trans.SendPoke.build(uin, groupUin);
await this.context.client.sendOidbPacket(req);
}
async FriendPoke(uin: number) {
const req = trans.SendPoke.build(uin);
await this.context.client.sendOidbPacket(req); await this.context.client.sendOidbPacket(req);
} }
@@ -180,9 +185,9 @@ export class PacketOperationContext {
const ps = msg.map((m) => { const ps = msg.map((m) => {
return m.msg.map(async (e) => { return m.msg.map(async (e) => {
if (e instanceof PacketMsgReplyElement && !e.targetElems) { if (e instanceof PacketMsgReplyElement && !e.targetElems) {
this.context.logger.debug(`Cannot find reply element's targetElems, prepare to fetch it...`); this.context.logger.debug('Cannot find reply element\'s targetElems, prepare to fetch it...');
if (!e.targetPeer?.peerUid) { if (!e.targetPeer?.peerUid) {
this.context.logger.error(`targetPeer is undefined!`); this.context.logger.error('targetPeer is undefined!');
} }
let targetMsg: NapProtoEncodeStructType<typeof PushMsgBody>[] | undefined; let targetMsg: NapProtoEncodeStructType<typeof PushMsgBody>[] | undefined;
if (e.isGroupReply) { if (e.isGroupReply) {
@@ -195,7 +200,7 @@ export class PacketOperationContext {
} }
}); });
}).flat(); }).flat();
await Promise.all(ps) await Promise.all(ps);
await this.UploadResources(msg, groupUin); await this.UploadResources(msg, groupUin);
} }
@@ -203,14 +208,14 @@ export class PacketOperationContext {
const req = trans.FetchGroupMessage.build(groupUin, startSeq, endSeq); const req = trans.FetchGroupMessage.build(groupUin, startSeq, endSeq);
const resp = await this.context.client.sendOidbPacket(req, true); const resp = await this.context.client.sendOidbPacket(req, true);
const res = trans.FetchGroupMessage.parse(resp); const res = trans.FetchGroupMessage.parse(resp);
return res.body.messages return res.body.messages;
} }
async FetchC2CMessage(targetUid: string, startSeq: number, endSeq: number): Promise<NapProtoDecodeStructType<typeof PushMsgBody>[]> { async FetchC2CMessage(targetUid: string, startSeq: number, endSeq: number): Promise<NapProtoDecodeStructType<typeof PushMsgBody>[]> {
const req = trans.FetchC2CMessage.build(targetUid, startSeq, endSeq); const req = trans.FetchC2CMessage.build(targetUid, startSeq, endSeq);
const resp = await this.context.client.sendOidbPacket(req, true); const resp = await this.context.client.sendOidbPacket(req, true);
const res = trans.FetchC2CMessage.parse(resp); const res = trans.FetchC2CMessage.parse(resp);
return res.messages return res.messages;
} }
async UploadForwardMsg(msg: PacketMsg[], groupUin: number = 0) { async UploadForwardMsg(msg: PacketMsg[], groupUin: number = 0) {

View File

@@ -8,13 +8,13 @@ class SendPoke extends PacketTransformer<typeof proto.OidbSvcTrpcTcpBase> {
super(); super();
} }
build(is_group: boolean, peer: number, target: number): OidbPacket { build(peer: number, group?: number): OidbPacket {
const payload = { const data = new NapProtoMsg(proto.OidbSvcTrpcTcp0XED3_1).encode({
uin: target, uin: peer,
ext: 0, groupUin: group,
...(is_group ? { groupUin: peer } : { friendUin: peer }) friendUin: group ?? peer,
}; ext: 0
const data = new NapProtoMsg(proto.OidbSvcTrpcTcp0XED3_1).encode(payload); });
return OidbBase.build(0xED3, 1, data); return OidbBase.build(0xED3, 1, data);
} }

View File

@@ -7,7 +7,7 @@ class OidbBase extends PacketTransformer<typeof proto.OidbSvcTrpcTcpBase> {
super(); super();
} }
build(cmd: number, subCmd: number, body: Uint8Array, isUid: boolean = true, _isLafter: boolean = false): OidbPacket { build(cmd: number, subCmd: number, body: Uint8Array, isUid: boolean = true, isLafter: boolean = false): OidbPacket {
const data = new NapProtoMsg(proto.OidbSvcTrpcTcpBase).encode({ const data = new NapProtoMsg(proto.OidbSvcTrpcTcpBase).encode({
command: cmd, command: cmd,
subCommand: subCmd, subCommand: subCmd,

View File

@@ -8,22 +8,10 @@ import {
GroupNotifyMsgType, GroupNotifyMsgType,
NTGroupRequestOperateTypes, NTGroupRequestOperateTypes,
KickMemberV2Req, KickMemberV2Req,
GroupDetailInfoV2Param,
GroupExtInfo,
GroupExtFilter,
} from '@/core/types'; } from '@/core/types';
import { GeneralCallResult } from '@/core/services/common'; import { GeneralCallResult } from '@/core/services/common';
export interface NodeIKernelGroupService { export interface NodeIKernelGroupService {
modifyGroupExtInfoV2(groupExtInfo: GroupExtInfo, groupExtFilter: GroupExtFilter): Promise<GeneralCallResult &
{
result: {
groupCode: string,
result: number
}
}>;
// ---> // --->
// 待启用 For Next Version 3.2.0 // 待启用 For Next Version 3.2.0
// isTroopMember ? 0 : 111 // isTroopMember ? 0 : 111
@@ -181,9 +169,6 @@ export interface NodeIKernelGroupService {
modifyGroupDetailInfo(groupCode: string, arg: unknown): void; modifyGroupDetailInfo(groupCode: string, arg: unknown): void;
// 第二个参数在大多数情况为0 设置群成员权限 例如上传群文件权限和群成员付费/加入邀请加入时为8
modifyGroupDetailInfoV2(param: GroupDetailInfoV2Param, arg: number): Promise<GeneralCallResult>;
setGroupMsgMask(groupCode: string, arg: unknown): void; setGroupMsgMask(groupCode: string, arg: unknown): void;
changeGroupShieldSettingTemp(groupCode: string, arg: unknown): void; changeGroupShieldSettingTemp(groupCode: string, arg: unknown): void;

View File

@@ -58,7 +58,6 @@ export interface GrayTipRovokeElement {
operatorUid: string; operatorUid: string;
operatorNick: string; operatorNick: string;
operatorRemark: string; operatorRemark: string;
isSelfOperate: boolean; // 是否是自己撤回的
operatorMemRemark?: string; operatorMemRemark?: string;
wording: string; // 自定义的撤回提示语 wording: string; // 自定义的撤回提示语
} }

View File

@@ -1,97 +1,4 @@
import { QQLevel, NTSex } from './user'; import { QQLevel, NTSex } from './user';
export interface GroupExtInfo {
groupCode: string;
resultCode: number;
extInfo: EXTInfo;
}
export interface GroupExtFilter {
groupInfoExtSeq: number;
reserve: number;
luckyWordId: number;
lightCharNum: number;
luckyWord: number;
starId: number;
essentialMsgSwitch: number;
todoSeq: number;
blacklistExpireTime: number;
isLimitGroupRtc: number;
companyId: number;
hasGroupCustomPortrait: number;
bindGuildId: number;
groupOwnerId: number;
essentialMsgPrivilege: number;
msgEventSeq: number;
inviteRobotSwitch: number;
gangUpId: number;
qqMusicMedalSwitch: number;
showPlayTogetherSwitch: number;
groupFlagPro1: number;
groupBindGuildIds: number;
viewedMsgDisappearTime: number;
groupExtFlameData: number;
groupBindGuildSwitch: number;
groupAioBindGuildId: number;
groupExcludeGuildIds: number;
fullGroupExpansionSwitch: number;
fullGroupExpansionSeq: number;
inviteRobotMemberSwitch: number;
inviteRobotMemberExamine: number;
groupSquareSwitch: number;
};
export interface EXTInfo {
groupInfoExtSeq: number;
reserve: number;
luckyWordId: string;
lightCharNum: number;
luckyWord: string;
starId: number;
essentialMsgSwitch: number;
todoSeq: number;
blacklistExpireTime: number;
isLimitGroupRtc: number;
companyId: number;
hasGroupCustomPortrait: number;
bindGuildId: string;
groupOwnerId: GroupOwnerID;
essentialMsgPrivilege: number;
msgEventSeq: string;
inviteRobotSwitch: number;
gangUpId: string;
qqMusicMedalSwitch: number;
showPlayTogetherSwitch: number;
groupFlagPro1: string;
groupBindGuildIds: GroupGuildIDS;
viewedMsgDisappearTime: string;
groupExtFlameData: GroupEXTFlameData;
groupBindGuildSwitch: number;
groupAioBindGuildId: string;
groupExcludeGuildIds: GroupGuildIDS;
fullGroupExpansionSwitch: number;
fullGroupExpansionSeq: string;
inviteRobotMemberSwitch: number;
inviteRobotMemberExamine: number;
groupSquareSwitch: number;
}
export interface GroupGuildIDS {
guildIds: any[];
}
export interface GroupEXTFlameData {
switchState: number;
state: number;
dayNums: any[];
version: number;
updateTime: string;
isDisplayDayNum: boolean;
}
export interface GroupOwnerID {
memberUin: string;
memberUid: string;
memberQid: string;
}
export interface KickMemberInfo { export interface KickMemberInfo {
optFlag: number; optFlag: number;
@@ -100,185 +7,6 @@ export interface KickMemberInfo {
optBytesMsg: string; optBytesMsg: string;
} }
export interface GroupDetailInfoV2Param {
groupCode: string;
filter: Filter;
modifyInfo: ModifyInfo;
}
export interface Filter {
noCodeFingerOpenFlag: number;
noFingerOpenFlag: number;
groupName: number;
classExt: number;
classText: number;
fingerMemo: number;
richFingerMemo: number;
tagRecord: number;
groupGeoInfo: FilterGroupGeoInfo;
groupExtAdminNum: number;
flag: number;
groupMemo: number;
groupAioSkinUrl: number;
groupBoardSkinUrl: number;
groupCoverSkinUrl: number;
groupGrade: number;
activeMemberNum: number;
certificationType: number;
certificationText: number;
groupNewGuideLines: FilterGroupNewGuideLines;
groupFace: number;
addOption: number;
shutUpTime: number;
groupTypeFlag: number;
appPrivilegeFlag: number;
appPrivilegeMask: number;
groupExtOnly: GroupEXTOnly;
groupSecLevel: number;
groupSecLevelInfo: number;
subscriptionUin: number;
subscriptionUid: string;
allowMemberInvite: number;
groupQuestion: number;
groupAnswer: number;
groupFlagExt3: number;
groupFlagExt3Mask: number;
groupOpenAppid: number;
rootId: number;
msgLimitFrequency: number;
hlGuildAppid: number;
hlGuildSubType: number;
hlGuildOrgId: number;
groupFlagExt4: number;
groupFlagExt4Mask: number;
groupSchoolInfo: FilterGroupSchoolInfo;
groupCardPrefix: FilterGroupCardPrefix;
allianceId: number;
groupFlagPro1: number;
groupFlagPro1Mask: number;
}
export interface FilterGroupCardPrefix {
introduction: number;
rptPrefix: number;
}
export interface GroupEXTOnly {
tribeId: number;
moneyForAddGroup: number;
}
export interface FilterGroupGeoInfo {
ownerUid: number;
setTime: number;
cityId: number;
longitude: number;
latitude: number;
geoContent: number;
poiId: number;
}
export interface FilterGroupNewGuideLines {
enabled: number;
content: number;
}
export interface FilterGroupSchoolInfo {
location: number;
grade: number;
school: number;
}
export interface ModifyInfo {
noCodeFingerOpenFlag: number;
noFingerOpenFlag: number;
groupName: string;
classExt: number;
classText: string;
fingerMemo: string;
richFingerMemo: string;
tagRecord: any[];
groupGeoInfo: ModifyInfoGroupGeoInfo;
groupExtAdminNum: number;
flag: number;
groupMemo: string;
groupAioSkinUrl: string;
groupBoardSkinUrl: string;
groupCoverSkinUrl: string;
groupGrade: number;
activeMemberNum: number;
certificationType: number;
certificationText: string;
groupNewGuideLines: ModifyInfoGroupNewGuideLines;
groupFace: number;
addOption: number;// 0 空设置 1 任何人都可以进入 2 需要管理员批准 3 不允许任何人入群 4 问题进入答案 5 问题管理员批准
shutUpTime: number;
groupTypeFlag: number;
appPrivilegeFlag: number;
// 需要管理员审核
// 0000 0000 0000 0000 0000 0000 0000
// 无需审核入群
// 0000 0001 0000 0000 0000 0000 0000
// 成员数100内无审核
// 0100 0000 0000 0000 0000 0000 0000
// 禁用 群成员邀请好友
// 0100 0000 0000 0000 0000 0000 0000
appPrivilegeMask: number;
// 0110 0001 0000 0000 0000 0000 0000
// 101711872
groupExtOnly: GroupEXTOnly;
groupSecLevel: number;
groupSecLevelInfo: number;
subscriptionUin: string;
subscriptionUid: string;
allowMemberInvite: number;
groupQuestion: string;
groupAnswer: string;
groupFlagExt3: number;
groupFlagExt3Mask: number;
groupOpenAppid: number;
rootId: string;
msgLimitFrequency: number;
hlGuildAppid: number;
hlGuildSubType: number;
hlGuildOrgId: number;
groupFlagExt4: number;
groupFlagExt4Mask: number;
groupSchoolInfo: ModifyInfoGroupSchoolInfo;
groupCardPrefix: ModifyInfoGroupCardPrefix;
allianceId: string;
groupFlagPro1: number;
groupFlagPro1Mask: number;
}
export interface ModifyInfoGroupCardPrefix {
introduction: string;
rptPrefix: any[];
}
export interface ModifyInfoGroupGeoInfo {
ownerUid: string;
SetTime: number;
CityId: number;
Longitude: string;
Latitude: string;
GeoContent: string;
poiId: string;
}
export interface ModifyInfoGroupNewGuideLines {
enabled: boolean;
content: string;
}
export interface ModifyInfoGroupSchoolInfo {
location: string;
grade: number;
school: string;
}
// 获取群详细信息的来源类型 // 获取群详细信息的来源类型
export enum GroupInfoSource { export enum GroupInfoSource {
KUNSPECIFIED, KUNSPECIFIED,

View File

@@ -477,7 +477,7 @@ export enum SendStatusType {
export interface RawMessage { export interface RawMessage {
parentMsgPeer: Peer; // 父消息的Peer parentMsgPeer: Peer; // 父消息的Peer
parentMsgIdList: string[];// 父消息 ID 列表 parentMsgIdList: string[];// 父消息 ID 列表
id?: number;// 扩展字段,与 Ob11 msg ID 有关 id?: string;// 扩展字段,与 Ob11 msg ID 有关
guildId: string;// 频道ID guildId: string;// 频道ID
msgRandom: string;// 消息ID相关 msgRandom: string;// 消息ID相关
msgId: string;// 雪花ID msgId: string;// 雪花ID

View File

@@ -48,12 +48,6 @@ export async function NCoreInitFramework(
}); });
} }
//直到登录成功后,执行下一步 //直到登录成功后,执行下一步
// const selfInfo = {
// uid: 'u_FUSS0_x06S_9Tf4na_WpUg',
// uin: '3684714082',
// nick: '',
// online: true
// }
const selfInfo = await new Promise<SelfInfo>((resolveSelfInfo) => { const selfInfo = await new Promise<SelfInfo>((resolveSelfInfo) => {
const loginListener = new NodeIKernelLoginListener(); const loginListener = new NodeIKernelLoginListener();
loginListener.onQRCodeLoginSucceed = async (loginResult) => { loginListener.onQRCodeLoginSucceed = async (loginResult) => {

View File

@@ -1,26 +0,0 @@
const fs = require('fs');
const path = require('path');
async function initializeNapCat(session, loginService, registerCallback) {
//const logFile = path.join(currentPath, 'napcat.log');
console.log('[NapCat] [Info] 开始初始化NapCat');
//fs.writeFileSync(logFile, '', { flag: 'w' });
//fs.writeFileSync(logFile, '[NapCat] [Info] NapCat 初始化成功\n', { flag: 'a' });
try {
const currentPath = path.dirname(__filename);
const { NCoreInitFramework } = await import('file://' + path.join(currentPath, './napcat.mjs'));
await NCoreInitFramework(session, loginService, (callback) => { registerCallback(callback) });
} catch (error) {
console.log('[NapCat] [Error] 初始化NapCat', error);
//fs.writeFileSync(logFile, `[NapCat] [Error] 初始化NapCat失败: ${error.message}\n`, { flag: 'a' });
}
}
module.exports = {
initializeNapCat: initializeNapCat
};

View File

@@ -3,7 +3,7 @@ import { OneBotAction } from '../OneBotAction';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
bot_appid: Type.String(), bot_appid: Type.String(),
button_id: Type.String({ default: '' }), button_id: Type.String({ default: '' }),
callback_data: Type.String({ default: '' }), callback_data: Type.String({ default: '' }),
@@ -25,6 +25,6 @@ export class ClickInlineKeyboardButton extends OneBotAction<Payload, unknown> {
callback_data: payload.callback_data, callback_data: payload.callback_data,
dmFlag: 0, dmFlag: 0,
chatType: 2 chatType: 2
}) });
} }
} }

View File

@@ -3,7 +3,7 @@ import { OneBotAction } from '@/onebot/action/OneBotAction';
import { ActionName } from '@/onebot/action/router'; import { ActionName } from '@/onebot/action/router';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
count: Type.Union([Type.Number(), Type.String()], { default: 48 }), count: Type.Number({ default: 48 }),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;

View File

@@ -5,7 +5,7 @@ import { MessageUnique } from '@/common/message-unique';
import { type NTQQMsgApi } from '@/core/apis'; import { type NTQQMsgApi } from '@/core/apis';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
message_id: Type.Union([Type.Number(), Type.String()]), message_id: Type.String(),
emojiId: Type.Union([Type.Number(), Type.String()]), emojiId: Type.Union([Type.Number(), Type.String()]),
emojiType: Type.Union([Type.Number(), Type.String()]), emojiType: Type.Union([Type.Number(), Type.String()]),
count: Type.Union([Type.Number(), Type.String()], { default: 20 }), count: Type.Union([Type.Number(), Type.String()], { default: 20 }),
@@ -18,7 +18,7 @@ export class FetchEmojiLike extends OneBotAction<Payload, Awaited<ReturnType<NTQ
override payloadSchema = SchemaData; override payloadSchema = SchemaData;
async _handle(payload: Payload) { async _handle(payload: Payload) {
const msgIdPeer = MessageUnique.getMsgIdAndPeerByShortId(+payload.message_id); const msgIdPeer = MessageUnique.getInnerData(payload.message_id);
if (!msgIdPeer) throw new Error('消息不存在'); if (!msgIdPeer) throw new Error('消息不存在');
const msg = (await this.core.apis.MsgApi.getMsgsByMsgId(msgIdPeer.Peer, [msgIdPeer.MsgId])).msgList[0]; const msg = (await this.core.apis.MsgApi.getMsgsByMsgId(msgIdPeer.Peer, [msgIdPeer.MsgId])).msgList[0];
if (!msg) throw new Error('消息不存在'); if (!msg) throw new Error('消息不存在');

View File

@@ -4,7 +4,7 @@ import { AIVoiceChatType } from '@/core/packet/entities/aiChat';
import { Type, Static } from '@sinclair/typebox'; import { Type, Static } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
chat_type: Type.Union([Type.Union([Type.Number(), Type.String()])], { default: 1 }), chat_type: Type.Union([Type.Union([Type.Number(), Type.String()])], { default: 1 }),
}); });

View File

@@ -4,8 +4,8 @@ import { ActionName } from '@/onebot/action/router';
import { Type, Static } from '@sinclair/typebox'; import { Type, Static } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
category: Type.Union([Type.Number(), Type.String()]), category: Type.Number({ default: 0 }),
count: Type.Union([Type.Union([Type.Number(), Type.String()])], { default: 1 }), count: Type.Number({ default: 1 }),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;

View File

@@ -2,7 +2,7 @@ import { OneBotAction } from '@/onebot/action/OneBotAction';
import { ActionName } from '@/onebot/action/router'; import { ActionName } from '@/onebot/action/router';
import { Type, Static } from '@sinclair/typebox'; import { Type, Static } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;

View File

@@ -4,9 +4,9 @@ import { ActionName } from '@/onebot/action/router';
import { Type, Static } from '@sinclair/typebox'; import { Type, Static } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
user_id: Type.Optional(Type.Union([Type.Number(), Type.String()])), user_id: Type.Optional(Type.String()),
start: Type.Union([Type.Number(), Type.String()], { default: 0 }), start: Type.String({ default: '0' }),
count: Type.Union([Type.Number(), Type.String()], { default: 10 }) count: Type.String({ default: '10' })
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;

View File

@@ -36,7 +36,7 @@ export class GetUnidirectionalFriendList extends OneBotAction<void, Friend[]> {
uint64_uin: self_id, uint64_uin: self_id,
uint64_top: 0, uint64_top: 0,
uint32_req_num: 99, uint32_req_num: 99,
bytes_cookies: "" bytes_cookies: ''
}; };
const packed_data = await this.pack_data(JSON.stringify(req_json)); const packed_data = await this.pack_data(JSON.stringify(req_json));
const data = Buffer.from(packed_data).toString('hex'); const data = Buffer.from(packed_data).toString('hex');

View File

@@ -3,7 +3,7 @@ import { GetPacketStatusDepends } from '@/onebot/action/packet/GetPacketStatus';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
user_id: Type.Union([Type.Number(), Type.String()]), user_id: Type.String(),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;

View File

@@ -4,7 +4,7 @@ import { GetPacketStatusDepends } from '@/onebot/action/packet/GetPacketStatus';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
file_id: Type.String(), file_id: Type.String(),
current_parent_directory: Type.String(), current_parent_directory: Type.String(),
target_parent_directory: Type.String(), target_parent_directory: Type.String(),

View File

@@ -4,7 +4,7 @@ import { GetPacketStatusDepends } from '@/onebot/action/packet/GetPacketStatus';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
file_id: Type.String(), file_id: Type.String(),
current_parent_directory: Type.String(), current_parent_directory: Type.String(),
new_name: Type.String(), new_name: Type.String(),

View File

@@ -3,8 +3,8 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
face_id: Type.Union([Type.Number(), Type.String()]),// 参考 face_config.json 的 QSid face_id: Type.String(),// 参考 face_config.json 的 QSid
face_type: Type.Union([Type.Number(), Type.String()], { default: '1' }), face_type: Type.String({ default: '1' }),
wording: Type.String({ default: ' ' }), wording: Type.String({ default: ' ' }),
}); });
@@ -16,9 +16,9 @@ export class SetDiyOnlineStatus extends OneBotAction<Payload, string> {
async _handle(payload: Payload) { async _handle(payload: Payload) {
const ret = await this.core.apis.UserApi.setDiySelfOnlineStatus( const ret = await this.core.apis.UserApi.setDiySelfOnlineStatus(
payload.face_id.toString(), payload.face_id,
payload.wording, payload.wording,
payload.face_type.toString(), payload.face_type,
); );
if (ret.result !== 0) { if (ret.result !== 0) {
throw new Error('设置在线状态失败'); throw new Error('设置在线状态失败');

View File

@@ -1,28 +0,0 @@
import { OneBotAction } from '@/onebot/action/OneBotAction';
import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({
group_id: Type.String(),
add_type: Type.Number(),
group_question: Type.Optional(Type.String()),
group_answer: Type.Optional(Type.String()),
});
type Payload = Static<typeof SchemaData>;
export default class SetGroupAddOption extends OneBotAction<Payload, null> {
override actionName = ActionName.SetGroupAddOption;
override payloadSchema = SchemaData;
async _handle(payload: Payload): Promise<null> {
let ret = await this.core.apis.GroupApi.setGroupAddOption(payload.group_id, {
addOption: payload.add_type,
groupQuestion: payload.group_question,
groupAnswer: payload.group_answer,
});
if (ret.result != 0) {
throw new Error(`设置群添加选项失败, ${ret.result}:${ret.errMsg}`);
}
return null;
}
}

View File

@@ -1,23 +0,0 @@
import { OneBotAction } from '@/onebot/action/OneBotAction';
import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({
group_id: Type.String(),
user_id: Type.Array(Type.String()),
reject_add_request: Type.Optional(Type.Union([Type.Boolean(), Type.String()])),
});
type Payload = Static<typeof SchemaData>;
export default class SetGroupKickMembers extends OneBotAction<Payload, null> {
override actionName = ActionName.SetGroupKickMembers;
override payloadSchema = SchemaData;
async _handle(payload: Payload): Promise<null> {
const rejectReq = payload.reject_add_request?.toString() == 'true';
const uids: string[] = await Promise.all(payload.user_id.map(async uin => await this.core.apis.UserApi.getUidByUinV2(uin)));
await this.core.apis.GroupApi.kickMember(payload.group_id.toString(), uids.filter(uid => !!uid), rejectReq);
return null;
}
}

View File

@@ -1,27 +0,0 @@
import { OneBotAction } from '@/onebot/action/OneBotAction';
import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({
group_id: Type.String(),
robot_member_switch: Type.Optional(Type.Number()),
robot_member_examine: Type.Optional(Type.Number()),
});
type Payload = Static<typeof SchemaData>;
export default class SetGroupRobotAddOption extends OneBotAction<Payload, null> {
override actionName = ActionName.SetGroupRobotAddOption;
override payloadSchema = SchemaData;
async _handle(payload: Payload): Promise<null> {
let ret = await this.core.apis.GroupApi.setGroupRobotAddOption(
payload.group_id,
payload.robot_member_switch,
payload.robot_member_examine,
);
if (ret.result != 0) {
throw new Error(`设置群机器人添加选项失败, ${ret.result}:${ret.errMsg}`);
}
return null;
}
}

View File

@@ -1,26 +0,0 @@
import { OneBotAction } from '@/onebot/action/OneBotAction';
import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({
group_id: Type.String(),
no_code_finger_open: Type.Optional(Type.Number()),
no_finger_open: Type.Optional(Type.Number()),
});
type Payload = Static<typeof SchemaData>;
export default class SetGroupSearch extends OneBotAction<Payload, null> {
override actionName = ActionName.SetGroupSearch;
override payloadSchema = SchemaData;
async _handle(payload: Payload): Promise<null> {
let ret = await this.core.apis.GroupApi.setGroupSearch(payload.group_id, {
noCodeFingerOpenFlag: payload.no_code_finger_open,
noFingerOpenFlag: payload.no_finger_open,
});
if (ret.result != 0) {
throw new Error(`设置群搜索失败, ${ret.result}:${ret.errMsg}`);
}
return null;
}
}

View File

@@ -3,7 +3,7 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;

View File

@@ -4,7 +4,7 @@ import { ChatType } from '@/core';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
user_id: Type.Union([Type.Number(), Type.String()]), user_id: Type.String(),
event_type: Type.Number(), event_type: Type.Number(),
}); });

View File

@@ -3,9 +3,9 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
status: Type.Union([Type.Number(), Type.String()]), status: Type.Number(),
ext_status: Type.Union([Type.Number(), Type.String()]), ext_status: Type.Number(),
battery_status: Type.Union([Type.Number(), Type.String()]), battery_status: Type.Number(),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;
@@ -16,9 +16,9 @@ export class SetOnlineStatus extends OneBotAction<Payload, null> {
async _handle(payload: Payload) { async _handle(payload: Payload) {
const ret = await this.core.apis.UserApi.setSelfOnlineStatus( const ret = await this.core.apis.UserApi.setSelfOnlineStatus(
+payload.status, payload.status,
+payload.ext_status, payload.ext_status,
+payload.battery_status, payload.battery_status,
); );
if (ret.result !== 0) { if (ret.result !== 0) {
throw new Error('设置在线状态失败'); throw new Error('设置在线状态失败');

View File

@@ -3,8 +3,8 @@ import { GetPacketStatusDepends } from '@/onebot/action/packet/GetPacketStatus';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
user_id: Type.Union([Type.Number(), Type.String()]), user_id: Type.String(),
special_title: Type.String({ default: '' }), special_title: Type.String({ default: '' }),
}); });

View File

@@ -4,8 +4,8 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
user_id: Type.Optional(Type.Union([Type.Number(), Type.String()])), user_id: Type.Optional(Type.String()),
group_id: Type.Optional(Type.Union([Type.Number(), Type.String()])), group_id: Type.Optional(Type.String()),
phoneNumber: Type.String({ default: '' }), phoneNumber: Type.String({ default: '' }),
}); });
@@ -29,7 +29,7 @@ export class SharePeer extends OneBotAction<Payload, GeneralCallResult & {
} }
const SchemaDataGroupEx = Type.Object({ const SchemaDataGroupEx = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
}); });
type PayloadGroupEx = Static<typeof SchemaDataGroupEx>; type PayloadGroupEx = Static<typeof SchemaDataGroupEx>;

View File

@@ -4,7 +4,7 @@ import { GetPacketStatusDepends } from '@/onebot/action/packet/GetPacketStatus';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
file_id: Type.String(), file_id: Type.String(),
}); });

View File

@@ -4,7 +4,7 @@ import { GetPacketStatusDepends } from '@/onebot/action/packet/GetPacketStatus';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
file_id: Type.String(), file_id: Type.String(),
}); });

View File

@@ -3,11 +3,8 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
// 兼容gocq 与name二选一 folder_name: Type.String(),
folder_name: Type.Optional(Type.String()),
// 兼容gocq 与folder_name二选一
name: Type.Optional(Type.String()),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;
@@ -19,7 +16,6 @@ export class CreateGroupFileFolder extends OneBotAction<Payload, ResponseType>
override actionName = ActionName.GoCQHTTP_CreateGroupFileFolder; override actionName = ActionName.GoCQHTTP_CreateGroupFileFolder;
override payloadSchema = SchemaData; override payloadSchema = SchemaData;
async _handle(payload: Payload) { async _handle(payload: Payload) {
const folderName = payload.folder_name || payload.name; return (await this.core.apis.GroupApi.creatGroupFileFolder(payload.group_id.toString(), payload.folder_name)).resultWithGroupItem;
return (await this.core.apis.GroupApi.creatGroupFileFolder(payload.group_id.toString(), folderName!)).resultWithGroupItem;
} }
} }

View File

@@ -6,7 +6,7 @@ import { Static, Type } from '@sinclair/typebox';
import { NTQQGroupApi } from '@/core/apis'; import { NTQQGroupApi } from '@/core/apis';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
file_id: Type.String(), file_id: Type.String(),
}); });

View File

@@ -4,7 +4,7 @@ import { Static, Type } from '@sinclair/typebox';
import { NTQQGroupApi } from '@/core/apis'; import { NTQQGroupApi } from '@/core/apis';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
folder_id: Type.Optional(Type.String()), folder_id: Type.Optional(Type.String()),
folder: Type.Optional(Type.String()), folder: Type.Optional(Type.String()),
}); });

View File

@@ -117,8 +117,7 @@ export class GoCQHTTPGetForwardMsgAction extends OneBotAction<Payload, {
} }
throw new Error('ResId无效: 找不到相关的聊天记录'); throw new Error('ResId无效: 找不到相关的聊天记录');
} }
const rootMsgId = MessageUnique.getShortIdByMsgId(msgId.toString()); const rootMsg = MessageUnique.getInnerData(msgId);
const rootMsg = MessageUnique.getMsgIdAndPeerByShortId(rootMsgId ?? +msgId);
if (rootMsg) { if (rootMsg) {
// 5. 获取消息内容 // 5. 获取消息内容

View File

@@ -12,7 +12,7 @@ interface Response {
} }
const SchemaData = Type.Object({ const SchemaData = Type.Object({
user_id: Type.String(), user_id: Type.String(),
message_seq: Type.Optional(Type.String()), message_id: Type.Optional(Type.String()),
count: Type.Number({ default: 20 }), count: Type.Number({ default: 20 }),
reverseOrder: Type.Boolean({ default: false }) reverseOrder: Type.Boolean({ default: false })
}); });
@@ -24,24 +24,24 @@ export default class GetFriendMsgHistory extends OneBotAction<Payload, Response>
override actionName = ActionName.GetFriendMsgHistory; override actionName = ActionName.GetFriendMsgHistory;
override payloadSchema = SchemaData; override payloadSchema = SchemaData;
async _handle(payload: Payload, _adapter: string, config: NetworkAdapterConfig): Promise<Response> { async _handle(payload: Payload, _adapter: string, _config: NetworkAdapterConfig): Promise<Response> {
//处理参数 //处理参数
const uid = await this.core.apis.UserApi.getUidByUinV2(payload.user_id.toString()); const uid = await this.core.apis.UserApi.getUidByUinV2(payload.user_id.toString());
if (!uid) throw new Error(`记录${payload.user_id}不存在`); if (!uid) throw new Error(`记录${payload.user_id}不存在`);
const friend = await this.core.apis.FriendApi.isBuddy(uid); const friend = await this.core.apis.FriendApi.isBuddy(uid);
const peer = { chatType: friend ? ChatType.KCHATTYPEC2C : ChatType.KCHATTYPETEMPC2CFROMGROUP, peerUid: uid }; const peer = { chatType: friend ? ChatType.KCHATTYPEC2C : ChatType.KCHATTYPETEMPC2CFROMGROUP, peerUid: uid };
const hasMessageSeq = !payload.message_seq ? !!payload.message_seq : !(payload.message_seq?.toString() === '' || payload.message_seq?.toString() === '0'); const hasMessageId = !payload.message_id ? !!payload.message_id : !(payload.message_id?.toString() === '' || payload.message_id?.toString() === '0');
const startMsgId = hasMessageSeq ? (MessageUnique.getMsgIdAndPeerByShortId(+payload.message_seq!)?.MsgId ?? payload.message_seq!.toString()) : '0'; const startMsgId = hasMessageId ? (MessageUnique.getInnerData(payload.message_id!)?.MsgId ?? payload.message_id!.toString()) : '0';
const msgList = hasMessageSeq ? const msgList = hasMessageId ?
(await this.core.apis.MsgApi.getMsgHistory(peer, startMsgId, +payload.count, payload.reverseOrder)).msgList : (await this.core.apis.MsgApi.getAioFirstViewLatestMsgs(peer, +payload.count)).msgList; (await this.core.apis.MsgApi.getMsgHistory(peer, startMsgId, +payload.count, payload.reverseOrder)).msgList : (await this.core.apis.MsgApi.getAioFirstViewLatestMsgs(peer, +payload.count)).msgList;
if (msgList.length === 0) throw new Error(`消息${payload.message_seq}不存在`); if (msgList.length === 0) throw new Error(`消息${payload.message_id}不存在`);
//转换序号 //转换序号
await Promise.all(msgList.map(async msg => { await Promise.all(msgList.map(async msg => {
msg.id = MessageUnique.createUniqueMsgId({ guildId: '', chatType: msg.chatType, peerUid: msg.peerUid }, msg.msgId); msg.id = MessageUnique.getOutputData({ guildId: '', chatType: msg.chatType, peerUid: msg.peerUid }, msg.msgId, msg.msgSeq);
})); }));
//烘焙消息 //烘焙消息
const ob11MsgList = (await Promise.all( const ob11MsgList = (await Promise.all(
msgList.map(msg => this.obContext.apis.MsgApi.parseMessage(msg, config.messagePostFormat))) msgList.map(msg => this.obContext.apis.MsgApi.parseMessage(msg)))
).filter(msg => msg !== undefined); ).filter(msg => msg !== undefined);
return { 'messages': ob11MsgList }; return { 'messages': ob11MsgList };
} }

View File

@@ -3,7 +3,7 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]) group_id: Type.String()
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;

View File

@@ -3,7 +3,7 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]) group_id: Type.String()
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;

View File

@@ -5,7 +5,7 @@ import { OB11Construct } from '@/onebot/helper/data';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
folder_id: Type.Optional(Type.String()), folder_id: Type.Optional(Type.String()),
folder: Type.Optional(Type.String()), folder: Type.Optional(Type.String()),
file_count: Type.Union([Type.Number(), Type.String()], { default: 50 }), file_count: Type.Union([Type.Number(), Type.String()], { default: 50 }),

View File

@@ -4,7 +4,7 @@ import { WebHonorType } from '@/core/types';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
type: Type.Optional(Type.Enum(WebHonorType)) type: Type.Optional(Type.Enum(WebHonorType))
}); });

View File

@@ -4,15 +4,13 @@ import { ActionName } from '@/onebot/action/router';
import { ChatType, Peer } from '@/core/types'; import { ChatType, Peer } from '@/core/types';
import { MessageUnique } from '@/common/message-unique'; import { MessageUnique } from '@/common/message-unique';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
import { NetworkAdapterConfig } from '@/onebot/config/config';
interface Response { interface Response {
messages: OB11Message[]; messages: OB11Message[];
} }
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.String(), group_id: Type.String(),
message_seq: Type.Optional(Type.String()), message_id: Type.Optional(Type.String()),
count: Type.Number({ default: 20 }), count: Type.Number({ default: 20 }),
reverseOrder: Type.Boolean({ default: false }) reverseOrder: Type.Boolean({ default: false })
}); });
@@ -25,21 +23,21 @@ export default class GoCQHTTPGetGroupMsgHistory extends OneBotAction<Payload, Re
override actionName = ActionName.GoCQHTTP_GetGroupMsgHistory; override actionName = ActionName.GoCQHTTP_GetGroupMsgHistory;
override payloadSchema = SchemaData; override payloadSchema = SchemaData;
async _handle(payload: Payload, _adapter: string, config: NetworkAdapterConfig): Promise<Response> { async _handle(payload: Payload, _adapter: string): Promise<Response> {
const peer: Peer = { chatType: ChatType.KCHATTYPEGROUP, peerUid: payload.group_id.toString() }; const peer: Peer = { chatType: ChatType.KCHATTYPEGROUP, peerUid: payload.group_id.toString() };
const hasMessageSeq = !payload.message_seq ? !!payload.message_seq : !(payload.message_seq?.toString() === '' || payload.message_seq?.toString() === '0'); const hasMessageSeq = !payload.message_id ? !!payload.message_id : !(payload.message_id?.toString() === '' || payload.message_id?.toString() === '0');
//拉取消息 //拉取消息
const startMsgId = hasMessageSeq ? (MessageUnique.getMsgIdAndPeerByShortId(+payload.message_seq!)?.MsgId ?? payload.message_seq!.toString()) : '0'; const startMsgId = hasMessageSeq ? (MessageUnique.getInnerData(payload.message_id!)?.MsgId ?? payload.message_id!.toString()) : '0';
const msgList = hasMessageSeq ? const msgList = hasMessageSeq ?
(await this.core.apis.MsgApi.getMsgHistory(peer, startMsgId, +payload.count, payload.reverseOrder)).msgList : (await this.core.apis.MsgApi.getAioFirstViewLatestMsgs(peer, +payload.count)).msgList; (await this.core.apis.MsgApi.getMsgHistory(peer, startMsgId, +payload.count, payload.reverseOrder)).msgList : (await this.core.apis.MsgApi.getAioFirstViewLatestMsgs(peer, +payload.count)).msgList;
if (msgList.length === 0) throw new Error(`消息${payload.message_seq}不存在`); if (msgList.length === 0) throw new Error(`消息${payload.message_id}不存在`);
//转换序号 //转换序号
await Promise.all(msgList.map(async msg => { await Promise.all(msgList.map(async msg => {
msg.id = MessageUnique.createUniqueMsgId({ guildId: '', chatType: msg.chatType, peerUid: msg.peerUid }, msg.msgId); msg.id = MessageUnique.getOutputData({ guildId: '', chatType: msg.chatType, peerUid: msg.peerUid }, msg.msgId, msg.msgSeq);
})); }));
//烘焙消息 //烘焙消息
const ob11MsgList = (await Promise.all( const ob11MsgList = (await Promise.all(
msgList.map(msg => this.obContext.apis.MsgApi.parseMessage(msg, config.messagePostFormat))) msgList.map(msg => this.obContext.apis.MsgApi.parseMessage(msg)))
).filter(msg => msg !== undefined); ).filter(msg => msg !== undefined);
return { 'messages': ob11MsgList }; return { 'messages': ob11MsgList };
} }

View File

@@ -6,7 +6,7 @@ import { OB11Construct } from '@/onebot/helper/data';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
file_count: Type.Union([Type.Number(), Type.String()], { default: 50 }), file_count: Type.Union([Type.Number(), Type.String()], { default: 50 }),
}); });

View File

@@ -6,7 +6,7 @@ import { calcQQLevel } from '@/common/helper';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
user_id: Type.Union([Type.Number(), Type.String()]), user_id: Type.String(),
no_cache: Type.Union([Type.Boolean(), Type.String()], { default: false }), no_cache: Type.Union([Type.Boolean(), Type.String()], { default: false }),
}); });
@@ -28,7 +28,7 @@ export default class GoCQHTTPGetStrangerInfo extends OneBotAction<Payload, OB11U
...extendData.detail.simpleInfo.baseInfo, ...extendData.detail.simpleInfo.baseInfo,
...extendData.detail.simpleInfo.relationFlags ?? {}, ...extendData.detail.simpleInfo.relationFlags ?? {},
...extendData.detail.simpleInfo.status ?? {}, ...extendData.detail.simpleInfo.status ?? {},
user_id: parseInt(extendData.detail.uin) ?? 0, user_id: extendData.detail.uin ?? 0,
uid: info.uid ?? uid, uid: info.uid ?? uid,
nickname: extendData.detail.simpleInfo.coreInfo.nick ?? '', nickname: extendData.detail.simpleInfo.coreInfo.nick ?? '',
age: extendData.detail.simpleInfo.baseInfo.age ?? info.age, age: extendData.detail.simpleInfo.baseInfo.age ?? info.age,

View File

@@ -3,8 +3,8 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
friend_id: Type.Optional(Type.Union([Type.String(), Type.Number()])), friend_id: Type.Optional(Type.String()),
user_id: Type.Optional(Type.Union([Type.String(), Type.Number()])), user_id: Type.Optional(Type.String()),
temp_block: Type.Optional(Type.Boolean()), temp_block: Type.Optional(Type.Boolean()),
temp_both_del: Type.Optional(Type.Boolean()), temp_both_del: Type.Optional(Type.Boolean()),
}); });

View File

@@ -1,19 +0,0 @@
import { OneBotAction } from '@/onebot/action/OneBotAction';
import { ActionName } from '@/onebot/action/router';
import { QuickAction, QuickActionEvent } from '@/onebot/types';
interface Payload {
context: QuickActionEvent,
operation: QuickAction
}
export class GoCQHTTPHandleQuickAction extends OneBotAction<Payload, null> {
override actionName = ActionName.GoCQHTTP_HandleQuickAction;
async _handle(payload: Payload): Promise<null> {
this.obContext.apis.QuickActionApi
.handleQuickOperation(payload.context, payload.operation)
.catch(e => this.core.context.logger.logError(e));
return null;
}
}

View File

@@ -1,4 +1,4 @@
import { ContextMode, normalize, ReturnDataType, SendMsgBase } from '@/onebot/action/msg/SendMsg'; import { normalize, SendMsgBase } from '@/onebot/action/msg/SendMsg';
import { OB11PostSendMsg } from '@/onebot/types'; import { OB11PostSendMsg } from '@/onebot/types';
import { ActionName } from '@/onebot/action/router'; import { ActionName } from '@/onebot/action/router';
@@ -19,14 +19,8 @@ export class GoCQHTTPSendForwardMsg extends GoCQHTTPSendForwardMsgBase {
} }
export class GoCQHTTPSendPrivateForwardMsg extends GoCQHTTPSendForwardMsgBase { export class GoCQHTTPSendPrivateForwardMsg extends GoCQHTTPSendForwardMsgBase {
override actionName = ActionName.GoCQHTTP_SendPrivateForwardMsg; override actionName = ActionName.GoCQHTTP_SendPrivateForwardMsg;
override async _handle(payload: OB11PostSendMsg): Promise<ReturnDataType> {
return this.base_handle(payload, ContextMode.Private);
}
} }
export class GoCQHTTPSendGroupForwardMsg extends GoCQHTTPSendForwardMsgBase { export class GoCQHTTPSendGroupForwardMsg extends GoCQHTTPSendForwardMsgBase {
override actionName = ActionName.GoCQHTTP_SendGroupForwardMsg; override actionName = ActionName.GoCQHTTP_SendGroupForwardMsg;
override async _handle(payload: OB11PostSendMsg): Promise<ReturnDataType> {
return this.base_handle(payload, ContextMode.Group);
}
} }

View File

@@ -5,7 +5,7 @@ import { unlink } from 'node:fs/promises';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
content: Type.String(), content: Type.String(),
image: Type.Optional(Type.String()), image: Type.Optional(Type.String()),
pinned: Type.Union([Type.Number(), Type.String()], { default: 0 }), pinned: Type.Union([Type.Number(), Type.String()], { default: 0 }),

View File

@@ -6,7 +6,7 @@ import fs from 'node:fs/promises';
import { GeneralCallResult } from '@/core'; import { GeneralCallResult } from '@/core';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
file: Type.String(), file: Type.String(),
group_id: Type.Union([Type.Number(), Type.String()]) group_id: Type.String()
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;

View File

@@ -7,7 +7,7 @@ import { SendMessageContext } from '@/onebot/api';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
file: Type.String(), file: Type.String(),
name: Type.String(), name: Type.String(),
folder: Type.Optional(Type.String()), folder: Type.Optional(Type.String()),

View File

@@ -8,7 +8,7 @@ import { ContextMode, createContext } from '@/onebot/action/msg/SendMsg';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
user_id: Type.Union([Type.Number(), Type.String()]), user_id: Type.String(),
file: Type.String(), file: Type.String(),
name: Type.String(), name: Type.String(),
}); });

View File

@@ -4,7 +4,7 @@ import { MessageUnique } from '@/common/message-unique';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
message_id: Type.Union([Type.Number(), Type.String()]), message_id: Type.String(),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;
@@ -13,7 +13,7 @@ export default class DelEssenceMsg extends OneBotAction<Payload, unknown> {
override payloadSchema = SchemaData; override payloadSchema = SchemaData;
async _handle(payload: Payload): Promise<unknown> { async _handle(payload: Payload): Promise<unknown> {
const msg = MessageUnique.getMsgIdAndPeerByShortId(+payload.message_id); const msg = MessageUnique.getInnerData(payload.message_id);
if (!msg) { if (!msg) {
const data = this.core.apis.GroupApi.essenceLRU.getValue(+payload.message_id); const data = this.core.apis.GroupApi.essenceLRU.getValue(+payload.message_id);
if(!data) throw new Error('消息不存在'); if(!data) throw new Error('消息不存在');

View File

@@ -3,7 +3,7 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
notice_id: Type.String() notice_id: Type.String()
}); });

View File

@@ -5,7 +5,7 @@ import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
character: Type.String(), character: Type.String(),
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
text: Type.String(), text: Type.String(),
}); });

View File

@@ -1,27 +0,0 @@
import { OneBotAction } from '@/onebot/action/OneBotAction';
import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]),
});
type Payload = Static<typeof SchemaData>;
export class GetGroupDetailInfo extends OneBotAction<Payload, unknown> {
override actionName = ActionName.GetGroupDetailInfo;
override payloadSchema = SchemaData;
async _handle(payload: Payload) {
const data = await this.core.apis.GroupApi.fetchGroupDetail(payload.group_id.toString());
return {
...data,
group_all_shut: data.shutUpAllTimestamp > 0 ? -1 : 0,
group_remark: '',
group_id: +payload.group_id,
group_name: data.groupName,
member_count: data.memberNum,
max_member_count: data.maxMemberNum,
};
}
}

View File

@@ -4,10 +4,8 @@ import { ActionName } from '@/onebot/action/router';
import { MessageUnique } from '@/common/message-unique'; import { MessageUnique } from '@/common/message-unique';
import crypto from 'crypto'; import crypto from 'crypto';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
import { NetworkAdapterConfig } from '@/onebot/config/config';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;
@@ -22,12 +20,12 @@ export class GetGroupEssence extends OneBotAction<Payload, unknown> {
return undefined; return undefined;
} }
return { return {
id: MessageUnique.createUniqueMsgId(peer, replyMsgList.msgId), id: MessageUnique.getOutputData(peer, replyMsgList.msgId, replyMsgList.msgSeq),
msg: replyMsgList msg: replyMsgList
}; };
} }
async _handle(payload: Payload, _adapter: string, config: NetworkAdapterConfig) { async _handle(payload: Payload, _adapter: string) {
const msglist = (await this.core.apis.WebApi.getGroupEssenceMsgAll(payload.group_id.toString())).flatMap((e) => e.data.msg_list); const msglist = (await this.core.apis.WebApi.getGroupEssenceMsgAll(payload.group_id.toString())).flatMap((e) => e.data.msg_list);
if (!msglist) { if (!msglist) {
throw new Error('获取失败'); throw new Error('获取失败');
@@ -48,7 +46,7 @@ export class GetGroupEssence extends OneBotAction<Payload, unknown> {
operator_nick: msg.add_digest_nick, operator_nick: msg.add_digest_nick,
message_id: message_id, message_id: message_id,
operator_time: msg.add_digest_time, operator_time: msg.add_digest_time,
content: (await this.obContext.apis.MsgApi.parseMessage(rawMessage, config.messagePostFormat))?.message content: (await this.obContext.apis.MsgApi.parseMessage(rawMessage))?.message
}; };
} }
const msgTempData = JSON.stringify({ const msgTempData = JSON.stringify({

View File

@@ -4,7 +4,6 @@ import { ActionName } from '@/onebot/action/router';
import { Notify } from '@/onebot/types'; import { Notify } from '@/onebot/types';
interface RetData { interface RetData {
invited_requests: Notify[];
InvitedRequest: Notify[]; InvitedRequest: Notify[];
join_requests: Notify[]; join_requests: Notify[];
} }
@@ -14,7 +13,7 @@ export class GetGroupIgnoredNotifies extends OneBotAction<void, RetData> {
async _handle(): Promise<RetData> { async _handle(): Promise<RetData> {
const SingleScreenNotifies = await this.core.apis.GroupApi.getSingleScreenNotifies(false, 50); const SingleScreenNotifies = await this.core.apis.GroupApi.getSingleScreenNotifies(false, 50);
const retData: RetData = { invited_requests: [], InvitedRequest: [], join_requests: [] }; const retData: RetData = { InvitedRequest: [], join_requests: [] };
const notifyPromises = SingleScreenNotifies.map(async (SSNotify) => { const notifyPromises = SingleScreenNotifies.map(async (SSNotify) => {
const invitorUin = SSNotify.user1?.uid ? +await this.core.apis.UserApi.getUinByUidV2(SSNotify.user1.uid) : 0; const invitorUin = SSNotify.user1?.uid ? +await this.core.apis.UserApi.getUinByUidV2(SSNotify.user1.uid) : 0;
@@ -39,7 +38,7 @@ export class GetGroupIgnoredNotifies extends OneBotAction<void, RetData> {
}); });
await Promise.all(notifyPromises); await Promise.all(notifyPromises);
retData.invited_requests = retData.InvitedRequest;
return retData; return retData;
} }
} }

View File

@@ -5,7 +5,7 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;

View File

@@ -5,8 +5,8 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
user_id: Type.Union([Type.Number(), Type.String()]), user_id: Type.String(),
no_cache: Type.Optional(Type.Union([Type.Boolean(), Type.String()])), no_cache: Type.Optional(Type.Union([Type.Boolean(), Type.String()])),
}); });

View File

@@ -6,7 +6,7 @@ import { Static, Type } from '@sinclair/typebox';
import { GroupMember } from '@/core'; import { GroupMember } from '@/core';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
no_cache: Type.Optional(Type.Union([Type.Boolean(), Type.String()])) no_cache: Type.Optional(Type.Union([Type.Boolean(), Type.String()]))
}); });

View File

@@ -8,22 +8,16 @@ interface GroupNotice {
notice_id: string; notice_id: string;
message: { message: {
text: string text: string
// 保持一段时间兼容性 防止以往版本出现问题 后续版本可考虑移除
image: Array<{ image: Array<{
height: string height: string
width: string width: string
id: string id: string
}>,
images: Array<{
height: string
width: string
id: string
}> }>
}; };
} }
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;
@@ -46,18 +40,15 @@ export class GetGroupNotice extends OneBotAction<Payload, GroupNotice[]> {
continue; continue;
} }
const retApiNotice: WebApiGroupNoticeFeed = ret.feeds[key]; const retApiNotice: WebApiGroupNoticeFeed = ret.feeds[key];
const image = retApiNotice.msg.pics?.map((pic) => {
return { id: pic.id, height: pic.h, width: pic.w };
}) || [];
const retNotice: GroupNotice = { const retNotice: GroupNotice = {
notice_id: retApiNotice.fid, notice_id: retApiNotice.fid,
sender_id: retApiNotice.u, sender_id: retApiNotice.u,
publish_time: retApiNotice.pubt, publish_time: retApiNotice.pubt,
message: { message: {
text: retApiNotice.msg.text, text: retApiNotice.msg.text,
image, image: retApiNotice.msg.pics?.map((pic) => {
images: image, return { id: pic.id, height: pic.h, width: pic.w };
}) || [],
}, },
}; };
retNotices.push(retNotice); retNotices.push(retNotice);

View File

@@ -4,7 +4,7 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;

View File

@@ -0,0 +1,19 @@
import { ActionName } from '@/onebot/action/router';
import { GetPacketStatusDepends } from '@/onebot/action/packet/GetPacketStatus';
import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({
group_id: Type.String(),
user_id: Type.String(),
});
type Payload = Static<typeof SchemaData>;
export class GroupPoke extends GetPacketStatusDepends<Payload, void> {
override actionName = ActionName.GroupPoke;
override payloadSchema = SchemaData;
async _handle(payload: Payload) {
await this.core.apis.PacketApi.pkt.operation.GroupPoke(+payload.group_id, +payload.user_id);
}
}

View File

@@ -5,7 +5,7 @@ import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
character: Type.String(), character: Type.String(),
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
text: Type.String(), text: Type.String(),
}); });

View File

@@ -1,19 +1,17 @@
import { ContextMode, ReturnDataType, SendMsgBase } from '@/onebot/action/msg/SendMsg'; import { ContextMode, SendMsgBase } from '@/onebot/action/msg/SendMsg';
import { ActionName, BaseCheckResult } from '@/onebot/action/router'; import { ActionName, BaseCheckResult } from '@/onebot/action/router';
import { OB11PostSendMsg } from '@/onebot/types'; import { OB11PostSendMsg } from '@/onebot/types';
// 未检测参数 // 未检测参数
class SendGroupMsg extends SendMsgBase { class SendGroupMsg extends SendMsgBase {
override actionName = ActionName.SendGroupMsg; override actionName = ActionName.SendGroupMsg;
override contextMode: ContextMode = ContextMode.Group;
protected override async check(payload: OB11PostSendMsg): Promise<BaseCheckResult> { protected override async check(payload: OB11PostSendMsg): Promise<BaseCheckResult> {
delete payload.user_id; delete payload.user_id;
payload.message_type = 'group'; payload.message_type = 'group';
return super.check(payload); return super.check(payload);
} }
override async _handle(payload: OB11PostSendMsg): Promise<ReturnDataType> {
return this.base_handle(payload, ContextMode.Group);
}
} }
export default SendGroupMsg; export default SendGroupMsg;

View File

@@ -4,7 +4,7 @@ import { MessageUnique } from '@/common/message-unique';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
message_id: Type.Union([Type.Number(), Type.String()]), message_id: Type.String(),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;
@@ -14,7 +14,7 @@ export default class SetEssenceMsg extends OneBotAction<Payload, unknown> {
override payloadSchema = SchemaData; override payloadSchema = SchemaData;
async _handle(payload: Payload) { async _handle(payload: Payload) {
const msg = MessageUnique.getMsgIdAndPeerByShortId(+payload.message_id); const msg = MessageUnique.getInnerData(payload.message_id);
if (!msg) { if (!msg) {
throw new Error('msg not found'); throw new Error('msg not found');
} }

View File

@@ -4,8 +4,8 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
user_id: Type.Union([Type.Number(), Type.String()]), user_id: Type.String(),
enable: Type.Optional(Type.Union([Type.Boolean(), Type.String()])), enable: Type.Optional(Type.Union([Type.Boolean(), Type.String()])),
}); });

View File

@@ -3,9 +3,9 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
user_id: Type.Union([Type.Number(), Type.String()]), user_id: Type.String(),
duration: Type.Union([Type.Number(), Type.String()], { default: 0 }), duration: Type.String({ default: '0' }),
}); });
type Payload = Static<typeof SchemaData>; type Payload = Static<typeof SchemaData>;

View File

@@ -3,8 +3,8 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
user_id: Type.Union([Type.Number(), Type.String()]), user_id: Type.String(),
card: Type.Optional(Type.String()) card: Type.Optional(Type.String())
}); });

View File

@@ -3,8 +3,8 @@ import { ActionName } from '@/onebot/action/router';
import { Static, Type } from '@sinclair/typebox'; import { Static, Type } from '@sinclair/typebox';
const SchemaData = Type.Object({ const SchemaData = Type.Object({
group_id: Type.Union([Type.Number(), Type.String()]), group_id: Type.String(),
user_id: Type.Union([Type.Number(), Type.String()]), user_id: Type.String(),
reject_add_request: Type.Optional(Type.Union([Type.Boolean(), Type.String()])), reject_add_request: Type.Optional(Type.Union([Type.Boolean(), Type.String()])),
}); });

Some files were not shown because too many files have changed in this diff Show More