🏗️ refactor file selection handling to improve response structure and utilize path data in SystemController
This commit is contained in:
parent
1882260096
commit
7515726a71
@ -3,6 +3,8 @@ import VersionService from "../service/VersionService";
|
||||
import ResponseUtils from "../utils/ResponseUtils";
|
||||
import VersionRepository from "../repository/VersionRepository";
|
||||
import Logger from "../core/Logger";
|
||||
import { BrowserWindow, dialog } from "electron";
|
||||
import BeanFactory from "../core/BeanFactory";
|
||||
|
||||
class VersionController extends BaseController {
|
||||
private readonly _versionService: VersionService;
|
||||
@ -81,15 +83,58 @@ class VersionController extends BaseController {
|
||||
}
|
||||
|
||||
importLocalFrpcVersion(req: ControllerParam) {
|
||||
this._versionService
|
||||
.importLocalFrpcVersion()
|
||||
.then(data => {
|
||||
req.event.reply(req.channel, ResponseUtils.success());
|
||||
const win: BrowserWindow = BeanFactory.getBean("win");
|
||||
dialog
|
||||
.showOpenDialog(win, {
|
||||
properties: ["openFile"],
|
||||
filters: [
|
||||
{ name: "Frpc", extensions: ["tar.gz", "zip"] } // 允许选择的文件类型,分开后缀以确保可以选择
|
||||
]
|
||||
})
|
||||
.catch((err: Error) => {
|
||||
.then(result => {
|
||||
if (result.canceled) {
|
||||
req.event.reply(
|
||||
req.channel,
|
||||
ResponseUtils.success({
|
||||
canceled: true
|
||||
})
|
||||
);
|
||||
return;
|
||||
} else {
|
||||
const filePath = result.filePaths[0];
|
||||
this._versionService
|
||||
.importLocalFrpcVersion(filePath)
|
||||
.then(data => {
|
||||
req.event.reply(
|
||||
req.channel,
|
||||
ResponseUtils.success({
|
||||
canceled: false
|
||||
})
|
||||
);
|
||||
})
|
||||
.catch((err: Error) => {
|
||||
Logger.error("VersionController.importLocalFrpcVersion", err);
|
||||
req.event.reply(req.channel, ResponseUtils.fail(err));
|
||||
});
|
||||
}
|
||||
})
|
||||
.catch(err => {
|
||||
Logger.error("VersionController.importLocalFrpcVersion", err);
|
||||
req.event.reply(req.channel, ResponseUtils.fail(err));
|
||||
});
|
||||
|
||||
// const win: BrowserWindow = BeanFactory.getBean("win");
|
||||
// const result = await dialog.showOpenDialog(win, {
|
||||
// properties: ["openFile"],
|
||||
// filters: [
|
||||
// { name: "Frpc", extensions: ["tar.gz", "zip"] } // 允许选择的文件类型,分开后缀以确保可以选择
|
||||
// ]
|
||||
// });
|
||||
// if (result.canceled) {
|
||||
//
|
||||
// }else {
|
||||
//
|
||||
// }
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1,8 +1,11 @@
|
||||
|
||||
enum ResponseCode {
|
||||
SUCCESS = "A1000:successful.",
|
||||
INTERNAL_ERROR = "B1000:internal error.",
|
||||
NOT_CONFIG = "B1001:未配置"
|
||||
SUCCESS = "A1000;successful.",
|
||||
INTERNAL_ERROR = "B1000;internal error.",
|
||||
NOT_CONFIG = "B1001;未配置",
|
||||
VERSION_EXISTS = "B1002;导入失败,版本已存在",
|
||||
VERSION_ARGS_ERROR = "B1003;所选 frp 架构与操作系统不符",
|
||||
UNKNOWN_VERSION = "B1004;无法识别文件"
|
||||
}
|
||||
|
||||
class BusinessError extends Error {
|
||||
@ -14,7 +17,7 @@ class BusinessError extends Error {
|
||||
// }
|
||||
|
||||
constructor(bizErrorEnum: ResponseCode) {
|
||||
const [bizCode, message] = bizErrorEnum.split(":");
|
||||
const [bizCode, message] = bizErrorEnum.split(";");
|
||||
super(message);
|
||||
this._bizCode = bizCode;
|
||||
this.name = "BusinessError";
|
||||
|
@ -7,12 +7,14 @@ import treeKill from "tree-kill";
|
||||
import BeanFactory from "../core/BeanFactory";
|
||||
import ResponseUtils from "../utils/ResponseUtils";
|
||||
import { BusinessError, ResponseCode } from "../core/BusinessError";
|
||||
import Logger from "../core/Logger";
|
||||
|
||||
class FrpcProcessService {
|
||||
private readonly _serverService: ServerService;
|
||||
private readonly _versionDao: VersionRepository;
|
||||
private _frpcProcess: any;
|
||||
private _frpcProcessListener: any;
|
||||
private _frpcLastStartTime: number = -1;
|
||||
|
||||
constructor(serverService: ServerService, versionDao: VersionRepository) {
|
||||
this._serverService = serverService;
|
||||
@ -42,7 +44,6 @@ class FrpcProcessService {
|
||||
const version = await this._versionDao.findByGithubReleaseId(
|
||||
config.frpcVersion
|
||||
);
|
||||
// todo genConfigfile.
|
||||
const configPath = PathUtils.getTomlConfigFilePath();
|
||||
await this._serverService.genTomlConfig(configPath);
|
||||
const command = `./${PathUtils.getFrpcFilename()} -c "${configPath}"`;
|
||||
@ -50,22 +51,33 @@ class FrpcProcessService {
|
||||
cwd: version.localPath,
|
||||
shell: true
|
||||
});
|
||||
this._frpcLastStartTime = Date.now();
|
||||
Logger.debug(
|
||||
`FrpcProcessService.startFrpcProcess`,
|
||||
`start command: ${command}`
|
||||
);
|
||||
this._frpcProcess.stdout.on("data", data => {
|
||||
console.log(`stdout: ${data}`);
|
||||
Logger.debug(`FrpcProcessService.startFrpcProcess`, `stdout: ${data}`);
|
||||
});
|
||||
|
||||
this._frpcProcess.stderr.on("data", data => {
|
||||
console.error(`stderr: ${data}`);
|
||||
Logger.debug(`FrpcProcessService.startFrpcProcess`, `stderr: ${data}`);
|
||||
});
|
||||
}
|
||||
|
||||
async stopFrpcProcess() {
|
||||
if (this._frpcProcess && this.isRunning()) {
|
||||
Logger.debug(
|
||||
`FrpcProcessService.stopFrpcProcess`,
|
||||
`pid: ${this._frpcProcess.pid}`
|
||||
);
|
||||
treeKill(this._frpcProcess.pid, (error: Error) => {
|
||||
if (error) {
|
||||
throw error;
|
||||
} else {
|
||||
this._frpcProcess = null;
|
||||
this._frpcLastStartTime = -1;
|
||||
|
||||
// clearInterval(this._frpcProcessListener);
|
||||
}
|
||||
});
|
||||
@ -80,12 +92,17 @@ class FrpcProcessService {
|
||||
// LogModule.FRP_CLIENT,
|
||||
// `Monitoring frpc process status: ${status}, Listener ID: ${frpcStatusListener}`
|
||||
// );
|
||||
console.log("running", running);
|
||||
Logger.debug(
|
||||
`FrpcProcessService.watchFrpcProcess`,
|
||||
`running: ${running}`
|
||||
);
|
||||
if (!running) {
|
||||
new Notification({
|
||||
title: app.getName(),
|
||||
body: "Connection lost, please check the logs for details."
|
||||
}).show();
|
||||
if (this._frpcLastStartTime !== -1) {
|
||||
new Notification({
|
||||
title: app.getName(),
|
||||
body: "Connection lost, please check the logs for details."
|
||||
}).show();
|
||||
}
|
||||
// logError(
|
||||
// LogModule.FRP_CLIENT,
|
||||
// "Frpc process status check failed. Connection lost."
|
||||
|
@ -65,6 +65,8 @@ class ServerService extends BaseService<OpenSourceFrpcDesktopServer> {
|
||||
const { frpcVersion, _id, system, ...commonConfig } = server;
|
||||
const frpcConfig = { ...commonConfig };
|
||||
frpcConfig.log.to = PathUtils.getFrpcLogFilePath();
|
||||
frpcConfig.loginFailExit = false;
|
||||
frpcConfig.webServer.addr = "127.0.0.1";
|
||||
const toml = TOML.stringify({ ...frpcConfig, proxies: enabledProxies });
|
||||
|
||||
fs.writeFileSync(
|
||||
|
@ -3,7 +3,7 @@ import BaseService from "./BaseService";
|
||||
import GitHubService from "./GitHubService";
|
||||
import frpReleasesJson from "../json/frp-releases.json";
|
||||
import { download } from "electron-dl";
|
||||
import { BrowserWindow, dialog } from "electron";
|
||||
import { BrowserWindow } from "electron";
|
||||
import GlobalConstant from "../core/GlobalConstant";
|
||||
import path from "path";
|
||||
import fs from "fs";
|
||||
@ -12,7 +12,7 @@ import PathUtils from "../utils/PathUtils";
|
||||
import FileUtils from "../utils/FileUtils";
|
||||
import frpChecksums from "../json/frp_all_sha256_checksums.json";
|
||||
import SystemService from "./SystemService";
|
||||
import BeanFactory from "../core/BeanFactory";
|
||||
import { BusinessError, ResponseCode } from "../core/BusinessError";
|
||||
|
||||
class VersionService extends BaseService<FrpcVersion> {
|
||||
private readonly _versionDao: VersionRepository;
|
||||
@ -165,36 +165,24 @@ class VersionService extends BaseService<FrpcVersion> {
|
||||
return false;
|
||||
}
|
||||
|
||||
async importLocalFrpcVersion() {
|
||||
const win: BrowserWindow = BeanFactory.getBean("win");
|
||||
const result = await dialog.showOpenDialog(win, {
|
||||
properties: ["openFile"],
|
||||
filters: [
|
||||
{ name: "Frpc", extensions: ["tar.gz", "zip"] } // 允许选择的文件类型,分开后缀以确保可以选择
|
||||
]
|
||||
});
|
||||
if (result.canceled) {
|
||||
return;
|
||||
} else {
|
||||
const filePath = result.filePaths[0];
|
||||
const checksum = FileUtils.calculateFileChecksum(filePath);
|
||||
const frpName = frpChecksums[checksum];
|
||||
if (frpName) {
|
||||
if (this._currFrpArch.every(item => frpName.includes(item))) {
|
||||
const version = this.getFrpVersionByAssetName(frpName);
|
||||
const existsVersion = await this._versionDao.findByGithubReleaseId(
|
||||
version.githubReleaseId
|
||||
);
|
||||
if (existsVersion) {
|
||||
throw new Error("导入失败,版本已存在");
|
||||
}
|
||||
return this.decompressFrp(version, filePath);
|
||||
} else {
|
||||
throw new Error(`导入失败,所选 frp 架构与操作系统不符`);
|
||||
async importLocalFrpcVersion(filePath: string) {
|
||||
const checksum = FileUtils.calculateFileChecksum(filePath);
|
||||
const frpName = frpChecksums[checksum];
|
||||
if (frpName) {
|
||||
if (this._currFrpArch.every(item => frpName.includes(item))) {
|
||||
const version = this.getFrpVersionByAssetName(frpName);
|
||||
const existsVersion = await this._versionDao.findByGithubReleaseId(
|
||||
version.githubReleaseId
|
||||
);
|
||||
if (existsVersion) {
|
||||
throw new BusinessError(ResponseCode.VERSION_EXISTS);
|
||||
}
|
||||
return this.decompressFrp(version, filePath);
|
||||
} else {
|
||||
throw new Error("导入失败,无法识别文件");
|
||||
throw new BusinessError(ResponseCode.VERSION_ARGS_ERROR);
|
||||
}
|
||||
} else {
|
||||
throw new BusinessError(ResponseCode.UNKNOWN_VERSION);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -2,7 +2,7 @@ import { BusinessError, ResponseCode } from "../core/BusinessError";
|
||||
|
||||
class ResponseUtils {
|
||||
public static success<T>(data?: any, message?: string) {
|
||||
const [bizCode, message2] = ResponseCode.SUCCESS.split(":");
|
||||
const [bizCode, message2] = ResponseCode.SUCCESS.split(";");
|
||||
const resp: ApiResponse<T> = {
|
||||
bizCode: bizCode,
|
||||
data: data,
|
||||
@ -22,16 +22,16 @@ class ResponseUtils {
|
||||
// }
|
||||
|
||||
public static fail(err: Error) {
|
||||
let bizCode = "";
|
||||
let message = "";
|
||||
if (err instanceof BusinessError) {
|
||||
bizCode = (err as BusinessError).bizCode;
|
||||
message = (err as BusinessError).message;
|
||||
if (!(err instanceof BusinessError)) {
|
||||
err = new BusinessError(ResponseCode.INTERNAL_ERROR);
|
||||
}
|
||||
const bizCode = (err as BusinessError).bizCode;
|
||||
const message = (err as BusinessError).message;
|
||||
|
||||
const resp: ApiResponse<any> = {
|
||||
bizCode: bizCode,
|
||||
data: null,
|
||||
message: message || "internal error."
|
||||
message: message
|
||||
};
|
||||
return resp;
|
||||
}
|
||||
|
@ -133,14 +133,34 @@ onMounted(() => {
|
||||
handleLoadAllVersions();
|
||||
});
|
||||
|
||||
on(ipcRouters.VERSION.importLocalFrpcVersion, () => {
|
||||
loading.value++;
|
||||
ElMessage({
|
||||
type: "success",
|
||||
message: "导入成功"
|
||||
});
|
||||
handleLoadAllVersions();
|
||||
});
|
||||
on(
|
||||
ipcRouters.VERSION.importLocalFrpcVersion,
|
||||
data => {
|
||||
const { canceled } = data;
|
||||
if (!canceled) {
|
||||
loading.value++;
|
||||
ElMessage({
|
||||
type: "success",
|
||||
message: "导入成功"
|
||||
});
|
||||
handleLoadAllVersions();
|
||||
}
|
||||
},
|
||||
(bizCode: string, message: string) => {
|
||||
if (bizCode === "B1002") {
|
||||
// 导入失败,版本已存在
|
||||
ElMessageBox.alert(`${message}`, `导入失败`);
|
||||
}
|
||||
if (bizCode === "B1003") {
|
||||
// 所选 frp 架构与操作系统不符
|
||||
ElMessageBox.alert(`${message}`, `导入失败`);
|
||||
}
|
||||
if (bizCode === "B1004") {
|
||||
// 无法识别文件
|
||||
ElMessageBox.alert(`${message}`, `导入失败`);
|
||||
}
|
||||
}
|
||||
);
|
||||
});
|
||||
|
||||
const handleImportFrp = () => {
|
||||
|
Loading…
Reference in New Issue
Block a user