"use strict";
|
|
import {
|
app,
|
protocol,
|
BrowserWindow,
|
ipcMain,
|
ipcRenderer,
|
dialog,
|
shell,
|
Menu,
|
webContents,
|
} from "electron";
|
import { autoUpdater } from "electron-updater";
|
import { createProtocol } from "vue-cli-plugin-electron-builder/lib";
|
// import installExtension, { VUEJS_DEVTOOLS } from 'electron-devtools-installer'
|
import path from "path";
|
import child_process from "child_process";
|
import log from "electron-log";
|
import update from "./update";
|
import config from "./assets/js/config";
|
const { lang } = config;
|
|
autoUpdater.logger = log;
|
autoUpdater.logger.transports.file.level = "info";
|
|
let win = null;
|
let loadingWin = null;
|
|
// 调试自动升级
|
/**
|
* checkForUpdatesAndNotify() just won't work in development mode.
|
*
|
* If you insist on test it in dev mode, you can do some hack with isPackaged:
|
*
|
* Be careful, do not use this hack for production
|
*
|
* Object.defineProperty(app, 'isPackaged', {
|
get() {
|
return true;
|
}
|
});
|
*
|
*
|
*/
|
// Object.defineProperty(app, 'isPackaged', {
|
// get() {
|
// return true;
|
// }
|
// });
|
|
// 单例锁
|
const gotTheLock = app.requestSingleInstanceLock();
|
|
if (!gotTheLock) {
|
app.quit();
|
} else {
|
app.on("second-instance", (event, commandLine, workingDirectory) => {
|
// 当运行第二个实例时,将会聚焦到myWindow这个窗口
|
if (win) {
|
if (win.isMinimized()) win.restore();
|
win.focus();
|
if (commandLine[2]) {
|
win.webContents.send(
|
"selected-file",
|
{ filePaths: [commandLine[2]] },
|
"MenuList"
|
);
|
}
|
}
|
});
|
}
|
|
const remote = require("@electron/remote/main");
|
remote.initialize();
|
// remote.enable()
|
|
const isDevelopment = process.env.NODE_ENV !== "production";
|
|
// const appUrl = 'http://localhost:8093/res/testParam/factorsAndThreshold';
|
const appUrl = "http://localhost:8093/res/testParam/callService?seconds=3";
|
const requestPromise = require("minimal-request-promise");
|
const checkService = function (cb) {
|
requestPromise.get(appUrl).then(
|
function (response) {
|
log.info(response);
|
log.info("Server started!");
|
cb();
|
},
|
function (response) {
|
log.warn(response);
|
log.info("Waiting for the server start...");
|
setTimeout(function () {
|
checkService(cb);
|
}, 500);
|
}
|
);
|
};
|
// const path = require('path');
|
|
// Scheme must be registered before the app is ready
|
protocol.registerSchemesAsPrivileged([
|
{ scheme: "app", privileges: { secure: true, standard: true, stream: true } },
|
]);
|
|
// TODO debug;
|
// win.webContents.openDevTools()
|
|
if (!isDevelopment) {
|
Menu.setApplicationMenu(null);
|
}
|
|
// loading 窗口
|
const loadingURL = isDevelopment
|
? path.join(__dirname, "./loading.html")
|
: `file://${__dirname}/loading.html`;
|
const showLoading = (cb, argFn) => {
|
loadingWin = new BrowserWindow({
|
// show: false,
|
frame: false,
|
width: 260,
|
height: 260,
|
resizable: false,
|
transparent: true,
|
webPreferences: {
|
preload: path.join(__dirname, "./preload.js"),
|
},
|
});
|
// loadingWin.once('show', () => {
|
// cb(true);
|
// });
|
// loadingWin.webContents.openDevTools();
|
loadingWin.loadURL(loadingURL);
|
loadingWin.setSkipTaskbar(true);
|
// loadingWin.show();
|
cb(true, argFn);
|
// 启动java程序
|
// if (platform === 'win32') {
|
// ipcMain.once('renderer-ready', (event, data) => {
|
// let dir = path.resolve(__dirname, '..');
|
// serverProcess = require('child_process').execFile(dir + '/app_x64.exe');
|
// });
|
// }
|
requestPromise.get(appUrl).then(
|
function () {
|
log.info("窗口初始化 服务正常");
|
// ipcRenderer.send('java-ready');
|
loadingWin.webContents.send("java-ready");
|
},
|
function () {
|
log.info("窗口初始化 接口不通");
|
log.info("正在终止java进程,然后重启服务");
|
update(win.webContents, true);
|
let stop = child_process.spawn("cmd.exe", ["/c", "stop.bat"]);
|
stop.on("exit", function (code) {
|
if (code > 0) {
|
log.info('执行stop.bat没有正确exit, 错误码:' + code);
|
return false;
|
}
|
log.info("java进程被终止,准备重启服务");
|
child_process.exec(
|
`"${process.cwd()}\\ResMeterManager.exe" restart`,
|
(err) => {
|
if (err) {
|
log.info("重启服务出错了stderr: " + JSON.stringify(err));
|
// 重新运行setup批处理 尝试重新注册服务
|
child_process.spawn("cmd.exe", ["/c", "setup_service.bat"]);
|
log.info("服务异常 正在尝试重新注册服务");
|
} else {
|
log.info("服务重启成功,连接中");
|
}
|
// 等到服务就绪再重启
|
checkService(() => {
|
loadingWin.webContents.send("java-ready");
|
});
|
}
|
);
|
});
|
stop.on('error', (code, data) => {
|
log.info('stop.bat 执行 error');
|
log.info(code);
|
log.info(data);
|
});
|
// // 重启服务 然后重启应用
|
// let restart = child_process.spawn('.\\ResMeterManager.exe', ['restart']);
|
// restart.stdout.on('data', function (data) {
|
// log.info('stdout: ' + data);
|
// });
|
|
// restart.stderr.on('data', function (data) {
|
// log.info('stderr: ' + data);
|
// });
|
|
// restart.on('exit', (code) => {
|
// if (code > 0) {
|
// return false;
|
// }
|
// log.info('服务重启成功,连接中');
|
// // 等到服务就绪再重启
|
// checkService(() => {
|
// loadingWin.webContents.send('java-ready');
|
// });
|
// });
|
}
|
);
|
};
|
async function createWindow(wait, cb) {
|
// Create the browser window.
|
win = new BrowserWindow({
|
show: !wait,
|
width: 1000,
|
height: 600,
|
webPreferences: {
|
// Use pluginOptions.nodeIntegration, leave this alone
|
// See nklayman.github.io/vue-cli-plugin-electron-builder/guide/security.html#node-integration for more info
|
// nodeIntegration: process.env.ELECTRON_NODE_INTEGRATION,
|
// contextIsolation: !process.env.ELECTRON_NODE_INTEGRATION
|
nodeIntegration: false,
|
webSecurity: true,
|
allowEval: false,
|
allowRunningInsecureContent: false,
|
contextIsolation: true,
|
enableRemoteModule: false,
|
preload: path.join(__dirname, "preload.js"),
|
},
|
});
|
|
// remote.enable(win.webContents);
|
if (process.env.WEBPACK_DEV_SERVER_URL) {
|
// Load the url of the dev server if in development mode
|
await win.loadURL(process.env.WEBPACK_DEV_SERVER_URL);
|
if (!process.env.IS_TEST) win.webContents.openDevTools();
|
} else {
|
createProtocol("app");
|
// Load the index.html when not in development
|
win.loadURL("app://./index.html");
|
}
|
|
if (wait) {
|
ipcMain.on("java-ready", () => {
|
log.info("java-ready!");
|
loadingWin.hide();
|
loadingWin.close();
|
win.show();
|
});
|
}
|
|
if (cb && "function" == typeof cb) {
|
win.once("ready-to-show", () => {
|
cb(win.webContents);
|
});
|
}
|
|
// 英文版不做升级
|
// 自动检测更新 软件的第一个实例打开后 为了不影响加载速度 在指定时间后做一次自检
|
win.once("ready-to-show", () => {
|
log.info("ready event");
|
|
// TODO
|
if ('US' != lang) {
|
setTimeout(() => {
|
update(win.webContents, true);
|
}, 1000 * 30);
|
}
|
});
|
|
win.webContents.session.on("will-download", (e, item) => {
|
// const filePath = path.join(saveUrl, item.getFilename());
|
// item.setSavePath(filePath); // 'C:\Users\kim\Downloads\第12次.zip'
|
// let value;
|
// //监听下载过程,计算并设置进度条进度
|
// item.on('updated', (evt, state) => {
|
// if ('progressing' === state) {
|
// //此处 用接收到的字节数和总字节数求一个比例 就是进度百分比
|
// if (item.getReceivedBytes() && item.getTotalBytes()) {
|
// value = parseInt(
|
// 100 * (
|
// item.getReceivedBytes() / item.getTotalBytes()
|
// )
|
// )
|
// }
|
// // 把百分比发给渲染进程进行展示
|
// // win.webContents.send('updateProgressing', value);
|
// // mac 程序坞、windows 任务栏显示进度
|
// win.setProgressBar(value);
|
// }
|
// });
|
//监听下载结束事件
|
item.on("done", (e, state) => {
|
//如果窗口还在的话,去掉进度条
|
// if (!win.isDestroyed()) {
|
// win.setProgressBar(-1);
|
// }
|
//下载被取消或中断了
|
if (state === "interrupted") {
|
dialog.showErrorBox(
|
"下载失败",
|
`文件 ${item.getFilename()} 因为某些原因被中断下载`
|
);
|
}
|
// 下载成功后打开文件所在文件夹
|
if (state === "completed") {
|
setTimeout(() => {
|
shell.showItemInFolder(item.getSavePath());
|
}, 1000);
|
}
|
});
|
});
|
}
|
|
// Quit when all windows are closed.
|
app.on("window-all-closed", () => {
|
// On macOS it is common for applications and their menu bar
|
// to stay active until the user quits explicitly with Cmd + Q
|
if (process.platform !== "darwin") {
|
app.quit();
|
}
|
});
|
|
app.on("activate", () => {
|
log.info("app activate event");
|
// On macOS it's common to re-create a window in the app when the
|
// dock icon is clicked and there are no other windows open.
|
if (BrowserWindow.getAllWindows().length === 0) createWindow();
|
});
|
|
// This method will be called when Electron has finished
|
// initialization and is ready to create browser windows.
|
// Some APIs can only be used after this event occurs.
|
app.on("ready", async () => {
|
log.info("app ready event");
|
let cb = undefined;
|
if (process.argv[1]) {
|
cb = (sender) => {
|
log.info("call selected-file.." + process.argv[1]);
|
sender.send(
|
"selected-file",
|
{ filePaths: [process.argv[1]] },
|
"MenuList"
|
);
|
};
|
}
|
if (isDevelopment) {
|
createWindow();
|
} else {
|
showLoading(createWindow, cb);
|
}
|
});
|
|
// 所有的新开窗口事件都调用系统默认浏览器来打开页面
|
app.on("web-contents-created", (e, webContents) => {
|
webContents.on("new-window", (event, url) => {
|
event.preventDefault();
|
shell.openExternal(url);
|
});
|
});
|
|
ipcMain.on("open-file-dialog", (event, data) => {
|
dialog
|
.showOpenDialog({
|
filters: [{ name: "xml", extensions: ["xml"] }],
|
properties: ["openFile"],
|
})
|
.then((files) => {
|
// console.log(files, '0000000')
|
if (files) {
|
event.sender.send("selected-file", files, data);
|
}
|
});
|
});
|
ipcMain.on("open-directory-dialog", (event, data) => {
|
dialog
|
.showOpenDialog({
|
properties: ["openDirectory"],
|
})
|
.then((files) => {
|
if (files) {
|
event.sender.send("selected-directory", files, data);
|
}
|
});
|
});
|
|
ipcMain.on("check-update", (event) => {
|
// checkForUpdates();
|
update(event.sender);
|
});
|
|
ipcMain.on("download-update", () => {
|
autoUpdater.downloadUpdate();
|
});
|
|
ipcMain.on("quitAndInstall", () => {
|
autoUpdater.quitAndInstall();
|
});
|
|
ipcMain.on("db-export", () => {
|
// 打开窗口选择导出文件的路径
|
let path = dialog.showSaveDialogSync({
|
title: "导出数据库",
|
filters: [{ name: "db", extensions: ["db"] }],
|
});
|
if (!path) {
|
return false;
|
}
|
let src = "res.db";
|
child_process.exec(
|
`copy "${process.cwd()}\\${src}" "${path}" /Y /V`,
|
(err) => {
|
if (err) {
|
log.info("数据库导出出错了stderr: " + JSON.stringify(err));
|
return;
|
}
|
log.info("数据库导出成功");
|
// 打开文件夹
|
shell.showItemInFolder(path);
|
}
|
);
|
});
|
|
ipcMain.on("db-import", () => {
|
let stop = child_process.spawn("cmd.exe", ["/c", "stop.bat"]);
|
stop.on("exit", function (code) {
|
if (code > 0) {
|
return false;
|
}
|
// 关闭服务成功后 打开选择文件对话框 让用户选择db文件 然后复制
|
let path = dialog.showOpenDialogSync({
|
filters: [{ name: "db", extensions: ["db"] }],
|
properties: ["openFile"],
|
});
|
if (path) {
|
// 然后复制文件
|
let src = "res.db";
|
// 然后复制文件
|
child_process.exec(
|
`copy "${path}" "${process.cwd()}\\${src}" /Y /V`,
|
(err) => {
|
if (err) {
|
log.info("数据库导入出错了stderr: " + JSON.stringify(err));
|
return;
|
}
|
log.info("数据库导入成功");
|
// 打开服务
|
let restart = child_process.spawn("ResMeterManager.exe", ["restart"]);
|
log.info("restart");
|
restart.stdout.on("data", function (data) {
|
log.info("stdout: " + data);
|
});
|
|
restart.stderr.on("data", function (data) {
|
log.info("stderr: " + data);
|
});
|
|
restart.on("exit", (code) => {
|
if (code > 0) {
|
return false;
|
}
|
log.info("服务重启成功,准备重启应用");
|
// 等到服务就绪再重启
|
checkService(() => {
|
// 重新启动软件
|
app.relaunch();
|
app.exit();
|
});
|
});
|
|
let status = child_process.spawn("ResMeterManager.exe", ["status"]);
|
log.info("restart");
|
status.stdout.on("data", function (data) {
|
log.info("stdout: " + data);
|
});
|
|
status.stderr.on("data", function (data) {
|
log.info("stderr: " + data);
|
});
|
}
|
);
|
} else {
|
// 重启服务 然后重启应用
|
let restart = child_process.spawn("ResMeterManager.exe", ["restart"]);
|
log.info("restart");
|
restart.stdout.on("data", function (data) {
|
log.info("stdout: " + data);
|
});
|
|
restart.stderr.on("data", function (data) {
|
log.info("stderr: " + data);
|
});
|
|
restart.on("exit", (code) => {
|
if (code > 0) {
|
return false;
|
}
|
log.info("服务重启成功,准备重启应用");
|
// 等到服务就绪再重启
|
checkService(() => {
|
// 重新启动软件
|
app.relaunch();
|
app.exit();
|
});
|
});
|
}
|
});
|
});
|
|
// Exit cleanly on request from parent process in development mode.
|
if (isDevelopment) {
|
if (process.platform === "win32") {
|
process.on("message", (data) => {
|
if (data === "graceful-exit") {
|
app.quit();
|
}
|
});
|
} else {
|
process.on("SIGTERM", () => {
|
app.quit();
|
});
|
}
|
}
|