mirror of
https://github.com/NapNeko/NapCatQQ.git
synced 2025-07-19 12:03:37 +00:00
Compare commits
17 Commits
Author | SHA1 | Date | |
---|---|---|---|
![]() |
500b2d0e6d | ||
![]() |
e59d094feb | ||
![]() |
a8372f14f8 | ||
![]() |
5174ff422d | ||
![]() |
5c06751c3b | ||
![]() |
ac2b0118a6 | ||
![]() |
3eb8fd4abe | ||
![]() |
48b389ebe3 | ||
![]() |
065adeb2cd | ||
![]() |
269d0a06fe | ||
![]() |
8eca26b1a5 | ||
![]() |
3019ef7de4 | ||
![]() |
522311b547 | ||
![]() |
21061561ec | ||
![]() |
b83c41ad56 | ||
![]() |
e80a1cc64a | ||
![]() |
a01e4ca89f |
3
.github/ISSUE_TEMPLATE/bug_report.yml
vendored
3
.github/ISSUE_TEMPLATE/bug_report.yml
vendored
@@ -10,6 +10,7 @@ body:
|
||||
在提交新的 Bug 反馈前,请确保您:
|
||||
* 已经搜索了现有的 issues,并且没有找到可以解决您问题的方法
|
||||
* 不与现有的某一 issue 重复
|
||||
* 不涉及[已经停止维护的特性](https://github.com/NapNeko/NapCatQQ?tab=readme-ov-file#挥别昨日),例如 CQ 码
|
||||
- type: input
|
||||
id: system-version
|
||||
attributes:
|
||||
@@ -78,4 +79,4 @@ body:
|
||||
attributes:
|
||||
label: OneBot 客户端运行日志
|
||||
description: 粘贴 OneBot 客户端的相关日志内容到此处
|
||||
render: shell
|
||||
render: shell
|
||||
|
@@ -9,7 +9,7 @@ NapCatQQ (aka 猫猫框架) 是现代化的基于 NTQQ 的 Bot 协议端实现
|
||||
## 猫猫技能
|
||||
- [x] **高性能**:1K+ 群聊数目、20 线程并行发送消息毫无压力
|
||||
- [x] **多种启动方式**:支持以无头、LiteLoader 插件、仅 QQ GUI 三种方式启动
|
||||
- [x] **多平台支持**: 支持Windows/Linux(可选Docker)/Android Termux/MacOs覆盖全平台
|
||||
- [x] **多平台支持**: 覆盖 Windows / Linux (可选 Docker) / Android Termux / MacOS
|
||||
- [x] **安装简单**: 支持一键脚本/程序自动部署/镜像部署等多种覆盖范围
|
||||
- [x] **低占用**:无头模式占用资源极低,适合在服务器上运行
|
||||
- [x] **超多接口**:实现大部分 OneBot 和 go-cqhttp 接口,超多扩展 API
|
||||
@@ -38,4 +38,4 @@ NapCatQQ (aka 猫猫框架) 是现代化的基于 NTQQ 的 Bot 协议端实现
|
||||
> [!CAUTION]\
|
||||
> **请不要在 QQ 官方群聊和任何影响力较大的简中互联网平台(包括但不限于: 哔哩哔哩,微博,知乎,抖音等)发布和讨论*任何*与本项目存在相关性的信息**
|
||||
|
||||
任何使用本仓库代码的地方,都应当严格遵守[本仓库开源许可](./LICENSE)。**此外,禁止任何项目未经授权二次分发或基于 NapCat 代码开发。**
|
||||
任何使用本仓库代码的地方,都应当严格遵守[本仓库开源许可](./LICENSE)。**此外,禁止任何项目未经授权二次分发或基于 NapCat 代码开发。**
|
Binary file not shown.
Binary file not shown.
@@ -21,13 +21,12 @@ for /f "tokens=2*" %%a in ('reg query "HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\M
|
||||
)
|
||||
|
||||
:napcat_boot
|
||||
for %%a in (%RetString%) do (
|
||||
for %%a in ("%RetString%") do (
|
||||
set "pathWithoutUninstall=%%~dpa"
|
||||
)
|
||||
|
||||
SET QQPath=%pathWithoutUninstall%QQ.exe
|
||||
|
||||
REM 拿不到QQ路径则退出
|
||||
if not exist "%QQpath%" (
|
||||
echo provided QQ path is invalid: %QQpath%
|
||||
pause
|
||||
@@ -36,4 +35,6 @@ if not exist "%QQpath%" (
|
||||
set NAPCAT_MAIN_PATH=%NAPCAT_MAIN_PATH:\=/%
|
||||
echo (async () =^> {await import("file:///%NAPCAT_MAIN_PATH%")})() > %NAPCAT_LOAD_PATH%
|
||||
|
||||
"%NAPCAT_LAUNCHER_PATH%" "%QQPath%" "%NAPCAT_INJECT_PATH%"
|
||||
"%NAPCAT_LAUNCHER_PATH%" "%QQPath%" "%NAPCAT_INJECT_PATH%"
|
||||
|
||||
REM "%NAPCAT_LAUNCHER_PATH%" "%QQPath%" "%NAPCAT_INJECT_PATH%" 123456
|
@@ -21,7 +21,6 @@ for /f "tokens=2*" %%a in ('reg query "HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\M
|
||||
)
|
||||
|
||||
:napcat_boot
|
||||
:: %RetString% 增加引号,解决QQ目录包含空格的问题,比如安装在:C:\Program Files\Tencent\QQNT
|
||||
for %%a in ("%RetString%") do (
|
||||
set "pathWithoutUninstall=%%~dpa"
|
||||
)
|
||||
@@ -33,7 +32,10 @@ if not exist "%QQpath%" (
|
||||
pause
|
||||
exit /b
|
||||
)
|
||||
|
||||
set NAPCAT_MAIN_PATH=%NAPCAT_MAIN_PATH:\=/%
|
||||
echo (async () =^> {await import("file:///%NAPCAT_MAIN_PATH%")})() > %NAPCAT_LOAD_PATH%
|
||||
|
||||
"%NAPCAT_LAUNCHER_PATH%" "%QQPath%" "%NAPCAT_INJECT_PATH%"
|
||||
|
||||
REM "%NAPCAT_LAUNCHER_PATH%" "%QQPath%" "%NAPCAT_INJECT_PATH%" 123456
|
@@ -4,7 +4,7 @@
|
||||
"name": "NapCatQQ",
|
||||
"slug": "NapCat.Framework",
|
||||
"description": "高性能的 OneBot 11 协议实现",
|
||||
"version": "2.3.0",
|
||||
"version": "2.3.6",
|
||||
"icon": "./logo.png",
|
||||
"authors": [
|
||||
{
|
||||
|
@@ -2,7 +2,7 @@
|
||||
"name": "napcat",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"version": "2.3.0",
|
||||
"version": "2.3.6",
|
||||
"scripts": {
|
||||
"build:framework": "vite build --mode framework",
|
||||
"build:shell": "vite build --mode shell",
|
||||
|
@@ -167,7 +167,8 @@ export function rawMessageToText(msg: RawMessage, recursiveLevel = 0): string {
|
||||
function msgElementToText(element: MessageElement) {
|
||||
if (element.textElement) {
|
||||
if (element.textElement.atType === AtType.notAt) {
|
||||
return element.textElement.content;
|
||||
const originalContentLines = element.textElement.content.split('\n');
|
||||
return `${originalContentLines[0]}${originalContentLines.length > 1 ? ' ...' : ''}`;
|
||||
} else if (element.textElement.atType === AtType.atAll) {
|
||||
return `@全体成员`;
|
||||
} else if (element.textElement.atType === AtType.atUser) {
|
||||
@@ -189,7 +190,7 @@ export function rawMessageToText(msg: RawMessage, recursiveLevel = 0): string {
|
||||
}
|
||||
|
||||
if (element.picElement) {
|
||||
return `[图片 ${element.picElement.fileName}]`;
|
||||
return '[图片]';
|
||||
}
|
||||
|
||||
if (element.fileElement) {
|
||||
@@ -197,7 +198,7 @@ export function rawMessageToText(msg: RawMessage, recursiveLevel = 0): string {
|
||||
}
|
||||
|
||||
if (element.videoElement) {
|
||||
return `[视频 ${element.videoElement.fileName}]`;
|
||||
return '[视频]';
|
||||
}
|
||||
|
||||
if (element.pttElement) {
|
||||
@@ -205,7 +206,7 @@ export function rawMessageToText(msg: RawMessage, recursiveLevel = 0): string {
|
||||
}
|
||||
|
||||
if (element.arkElement) {
|
||||
return `[卡片消息 ${element.arkElement.bytesData}]`;
|
||||
return '[卡片消息]';
|
||||
}
|
||||
|
||||
if (element.faceElement) {
|
||||
@@ -213,19 +214,19 @@ export function rawMessageToText(msg: RawMessage, recursiveLevel = 0): string {
|
||||
}
|
||||
|
||||
if (element.marketFaceElement) {
|
||||
return `[商城表情 ${element.marketFaceElement.faceName}]`;
|
||||
return element.marketFaceElement.faceName;
|
||||
}
|
||||
|
||||
if (element.markdownElement) {
|
||||
return `[Markdown ${element.markdownElement.content}]`;
|
||||
return '[Markdown 消息]';
|
||||
}
|
||||
|
||||
if (element.multiForwardMsgElement) {
|
||||
return `[转发消息]`;
|
||||
return '[转发消息]';
|
||||
}
|
||||
|
||||
if (element.elementType === ElementType.GreyTip) {
|
||||
return `[灰条消息]`; // TODO: resolve the text
|
||||
return '[灰条消息]';
|
||||
}
|
||||
|
||||
return `[未实现 (ElementType = ${element.elementType})]`;
|
||||
|
@@ -1 +1 @@
|
||||
export const napCatVersion = '2.3.0';
|
||||
export const napCatVersion = '2.3.6';
|
||||
|
@@ -298,65 +298,6 @@ export class NTQQFileApi {
|
||||
});
|
||||
}
|
||||
|
||||
async addFileCache(peer: Peer, msgId: string, msgSeq: string, senderUid: string, elemId: string, elemType: string, fileSize: string, fileName: string) {
|
||||
let GroupData;
|
||||
let BuddyData;
|
||||
if (peer.chatType === ChatType.KCHATTYPEGROUP) {
|
||||
GroupData =
|
||||
[{
|
||||
groupCode: peer.peerUid,
|
||||
isConf: false,
|
||||
hasModifyConfGroupFace: true,
|
||||
hasModifyConfGroupName: true,
|
||||
groupName: 'NapCat.Cached',
|
||||
remark: 'NapCat.Cached',
|
||||
}];
|
||||
} else if (peer.chatType === ChatType.KCHATTYPEC2C) {
|
||||
BuddyData = [{
|
||||
category_name: 'NapCat.Cached',
|
||||
peerUid: peer.peerUid,
|
||||
peerUin: peer.peerUid,
|
||||
remark: 'NapCat.Cached',
|
||||
}];
|
||||
} else {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
return this.context.session.getSearchService().addSearchHistory({
|
||||
type: 4,
|
||||
contactList: [],
|
||||
id: -1,
|
||||
groupInfos: [],
|
||||
msgs: [],
|
||||
fileInfos: [
|
||||
{
|
||||
chatType: peer.chatType,
|
||||
buddyChatInfo: BuddyData || [],
|
||||
discussChatInfo: [],
|
||||
groupChatInfo: GroupData || [],
|
||||
dataLineChatInfo: [],
|
||||
tmpChatInfo: [],
|
||||
msgId: msgId,
|
||||
msgSeq: msgSeq,
|
||||
msgTime: Math.floor(Date.now() / 1000).toString(),
|
||||
senderUid: senderUid,
|
||||
senderNick: 'NapCat.Cached',
|
||||
senderRemark: 'NapCat.Cached',
|
||||
senderCard: 'NapCat.Cached',
|
||||
elemId: elemId,
|
||||
elemType: elemType,
|
||||
fileSize: fileSize,
|
||||
filePath: '',
|
||||
fileName: fileName,
|
||||
hits: [{
|
||||
start: 12,
|
||||
end: 14,
|
||||
}],
|
||||
},
|
||||
],
|
||||
});
|
||||
}
|
||||
|
||||
async searchForFile(keys: string[]): Promise<SearchResultItem | undefined> {
|
||||
const randomResultId = 100000 + Math.floor(Math.random() * 10000);
|
||||
let searchId = 0;
|
||||
|
@@ -9,8 +9,9 @@ import {
|
||||
MemberExtSourceType,
|
||||
NapCatCore,
|
||||
} from '@/core';
|
||||
import { isNumeric } from '@/common/helper';
|
||||
import { isNumeric, solveAsyncProblem } from '@/common/helper';
|
||||
import { LimitedHashTable } from '@/common/message-unique';
|
||||
import { NTEventWrapper } from '@/common/event';
|
||||
|
||||
export class NTQQGroupApi {
|
||||
context: InstanceContext;
|
||||
@@ -264,7 +265,27 @@ export class NTQQGroupApi {
|
||||
}
|
||||
return member;
|
||||
}
|
||||
|
||||
async getGroupMemberEx(GroupCode: string, uid: string, forced = false, retry = 2) {
|
||||
let data = await solveAsyncProblem((eventWrapper: NTEventWrapper, GroupCode: string, uid: string, forced = false) => {
|
||||
return eventWrapper.callNormalEventV2(
|
||||
'NodeIKernelGroupService/getMemberInfo',
|
||||
'NodeIKernelGroupListener/onMemberInfoChange',
|
||||
[GroupCode, [uid], forced],
|
||||
(ret) => ret.result === 0,
|
||||
(params, _, members) => params === GroupCode && members.size > 0 && members.has(uid),
|
||||
1,
|
||||
forced ? 2500 : 250
|
||||
);
|
||||
}, this.core.eventWrapper, GroupCode, uid, forced);
|
||||
if (data && data[3] instanceof Map && data[3].has(uid)) {
|
||||
return data[3].get(uid);
|
||||
}
|
||||
if (retry > 0) {
|
||||
let trydata = await this.getGroupMemberEx(GroupCode, uid, true, retry - 1) as GroupMember | undefined;
|
||||
if (trydata) return trydata;
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
async getGroupMembersV2(groupQQ: string, num = 3000): Promise<Map<string, GroupMember>> {
|
||||
const groupService = this.context.session.getGroupService();
|
||||
const sceneId = groupService.createMemberListScene(groupQQ, 'groupMemberList_MainWindow');
|
||||
|
@@ -11,7 +11,7 @@ export default class GetGroupAddRequest extends BaseAction<null, OB11GroupReques
|
||||
actionName = ActionName.GetGroupIgnoreAddRequest;
|
||||
|
||||
async _handle(payload: null): Promise<OB11GroupRequestNotify[] | null> {
|
||||
const data = await this.core.apis.GroupApi.getGroupIgnoreNotifies();
|
||||
// const data = await this.core.apis.GroupApi.getGroupIgnoreNotifies();
|
||||
// log(data);
|
||||
// const notifies: GroupNotify[] = data.notifies.filter(notify => notify.status === GroupNotifyStatus.WAIT_HANDLE);
|
||||
// const returnData: OB11GroupRequestNotify[] = [];
|
||||
|
@@ -26,7 +26,7 @@ class GetGroupMemberInfo extends BaseAction<Payload, OB11GroupMember> {
|
||||
const uid = await this.core.apis.UserApi.getUidByUinV2(payload.user_id.toString());
|
||||
if (!uid) throw new Error(`Uin2Uid Error ${payload.user_id}不存在`);
|
||||
const [member, info] = await Promise.allSettled([
|
||||
this.core.apis.GroupApi.getGroupMemberV2(payload.group_id.toString(), uid, isNocache),
|
||||
this.core.apis.GroupApi.getGroupMemberEx(payload.group_id.toString(), uid, isNocache),
|
||||
this.core.apis.UserApi.getUserDetailInfo(uid),
|
||||
]);
|
||||
if (member.status !== 'fulfilled') throw new Error(`群(${payload.group_id})成员${payload.user_id}获取失败 ${member.reason}`);
|
||||
|
@@ -115,6 +115,7 @@ export class OneBotMsgApi {
|
||||
file_id: encodedFileId,
|
||||
url: await this.core.apis.FileApi.getImageUrl(element),
|
||||
file_size: element.fileSize,
|
||||
file_unique: element.fileName
|
||||
},
|
||||
};
|
||||
} catch (e: any) {
|
||||
@@ -129,20 +130,6 @@ export class OneBotMsgApi {
|
||||
peerUid: msg.peerUid,
|
||||
guildId: '',
|
||||
};
|
||||
await this.core.apis.FileApi.addFileCache(
|
||||
{
|
||||
peerUid: msg.peerUid,
|
||||
chatType: msg.chatType,
|
||||
guildId: '',
|
||||
},
|
||||
msg.msgId,
|
||||
msg.msgSeq,
|
||||
msg.senderUid,
|
||||
elementWrapper.elementId,
|
||||
elementWrapper.elementType.toString(),
|
||||
element.fileSize,
|
||||
element.fileName,
|
||||
);
|
||||
return {
|
||||
type: OB11MessageDataType.file,
|
||||
data: {
|
||||
@@ -151,6 +138,7 @@ export class OneBotMsgApi {
|
||||
url: element.filePath,
|
||||
file_id: FileNapCatOneBotUUID.encode(peer, msg.msgId, elementWrapper.elementId),
|
||||
file_size: element.fileSize,
|
||||
file_unique: element.fileName,
|
||||
},
|
||||
};
|
||||
},
|
||||
@@ -182,20 +170,6 @@ export class OneBotMsgApi {
|
||||
},
|
||||
|
||||
marketFaceElement: async (_, msg, elementWrapper) => {
|
||||
await this.core.apis.FileApi.addFileCache(
|
||||
{
|
||||
peerUid: msg.peerUid,
|
||||
chatType: msg.chatType,
|
||||
guildId: '',
|
||||
},
|
||||
msg.msgId,
|
||||
msg.msgSeq,
|
||||
msg.senderUid,
|
||||
elementWrapper.elementId,
|
||||
elementWrapper.elementType.toString(),
|
||||
'0',
|
||||
'marketface',
|
||||
);
|
||||
const peer = {
|
||||
chatType: msg.chatType,
|
||||
peerUid: msg.peerUid,
|
||||
@@ -208,6 +182,7 @@ export class OneBotMsgApi {
|
||||
file_id: FileNapCatOneBotUUID.encode(peer, msg.msgId, elementWrapper.elementId),
|
||||
path: elementWrapper.elementId,
|
||||
url: elementWrapper.elementId,
|
||||
file_unique: _.key
|
||||
},
|
||||
};
|
||||
},
|
||||
@@ -283,21 +258,6 @@ export class OneBotMsgApi {
|
||||
videoDownUrl = element.filePath;
|
||||
}
|
||||
|
||||
await this.core.apis.FileApi.addFileCache(
|
||||
{
|
||||
peerUid: msg.peerUid,
|
||||
chatType: msg.chatType,
|
||||
guildId: '',
|
||||
},
|
||||
msg.msgId,
|
||||
msg.msgSeq,
|
||||
msg.senderUid,
|
||||
elementWrapper.elementId,
|
||||
elementWrapper.elementType.toString(),
|
||||
element.fileSize ?? '0',
|
||||
element.fileName,
|
||||
);
|
||||
|
||||
return {
|
||||
type: OB11MessageDataType.video,
|
||||
data: {
|
||||
@@ -306,6 +266,7 @@ export class OneBotMsgApi {
|
||||
url: videoDownUrl,
|
||||
file_id: FileNapCatOneBotUUID.encode(peer, msg.msgId, elementWrapper.elementId),
|
||||
file_size: element.fileSize,
|
||||
file_unique: element.fileName,
|
||||
},
|
||||
};
|
||||
},
|
||||
@@ -316,20 +277,6 @@ export class OneBotMsgApi {
|
||||
peerUid: msg.peerUid,
|
||||
guildId: '',
|
||||
};
|
||||
await this.core.apis.FileApi.addFileCache(
|
||||
{
|
||||
peerUid: msg.peerUid,
|
||||
chatType: msg.chatType,
|
||||
guildId: '',
|
||||
},
|
||||
msg.msgId,
|
||||
msg.msgSeq,
|
||||
msg.senderUid,
|
||||
elementWrapper.elementId,
|
||||
elementWrapper.elementType.toString(),
|
||||
element.fileSize || '0',
|
||||
element.fileUuid || '',
|
||||
);
|
||||
return {
|
||||
type: OB11MessageDataType.voice,
|
||||
data: {
|
||||
@@ -730,8 +677,10 @@ export class OneBotMsgApi {
|
||||
if (ret.result === 0) {
|
||||
resMsg.group_id = parseInt(ret.tmpChatInfo!.groupCode);
|
||||
resMsg.sender.nickname = ret.tmpChatInfo!.fromNick;
|
||||
resMsg.temp_source = resMsg.group_id;
|
||||
} else {
|
||||
resMsg.group_id = 284840486; //兜底数据
|
||||
resMsg.temp_source = resMsg.group_id;
|
||||
resMsg.sender.nickname = '临时会话';
|
||||
}
|
||||
}
|
||||
|
@@ -66,10 +66,7 @@ export function encodeCQCode(data: OB11MessageData) {
|
||||
|
||||
let result = '[CQ:' + data.type;
|
||||
for (const name in data.data) {
|
||||
const value =
|
||||
// eslint-disable-next-line
|
||||
// @ts-ignore
|
||||
data.data[name];
|
||||
const value = (data.data as any)[name];
|
||||
if (value === undefined) {
|
||||
continue;
|
||||
}
|
||||
|
@@ -98,7 +98,7 @@ export class NapCatOneBot11Adapter {
|
||||
if (ob11Config.http.enablePost) {
|
||||
ob11Config.http.postUrls.forEach(url => {
|
||||
this.networkManager.registerAdapter(new OB11ActiveHttpAdapter(
|
||||
url, ob11Config.token, this.core, this,
|
||||
url, ob11Config.http.secret, this.core, this,
|
||||
));
|
||||
});
|
||||
}
|
||||
@@ -168,7 +168,7 @@ export class NapCatOneBot11Adapter {
|
||||
if (now.http.enablePost) {
|
||||
now.http.postUrls.forEach(url => {
|
||||
this.networkManager.registerAdapterAndOpen(new OB11ActiveHttpAdapter(
|
||||
url, now.token, this.core, this,
|
||||
url, now.http.secret, this.core, this,
|
||||
));
|
||||
});
|
||||
} else {
|
||||
@@ -182,7 +182,7 @@ export class NapCatOneBot11Adapter {
|
||||
);
|
||||
for (const url of added) {
|
||||
await this.networkManager.registerAdapterAndOpen(new OB11ActiveHttpAdapter(
|
||||
url, now.token, this.core, this,
|
||||
url, now.http.secret, this.core, this,
|
||||
));
|
||||
}
|
||||
}
|
||||
|
@@ -8,6 +8,7 @@ export enum OB11MessageType {
|
||||
}
|
||||
|
||||
export interface OB11Message {
|
||||
temp_source?: number;
|
||||
message_sent_type?: string;
|
||||
target_id?: number; // 自己发送的消息才有此字段
|
||||
self_id?: number,
|
||||
|
@@ -3,6 +3,7 @@ import { ALLRouter } from './src/router';
|
||||
import { LogWrapper } from '@/common/log';
|
||||
import { NapCatPathWrapper } from '@/common/path';
|
||||
import { WebUiConfigWrapper } from './src/helper/config';
|
||||
import { RequestUtil } from '@/common/request';
|
||||
|
||||
const app = express();
|
||||
|
||||
@@ -38,7 +39,23 @@ export async function InitWebUi(logger: LogWrapper, pathWrapper: NapCatPathWrapp
|
||||
app.use(config.prefix + '/api', ALLRouter);
|
||||
app.listen(config.port, config.host, async () => {
|
||||
log(`[NapCat] [WebUi] Current WebUi is running at http://${config.host}:${config.port}${config.prefix}`);
|
||||
log(`[NapCat] [WebUi] Login URL is http://${config.host}:${config.port}${config.prefix}/webui`);
|
||||
log(`[NapCat] [WebUi] Login Token is ${config.token}`);
|
||||
log(`[NapCat] [WebUi] WebUi User Panel Url: http://${config.host}:${config.port}${config.prefix}/webui?token=${config.token}`);
|
||||
log(`[NapCat] [WebUi] WebUi Local Panel Url: http://127.0.0.1:${config.port}${config.prefix}/webui?token=${config.token}`);
|
||||
//获取上网Ip
|
||||
//https://www.ip.cn/api/index?ip&type=0
|
||||
RequestUtil.HttpGetJson<{ IP: {IP:string} }>(
|
||||
'https://ip.011102.xyz/',
|
||||
'GET',
|
||||
{},
|
||||
{},
|
||||
true,
|
||||
true
|
||||
).then((data) => {
|
||||
log(`[NapCat] [WebUi] WebUi Publish Panel Url: http://${data.IP.IP}:${config.port}${config.prefix}/webui/?token=${config.token}`);
|
||||
}).catch((err) => {
|
||||
logger.logError(`[NapCat] [WebUi] Get Publish Panel Url Error: ${err}`);
|
||||
});
|
||||
|
||||
});
|
||||
}
|
||||
|
@@ -30,7 +30,7 @@ async function onSettingWindowCreated(view: Element) {
|
||||
SettingItem(
|
||||
'<span id="napcat-update-title">Napcat</span>',
|
||||
undefined,
|
||||
SettingButton('V2.3.0', 'napcat-update-button', 'secondary'),
|
||||
SettingButton('V2.3.6', 'napcat-update-button', 'secondary'),
|
||||
),
|
||||
]),
|
||||
SettingList([
|
||||
|
@@ -164,7 +164,7 @@ async function onSettingWindowCreated(view) {
|
||||
SettingItem(
|
||||
'<span id="napcat-update-title">Napcat</span>',
|
||||
void 0,
|
||||
SettingButton("V2.3.0", "napcat-update-button", "secondary")
|
||||
SettingButton("V2.3.6", "napcat-update-button", "secondary")
|
||||
)
|
||||
]),
|
||||
SettingList([
|
||||
|
Reference in New Issue
Block a user