diff --git a/index.html b/index.html
index 9781257..3d21f41 100644
--- a/index.html
+++ b/index.html
@@ -43,7 +43,8 @@
diff --git a/src/IpcMainHandler.ts b/src/IpcMainHandler.ts
index 2ab22b3..5cc9d29 100644
--- a/src/IpcMainHandler.ts
+++ b/src/IpcMainHandler.ts
@@ -1,12 +1,74 @@
-import { ipcMain, screen, session } from "electron";
+import { BrowserWindow, ipcMain, screen, session } from "electron";
import http from 'http';
import https from 'https';
+import os from 'os';
import { URL } from 'url';
-import { ApiResponse, MenuItem, TagResolutionConfig, EIACDesktopApi, SpecialPUrlItem } from './EIAC_Desktop_Api';
+import { ApiResponse, MenuItem, TagResolutionConfig, EIACDesktopApi, SpecialPUrlItem, FaultReportingResponse } from './EIAC_Desktop_Api';
+
+const memoryCache = new Map();
export function initialize(): void {
- // Get primary display(需要注意:size 是逻辑像素尺寸(logical screen size),已被 DPI 缩放影响,需要除以 DPI 缩放比例才是物理像素尺寸(physical screen size))
- ipcMain.handle('get-primary-display', () => screen.getPrimaryDisplay());
+ // Set cache
+ ipcMain.handle('cache:set', (_event, key: string, value: any) => {
+ memoryCache.set(key, value);
+ });
+
+ // Get cache
+ ipcMain.handle('cache:get', (_event, key: string) => {
+ return memoryCache.get(key) ?? null;
+ });
+
+ // Get menu cache
+ ipcMain.handle('get-menu-cache', async () => menuData ?? await menuDataReadyPromise);
+
+ // Get config cache
+ ipcMain.handle('get-config-cache', async () => configData ?? await configDataReadyPromise);
+
+ // Get zoom factor
+ ipcMain.handle('get-zoom-factor-by-url', async (event, url: string) => {
+ const display: Electron.Display = screen.getPrimaryDisplay();
+ const physicalSize: Electron.Size = {
+ width: display.size.width * display.scaleFactor,
+ height: display.size.height * display.scaleFactor
+ };
+ const resolution: string = `${physicalSize.width}*${physicalSize.height}`;
+ console.log('PhysicalResolution:', resolution);
+ console.log(`Resolution: ${display.size.width}*${display.size.height}`);
+ console.log(`ScaleFactor: ${display.scaleFactor}`);
+
+ if (!configData) {
+ await configDataReadyPromise;
+ }
+
+ if (configData.code != 200 || configData.status != 0) {
+ console.error('Get config failed:', configData.msg + ', status: ' + configData.status + ', code: ' + configData.code);
+ return display.scaleFactor;
+ }
+
+ const configList: TagResolutionConfig[] = configData.data;
+ let config: TagResolutionConfig = configList.find(c => c.Resolutions.includes(resolution));
+ if (!config) {
+ config = configList.find(c => c.Resolutions === '*');
+ }
+ if (!config) {
+ config = configList[0];
+ }
+ console.log('Match Config:', config);
+
+ let specialPUrl: SpecialPUrlItem = config.SpecialPUrl.find(s => s.SPUrl.toLowerCase() === url.toLowerCase());
+ if (!specialPUrl) {
+ specialPUrl = config.SpecialPUrl.find(s => url.toLowerCase().startsWith(s.SPUrl.toLowerCase()));
+ }
+ console.log('specialPUrl:', specialPUrl);
+
+ let percentage: number = typeof config.Percentage === 'string' ? parseInt(config.Percentage) : config.Percentage;
+ if (specialPUrl) {
+ percentage = typeof specialPUrl.SPPer === 'string' ? parseInt(specialPUrl.SPPer) : specialPUrl.SPPer;
+ }
+
+ console.log('Percentage:', percentage);
+ return percentage;
+ });
// Check if the URL is available
ipcMain.handle('check-url-available', async (event, rawUrl: string) => {
@@ -99,59 +161,64 @@ export function initialize(): void {
}
});
- // Get menu cache
- ipcMain.handle('get-menu-cache', async () => menuData ?? await menuDataReadyPromise);
+ // Fault reporting
+ ipcMain.handle('fault-reporting', async (event, url: string, message: string, status: number) => {
+ console.log('Fault reporting:', url, message, status);
+ const webContents = event.sender;
- // Get config cache
- ipcMain.handle('get-config-cache', async () => configData ?? await configDataReadyPromise);
-
- // Get zoom factor
- ipcMain.handle('get-zoom-factor-by-url', async (event, url: string) => {
- const display: Electron.Display = screen.getPrimaryDisplay();
- const physicalSize: Electron.Size = {
- width: display.size.width * display.scaleFactor,
- height: display.size.height * display.scaleFactor
- };
- const resolution: string = `${physicalSize.width}*${physicalSize.height}`;
- console.log('PhysicalResolution:', resolution);
- console.log(`Resolution: ${display.size.width}*${display.size.height}`);
- console.log(`ScaleFactor: ${display.scaleFactor}`);
-
- if (!configData) {
- await configDataReadyPromise;
+ const win = BrowserWindow.fromWebContents(webContents);
+ if (!win) {
+ throw new Error('Not found BrowserWindow');
}
- if (configData.code != 200 || configData.status != 0) {
- console.error('Get config failed:', configData.msg + ', status: ' + configData.status + ', code: ' + configData.code);
- return display.scaleFactor;
- }
+ const base64 = await captureWindowAsBase64(win);
+ console.log('base64:', base64);
- const configList: TagResolutionConfig[] = configData.data;
- let config: TagResolutionConfig = configList.find(c => c.Resolutions.includes(resolution));
- if (!config) {
- config = configList.find(c => c.Resolutions === '*');
- }
- if (!config) {
- config = configList[0];
- }
- console.log('Match Config:', config);
+ try {
+ const response: ApiResponse = await EIACDesktopApi.Help.FaultReportingAsync({
+ Account: memoryCache.get('Account'),
+ IP: getLocalIPAddress(),
+ Url: url,
+ ImgBase64: base64,
+ Explain: `message: ${message}, status: ${status}`
+ });
+ console.log('Fault reporting response:', response);
- let specialPUrl: SpecialPUrlItem = config.SpecialPUrl.find(s => s.SPUrl.toLowerCase() === url.toLowerCase());
- if (!specialPUrl) {
- specialPUrl = config.SpecialPUrl.find(s => url.toLowerCase().startsWith(s.SPUrl.toLowerCase()));
- }
- console.log('specialPUrl:', specialPUrl);
+ if (response.code != 200 || response.status != 0) {
+ console.error('故障上报失败:', response.msg + ', status: ' + response.status + ', code: ' + response.code);
+ return { ok: false, status: -1, message: `故障上报失败: ${response.msg}, status: ${response.status}, code: ${response.code}` };
+ }
- let percentage: number = typeof config.Percentage === 'string' ? parseInt(config.Percentage) : config.Percentage;
- if (specialPUrl) {
- percentage = typeof specialPUrl.SPPer === 'string' ? parseInt(specialPUrl.SPPer) : specialPUrl.SPPer;
+ return { ok: true, status: response.status, message: response.msg };
+ } catch (error) {
+ console.error('故障上报失败:', error);
+ return { ok: false, status: -1, message: error.message };
}
-
- console.log('Percentage:', percentage);
- return percentage;
});
}
+function getLocalIPAddress(): string | null {
+ const interfaces = os.networkInterfaces();
+
+ for (const name of Object.keys(interfaces)) {
+ for (const net of interfaces[name] || []) {
+ // 排除 IPv6 和 127.0.0.1 内环地址
+ if (net.family === 'IPv4' && !net.internal) {
+ return net.address; // 返回第一个非内网 IPv4 地址
+ }
+ }
+ }
+
+ return null; // 没有找到
+}
+
+async function captureWindowAsBase64(win: BrowserWindow): Promise {
+ const image = await win.capturePage(); // 截图
+ const pngBuffer = image.toPNG(); // 转为 PNG Buffer
+ const base64 = pngBuffer.toString('base64'); // 转为 Base64 字符串
+ return `data:image/png;base64,${base64}`; // 返回 DataURL
+}
+
let menuData: ApiResponse