| | |
| | | 'use strict' |
| | | "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 { |
| | | 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 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'; |
| | | autoUpdater.logger.transports.file.level = "info"; |
| | | |
| | | let win = null; |
| | | let loadingWin = null; |
| | | |
| | | |
| | | // 调试自动升级 |
| | | /** |
| | |
| | | // }); |
| | | |
| | | // 单例锁 |
| | | const gotTheLock = app.requestSingleInstanceLock() |
| | | const gotTheLock = app.requestSingleInstanceLock(); |
| | | |
| | | if (!gotTheLock) { |
| | | app.quit() |
| | | app.quit(); |
| | | } else { |
| | | app.on('second-instance', (event, commandLine, workingDirectory) => { |
| | | app.on("second-instance", (event, commandLine, workingDirectory) => { |
| | | // 当运行第二个实例时,将会聚焦到myWindow这个窗口 |
| | | if (win) { |
| | | if (win.isMinimized()) win.restore() |
| | | win.focus() |
| | | if (win.isMinimized()) win.restore(); |
| | | win.focus(); |
| | | if (commandLine[2]) { |
| | | win.webContents.send('selected-file', { filePaths: [commandLine[2]] }, 'MenuList'); |
| | | win.webContents.send( |
| | | "selected-file", |
| | | { filePaths: [commandLine[2]] }, |
| | | "MenuList" |
| | | ); |
| | | } |
| | | } |
| | | }) |
| | | |
| | | }); |
| | | } |
| | | |
| | | |
| | | const remote = require('@electron/remote/main'); |
| | | const remote = require("@electron/remote/main"); |
| | | remote.initialize(); |
| | | // remote.enable() |
| | | |
| | | const isDevelopment = process.env.NODE_ENV !== 'production' |
| | | 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 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) { |
| | | requestPromise.get(appUrl).then( |
| | | function (response) { |
| | | log.info(response); |
| | | log.info('Server started!'); |
| | | log.info("Server started!"); |
| | | cb(); |
| | | }, function (response) { |
| | | }, |
| | | function (response) { |
| | | log.warn(response); |
| | | log.info('Waiting for the server start...'); |
| | | log.info("Waiting for the server start..."); |
| | | setTimeout(function () { |
| | | checkService(cb); |
| | | }, 500) |
| | | }) |
| | | }, 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 } } |
| | | ]) |
| | | { scheme: "app", privileges: { secure: true, standard: true, stream: true } }, |
| | | ]); |
| | | |
| | | // TODO debug; |
| | | // win.webContents.openDevTools() |
| | |
| | | Menu.setApplicationMenu(null); |
| | | } |
| | | |
| | | |
| | | // loading 窗口 |
| | | const loadingURL = isDevelopment ? path.join(__dirname, './loading.html') : `file://${__dirname}/loading.html`; |
| | | const loadingURL = isDevelopment |
| | | ? path.join(__dirname, "./loading.html") |
| | | : `file://${__dirname}/loading.html`; |
| | | const showLoading = (cb, argFn) => { |
| | | loadingWin = new BrowserWindow({ |
| | | // show: false, |
| | |
| | | resizable: false, |
| | | transparent: true, |
| | | webPreferences: { |
| | | preload: path.join(__dirname, './preload.js') |
| | | } |
| | | preload: path.join(__dirname, "./preload.js"), |
| | | }, |
| | | }); |
| | | // loadingWin.once('show', () => { |
| | | // cb(true); |
| | |
| | | // serverProcess = require('child_process').execFile(dir + '/app_x64.exe'); |
| | | // }); |
| | | // } |
| | | requestPromise.get(appUrl).then(function () { |
| | | log.info('窗口初始化 服务正常'); |
| | | requestPromise.get(appUrl).then( |
| | | function () { |
| | | log.info("窗口初始化 服务正常"); |
| | | // ipcRenderer.send('java-ready'); |
| | | loadingWin.webContents.send('java-ready'); |
| | | }, function () { |
| | | log.info('窗口初始化 接口不通'); |
| | | log.info('正在终止java进程,然后重启服务'); |
| | | let stop = child_process.spawn('cmd.exe', ['/c', 'stop.bat']); |
| | | stop.on('exit', function (code) { |
| | | loadingWin.webContents.send("java-ready"); |
| | | }, |
| | | function () { |
| | | log.info("窗口初始化 接口不通"); |
| | | log.info("正在终止java进程,然后重启服务"); |
| | | let stop = child_process.spawn("cmd.exe", ["/c", "stop.bat"]); |
| | | stop.on("exit", function (code) { |
| | | if (code > 0) { |
| | | return false; |
| | | } |
| | | log.info('java进程被终止,准备重启服务'); |
| | | child_process.exec(`"${process.cwd()}\\ResMeterManager.exe" restart`, (err) => { |
| | | log.info("java进程被终止,准备重启服务"); |
| | | child_process.exec( |
| | | `"${process.cwd()}\\ResMeterManager.exe" restart`, |
| | | (err) => { |
| | | if (err) { |
| | | log.info('重启服务出错了stderr: ' + JSON.stringify(err)); |
| | | return |
| | | log.info("重启服务出错了stderr: " + JSON.stringify(err)); |
| | | return; |
| | | } |
| | | log.info('服务重启成功,连接中'); |
| | | log.info("服务重启成功,连接中"); |
| | | // 等到服务就绪再重启 |
| | | checkService(() => { |
| | | loadingWin.webContents.send('java-ready'); |
| | | loadingWin.webContents.send("java-ready"); |
| | | }); |
| | | }); |
| | | } |
| | | ); |
| | | }); |
| | | // // 重启服务 然后重启应用 |
| | | // let restart = child_process.spawn('.\\ResMeterManager.exe', ['restart']); |
| | |
| | | // loadingWin.webContents.send('java-ready'); |
| | | // }); |
| | | // }); |
| | | }); |
| | | } |
| | | ); |
| | | }; |
| | | async function createWindow(wait, cb) { |
| | | // Create the browser window. |
| | | win = new BrowserWindow({ |
| | |
| | | allowRunningInsecureContent: false, |
| | | contextIsolation: true, |
| | | enableRemoteModule: false, |
| | | preload: path.join(__dirname, 'preload.js') |
| | | } |
| | | }) |
| | | 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() |
| | | await win.loadURL(process.env.WEBPACK_DEV_SERVER_URL); |
| | | if (!process.env.IS_TEST) win.webContents.openDevTools(); |
| | | } else { |
| | | createProtocol('app') |
| | | createProtocol("app"); |
| | | // Load the index.html when not in development |
| | | win.loadURL('app://./index.html') |
| | | win.loadURL("app://./index.html"); |
| | | } |
| | | |
| | | if (wait) { |
| | | ipcMain.on("java-ready", () => { |
| | | log.info('java-ready!'); |
| | | log.info("java-ready!"); |
| | | loadingWin.hide(); |
| | | loadingWin.close(); |
| | | win.show(); |
| | | }); |
| | | } |
| | | |
| | | if (cb && 'function' == typeof cb) { |
| | | win.once('ready-to-show', () => { |
| | | if (cb && "function" == typeof cb) { |
| | | win.once("ready-to-show", () => { |
| | | cb(win.webContents); |
| | | }) |
| | | }); |
| | | } |
| | | |
| | | // 英文版不做升级 |
| | | // 自动检测更新 软件的第一个实例打开后 为了不影响加载速度 在指定时间后做一次自检 |
| | | win.once('ready-to-show', () => { |
| | | log.info('ready event'); |
| | | 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) => { |
| | | 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('done', (e, state) => { |
| | | item.on("done", (e, state) => { |
| | | //如果窗口还在的话,去掉进度条 |
| | | // if (!win.isDestroyed()) { |
| | | // win.setProgressBar(-1); |
| | | // } |
| | | //下载被取消或中断了 |
| | | if (state === 'interrupted') { |
| | | dialog.showErrorBox('下载失败', `文件 ${item.getFilename()} 因为某些原因被中断下载`); |
| | | if (state === "interrupted") { |
| | | dialog.showErrorBox( |
| | | "下载失败", |
| | | `文件 ${item.getFilename()} 因为某些原因被中断下载` |
| | | ); |
| | | } |
| | | // 下载成功后打开文件所在文件夹 |
| | | if (state === 'completed') { |
| | | if (state === "completed") { |
| | | setTimeout(() => { |
| | | shell.showItemInFolder(item.getSavePath()) |
| | | shell.showItemInFolder(item.getSavePath()); |
| | | }, 1000); |
| | | } |
| | | }); |
| | |
| | | } |
| | | |
| | | // Quit when all windows are closed. |
| | | app.on('window-all-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() |
| | | if (process.platform !== "darwin") { |
| | | app.quit(); |
| | | } |
| | | }) |
| | | }); |
| | | |
| | | app.on('activate', () => { |
| | | log.info('app activate event'); |
| | | 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() |
| | | }) |
| | | 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'); |
| | | 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'); |
| | | } |
| | | 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) => { |
| | | 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) => { |
| | | 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); |
| | | 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("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) => { |
| | | ipcMain.on("check-update", (event) => { |
| | | // checkForUpdates(); |
| | | update(event.sender); |
| | | }); |
| | | |
| | | ipcMain.on('download-update', () => { |
| | | ipcMain.on("download-update", () => { |
| | | autoUpdater.downloadUpdate(); |
| | | }); |
| | | |
| | | ipcMain.on('quitAndInstall', () => { |
| | | ipcMain.on("quitAndInstall", () => { |
| | | autoUpdater.quitAndInstall(); |
| | | }); |
| | | |
| | | ipcMain.on('db-export', () => { |
| | | ipcMain.on("db-export", () => { |
| | | // 打开窗口选择导出文件的路径 |
| | | let path = dialog.showSaveDialogSync({ |
| | | title: '导出数据库', |
| | | filters: [{ name: 'db', extensions: ['db'] }], |
| | | 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) => { |
| | | 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("数据库导出出错了stderr: " + JSON.stringify(err)); |
| | | return; |
| | | } |
| | | log.info('数据库导出成功'); |
| | | log.info("数据库导出成功"); |
| | | // 打开文件夹 |
| | | shell.showItemInFolder(path); |
| | | }); |
| | | } |
| | | ); |
| | | }); |
| | | |
| | | ipcMain.on('db-import', () => { |
| | | let stop = child_process.spawn('cmd.exe', ['/c', 'stop.bat']); |
| | | stop.on('exit', function (code) { |
| | | 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'] |
| | | filters: [{ name: "db", extensions: ["db"] }], |
| | | properties: ["openFile"], |
| | | }); |
| | | if (path) { |
| | | // 然后复制文件 |
| | | let src = 'res.db'; |
| | | let src = "res.db"; |
| | | // 然后复制文件 |
| | | child_process.exec(`copy "${path}" "${process.cwd()}\\${src}" /Y /V`, (err) => { |
| | | child_process.exec( |
| | | `copy "${path}" "${process.cwd()}\\${src}" /Y /V`, |
| | | (err) => { |
| | | if (err) { |
| | | log.info('数据库导入出错了stderr: ' + JSON.stringify(err)); |
| | | return |
| | | log.info("数据库导入出错了stderr: " + JSON.stringify(err)); |
| | | return; |
| | | } |
| | | log.info('数据库导入成功'); |
| | | log.info("数据库导入成功"); |
| | | // 打开服务 |
| | | let restart = child_process.spawn('ResMeterManager.exe', ['restart']); |
| | | log.info('restart'); |
| | | restart.stdout.on('data', function (data) { |
| | | log.info('stdout: ' + data); |
| | | 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.stderr.on("data", function (data) { |
| | | log.info("stderr: " + data); |
| | | }); |
| | | |
| | | restart.on('exit', (code) => { |
| | | restart.on("exit", (code) => { |
| | | if (code > 0) { |
| | | return false; |
| | | } |
| | | log.info('服务重启成功,准备重启应用'); |
| | | log.info("服务重启成功,准备重启应用"); |
| | | // 等到服务就绪再重启 |
| | | checkService(() => { |
| | | // 重新启动软件 |
| | |
| | | }); |
| | | }); |
| | | |
| | | let status = child_process.spawn('ResMeterManager.exe', ['status']); |
| | | log.info('restart'); |
| | | status.stdout.on('data', function (data) { |
| | | log.info('stdout: ' + data); |
| | | 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); |
| | | 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); |
| | | 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.stderr.on("data", function (data) { |
| | | log.info("stderr: " + data); |
| | | }); |
| | | |
| | | restart.on('exit', (code) => { |
| | | restart.on("exit", (code) => { |
| | | if (code > 0) { |
| | | return false; |
| | | } |
| | | log.info('服务重启成功,准备重启应用'); |
| | | log.info("服务重启成功,准备重启应用"); |
| | | // 等到服务就绪再重启 |
| | | checkService(() => { |
| | | // 重新启动软件 |
| | |
| | | |
| | | // 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() |
| | | if (process.platform === "win32") { |
| | | process.on("message", (data) => { |
| | | if (data === "graceful-exit") { |
| | | app.quit(); |
| | | } |
| | | }) |
| | | }); |
| | | } else { |
| | | process.on('SIGTERM', () => { |
| | | app.quit() |
| | | }) |
| | | process.on("SIGTERM", () => { |
| | | app.quit(); |
| | | }); |
| | | } |
| | | } |