Skip to content

Commit

Permalink
Merge pull request #1534 from yaklang/feature/control-yak-version-com…
Browse files Browse the repository at this point in the history
…mand

create event emits for fetching yak version
  • Loading branch information
luoluoTH authored Mar 29, 2024
2 parents 85e1cc4 + f60e1c0 commit 0ce9b25
Show file tree
Hide file tree
Showing 11 changed files with 940 additions and 889 deletions.
7 changes: 5 additions & 2 deletions app/main/filePath.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,6 @@ const osHome = os.homedir()
/** 软件关联数据文件夹名 */
const projectName = "yakit-projects"

console.log(`software: ${appPath}\n osHome: ${osHome}\n projectName: ${projectName}`)

/** 软件关联数据路径设置逻辑 Start */
// 数据文件夹路径
let project_path = ""
Expand Down Expand Up @@ -51,7 +49,12 @@ try {
* 如果获取项目关联文件夹路径错误时,将自动设置为系统用户下面(容灾处理)
*/
const YakitProjectPath = project_path || osHomeProjectPath

console.log(`---------- Global-Path Start ----------`)
console.log(`software-path: ${appPath}`)
console.log(`os-home-path: ${osHome}`)
console.log(`yakit-projects-path: ${YakitProjectPath}`)
console.log(`---------- Global-Path End ----------`)

/** 引擎文件夹路径 */
const yaklangEngineDir = path.join(YakitProjectPath, "yak-engine")
Expand Down
193 changes: 127 additions & 66 deletions app/main/handlers/upgradeUtil.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ const fs = require("fs");
const https = require("https");
const requestProgress = require("request-progress");
const request = require("request");
const EventEmitter = require('events');

const zip = require('node-stream-zip');
const {
Expand Down Expand Up @@ -87,8 +88,7 @@ function saveSecret(name, host, port, tls, password, caPem) {
}

authMeta.push({
host, port, tls, password, caPem,
name: name || `${host}:${port}`,
host, port, tls, password, caPem, name: name || `${host}:${port}`,
})
saveAllSecret([...authMeta])
};
Expand All @@ -103,11 +103,9 @@ const saveAllSecret = (authInfos) => {
}


const authFileStr = JSON.stringify(
[...authInfos.filter((v, i, arr) => {
return arr.findIndex(origin => origin.name === v.name) === i
})]
);
const authFileStr = JSON.stringify([...authInfos.filter((v, i, arr) => {
return arr.findIndex(origin => origin.name === v.name) === i
})]);
fs.writeFileSync(remoteLinkFile, new Buffer(authFileStr, "utf8"))
};

Expand Down Expand Up @@ -180,11 +178,9 @@ const getYakitPlatform = () => {
}

module.exports = {
getLatestYakLocalEngine,
initial: async () => {
getLatestYakLocalEngine, initial: async () => {
return await initMkbaseDir();
},
register: (win, getClient) => {
}, register: (win, getClient) => {
ipcMain.handle("save-yakit-remote-auth", async (e, params) => {
let {name, host, port, tls, caPem, password} = params;
name = name || `${host}:${port}`
Expand Down Expand Up @@ -262,45 +258,118 @@ module.exports = {
return await asyncQueryLatestYakitEngineVersion(params)
})


class YakVersionEmitter extends EventEmitter {
}

const yakVersionEmitter = new YakVersionEmitter();
let isFetchingVersion = false;
let latestVersionCache = null;

// asyncQueryLatestYakEngineVersion wrapper
const asyncGetCurrentLatestYakVersion = (params) => {
return new Promise((resolve, reject) => {
try {
childProcess.execFile(getLatestYakLocalEngine(), ["-v"], (err, stdout) => {
if (err) {
console.info("start to fetch YAK-VERSION")
if (latestVersionCache) {
console.info("YAK-VERSION: fetch cache: " + `${latestVersionCache}`)
resolve(latestVersionCache)
return;
}

console.info("YAK-VERSION: mount version")
yakVersionEmitter.once('version', (err, version) => {
if (err) {

diagnosingYakVersion().catch(err => {
console.info("YAK-VERSION(DIAG): fetch error: " + `${err}`)
reject(err)
return
}
// const version = stdout.replaceAll("yak version ()", "").trim();
const version = /.*?yak(\.exe)?\s+version\s+([^\s]+)/.exec(stdout)[2];
if (!version) {
if (err) {
reject(err)
} else {
reject("[unknown reason] cannot fetch yak version (yak -v)")
}
} else {
resolve(version)
}
})
} catch (e) {
reject(e)
}).then(() => {
console.info("YAK-VERSION: fetch error: " + `${err}`)
reject(err)
})
} else {
console.info("YAK-VERSION: hit version: " + `${version}`)
resolve(version);
}
})
if (isFetchingVersion) {
console.info("YAK-VERSION is executing...")
return;
}

console.info("YAK-VERSION process is executing...")
isFetchingVersion = true;
childProcess.execFile(getLatestYakLocalEngine(), ["-v"], (err, stdout) => {
console.info(stdout)
if (err) {
yakVersionEmitter.emit('version', err, null);
isFetchingVersion = false
return;
}
// const version = stdout.replaceAll("yak version ()", "").trim();
const match = /.*?yak(\.exe)?\s+version\s+(\S+)/.exec(stdout);
const version = match && match[2];
if (!version) {
const error = new Error("[unknown reason] cannot fetch yak version (yak -v)");
yakVersionEmitter.emit('version', error, null);
isFetchingVersion = false;
} else {
latestVersionCache = version;
yakVersionEmitter.emit('version', null, version);
isFetchingVersion = false
}
})
})
}
ipcMain.handle("get-current-yak", async (e, params) => {
return await asyncGetCurrentLatestYakVersion(params)
})

const diagnosingYakVersion = () => new Promise((resolve, reject) => {
const commandPath = getLatestYakLocalEngine()
fs.access(commandPath, fs.constants.X_OK, err => {
if (err) {
if (err.code === 'ENOENT') {
reject(new Error(`命令未找到: ${commandPath}`));
} else if (err.code === 'EACCES') {
reject(new Error(`命令无法执行(无权限): ${commandPath}`));
} else {
reject(new Error(`命令无法执行: ${commandPath}`));
}
return;
}

childProcess.execFile(commandPath, ['-v'], {timeout: 20000}, (error, stdout, stderr) => {
if (error) {
let errorMessage = `命令执行失败: ${error.message}\nStdout: ${stdout}\nStderr: ${stderr}`;
if (error.code === 'ENOENT') {
errorMessage = `无法执行命令,引擎未找到: ${commandPath}\nStderr: ${stderr}`;
} else if (error.killed) {
errorMessage = `引擎启动被系统强制终止,可能的原因为内存占用过多或系统退出或安全防护软件: ${commandPath}\nStderr: ${stderr}`;
} else if (error.signal) {
errorMessage = `引擎由于信号而终止: ${error.signal}\nStderr: ${stderr}`;
} else if (error.code === 'ETIMEDOUT') {
errorMessage = `命令执行超时,进程遭遇未知问题,需要用户在命令行中执行引擎调试: ${commandPath}\nStdout: ${stdout}\nStderr: ${stderr}`;
}

reject(new Error(errorMessage));
return;
}

resolve(stdout);
})
})
})
ipcMain.handle('diagnosing-yak-version', async (e, params) => {
return diagnosingYakVersion()
})

/** 获取Yakit Yaklang本地版本号 操作系统 架构 */
ipcMain.handle("fetch-local-basic-info", async (e) => {
const localYakit = app.getVersion()
const localYaklang = await asyncGetCurrentLatestYakVersion()
return {
system:process.platform,
arch:process.arch,
localYakit,
localYaklang
system: process.platform, arch: process.arch, localYakit, localYaklang
}
})

Expand Down Expand Up @@ -342,17 +411,17 @@ module.exports = {
const pattern = /[\u4e00-\u9fa5]/g; // 匹配中文字符的正则表达式
const matches = str.match(pattern); // 找到所有中文字符的匹配项
if (matches) {
for (const match of matches) {
const encodedMatch = encodeURIComponent(match);
str = str.replace(match, encodedMatch);
}
for (const match of matches) {
const encodedMatch = encodeURIComponent(match);
str = str.replace(match, encodedMatch);
}
}
return str;
}

const downloadYakitByDownloadUrl = (resolve,reject,downloadUrl) => {
const downloadYakitByDownloadUrl = (resolve, reject, downloadUrl) => {
// 可能存在中文的下载文件夹,就判断下Downloads文件夹是否存在,不存在则新建一个
if(!fs.existsSync(yakitInstallDir)) fs.mkdirSync(yakitInstallDir, {recursive: true})
if (!fs.existsSync(yakitInstallDir)) fs.mkdirSync(yakitInstallDir, {recursive: true})
const dest = path.join(yakitInstallDir, path.basename(downloadUrl));
try {
fs.unlinkSync(dest)
Expand All @@ -361,13 +430,12 @@ module.exports = {
}
// https://github.com/IndigoUnited/node-request-progress
// The options argument is optional so you can omit it
requestProgress(
request(encodeChineseCharacters(downloadUrl)), {
// throttle: 2000, // Throttle the progress event to 2000ms, defaults to 1000ms
// delay: 1000, // Only start to emit after 1000ms delay, defaults to 0ms
// lengthHeader: 'x-transfer-length' // Length header to use, defaults to content-length
})
.on("response",function (resp){
requestProgress(request(encodeChineseCharacters(downloadUrl)), {
// throttle: 2000, // Throttle the progress event to 2000ms, defaults to 1000ms
// delay: 1000, // Only start to emit after 1000ms delay, defaults to 0ms
// lengthHeader: 'x-transfer-length' // Length header to use, defaults to content-length
})
.on("response", function (resp) {
if (resp.statusCode === 404) {
reject("暂无最新安装包")
}
Expand All @@ -391,7 +459,7 @@ module.exports = {
version = version.substr(1)
}
const downloadUrl = getYakitDownloadUrl(version, isEnterprise);
downloadYakitByDownloadUrl(resolve,reject,downloadUrl)
downloadYakitByDownloadUrl(resolve, reject, downloadUrl)
})
}

Expand All @@ -401,12 +469,12 @@ module.exports = {

ipcMain.handle("download-enpriTrace-latest-yakit", async (e, url) => {
return await new Promise((resolve, reject) => {
downloadYakitByDownloadUrl(resolve,reject,url)
})
downloadYakitByDownloadUrl(resolve, reject, url)
})
})

ipcMain.handle("update-enpritrace-info", async () => {
return await {version:getYakitPlatform()}
return await {version: getYakitPlatform()}
})

ipcMain.handle("get-windows-install-dir", async (e) => {
Expand Down Expand Up @@ -446,18 +514,13 @@ module.exports = {
}


childProcess.exec(
isWindows ?
`copy "${origin}" "${dest}"`
: `cp "${origin}" "${dest}" && chmod +x "${dest}"`,
err => {
if (err) {
reject(err)
return
}
resolve()
childProcess.exec(isWindows ? `copy "${origin}" "${dest}"` : `cp "${origin}" "${dest}" && chmod +x "${dest}"`, err => {
if (err) {
reject(err)
return
}
)
resolve()
})
})
}

Expand Down Expand Up @@ -490,8 +553,7 @@ module.exports = {

console.info("Start to Extract yak.zip")
const zipHandler = new zip({
file: loadExtraFilePath(path.join("bins", "yak.zip")),
storeEntries: true,
file: loadExtraFilePath(path.join("bins", "yak.zip")), storeEntries: true,
})
console.info("Start to Extract yak.zip: Set `ready`")
zipHandler.on("ready", () => {
Expand Down Expand Up @@ -572,8 +634,7 @@ module.exports = {

// 获取内置引擎版本
ipcMain.handle("GetBuildInEngineVersion"
/*"IsBinsExisted"*/,
async (e) => {
/*"IsBinsExisted"*/, async (e) => {
const yakZipName = path.join("bins", "yak.zip")
if (!fs.existsSync(loadExtraFilePath(yakZipName))) {
throw Error(`Cannot found yak.zip, bins: ${loadExtraFilePath(yakZipName)}`)
Expand Down
Loading

0 comments on commit 0ce9b25

Please sign in to comment.