From aec2d7363dcaeceb94ef2a78ae2a5cf3153134ff Mon Sep 17 00:00:00 2001 From: Joerg Date: Thu, 23 Oct 2025 09:21:17 +0200 Subject: [PATCH 1/3] Implemented WebSocket for getting last QRG/Mode --- main.js | 87 ++++++++++++++++++++++++++++++++++++++++++++++++++++ package.json | 1 + renderer.js | 5 +++ 3 files changed, 93 insertions(+) diff --git a/main.js b/main.js index 37bfaad..bddc278 100644 --- a/main.js +++ b/main.js @@ -4,6 +4,7 @@ const {ipcMain} = require('electron') const http = require('http'); const xml = require("xml2js"); const net = require('net'); +const WebSocket = require('ws'); const gotTheLock = app.requestSingleInstanceLock(); @@ -12,6 +13,8 @@ let s_mainWindow; let msgbacklog=[]; let httpServer; var WServer; +let wsServer; +let wsClients = new Set(); const DemoAdif='DJ7NT JO30 FT8 -15 33 20240110 051855 20240110 051855 40m 7.155783 TE1ST JO30OO '; @@ -143,6 +146,12 @@ ipcMain.on("quit", async (event,arg) => { event.returnValue=true; }); +ipcMain.on("radio_status_update", async (event,arg) => { + // Broadcast radio status updates from renderer to WebSocket clients + broadcastRadioStatus(arg); + event.returnValue=true; +}); + function show_noti(arg) { if (Notification.isSupported()) { try { @@ -477,11 +486,86 @@ function startserver() { settrx(qrg,mode); } }).listen(54321); + + // Start WebSocket server + startWebSocketServer(); } catch(e) { tomsg('Some other Tool blocks Port 2333 or 54321. Stop it, and restart this'); } } +function startWebSocketServer() { + try { + wsServer = new WebSocket.Server({ port: 54322 }); + tomsg('WebSocket server started on port 54322'); + + wsServer.on('connection', (ws) => { + wsClients.add(ws); + tomsg('WebSocket client connected'); + + ws.on('close', () => { + wsClients.delete(ws); + tomsg('WebSocket client disconnected'); + }); + + ws.on('error', (error) => { + console.error('WebSocket error:', error); + wsClients.delete(ws); + }); + + // Send current radio status on connection + ws.send(JSON.stringify({ + type: 'welcome', + message: 'Connected to WaveLogGate WebSocket server' + })); + }); + + wsServer.on('error', (error) => { + console.error('WebSocket server error:', error); + }); + + } catch(e) { + tomsg('Failed to start WebSocket server on port 54322: ' + e.message); + } +} + +function broadcastFrequencyMode(frequency, mode, source = 'unknown') { + const message = { + type: 'frequency_mode_change', + frequency: parseInt(frequency), + mode: mode, + source: source, + timestamp: Date.now() + }; + + const messageStr = JSON.stringify(message); + wsClients.forEach((client) => { + if (client.readyState === WebSocket.OPEN) { + client.send(messageStr); + } + }); +} + +function broadcastRadioStatus(radioData) { + const message = { + type: 'radio_status', + frequency: radioData.vfo ? parseInt(radioData.vfo) : null, + mode: radioData.mode || null, + power: radioData.power || null, + split: radioData.split || false, + vfoB: radioData.vfoB ? parseInt(radioData.vfoB) : null, + modeB: radioData.modeB || null, + timestamp: Date.now() + }; + + const messageStr = JSON.stringify(message); + wsClients.forEach((client) => { + if (client.readyState === WebSocket.OPEN) { + client.send(messageStr); + } + }); +} + async function get_modes() { return new Promise((resolve) => { @@ -574,6 +658,9 @@ async function settrx(qrg, mode = '') { client.on("close", () => {}); } + // Broadcast frequency/mode change to WebSocket clients + broadcastFrequencyMode(to.qrg, to.mode, 'wavelog'); + return true; } diff --git a/package.json b/package.json index 6a404fc..700d9e5 100644 --- a/package.json +++ b/package.json @@ -23,6 +23,7 @@ "jquery": "^3.7.1", "popper.js": "^1.16.1", "tcadif": "^2.3.0", + "ws": "^8.18.3", "xml2js": "^0.6.2" }, "devDependencies": { diff --git a/renderer.js b/renderer.js index 76c8ca1..e9599f4 100644 --- a/renderer.js +++ b/renderer.js @@ -182,7 +182,12 @@ async function get_trx() { $("#current_trx").html((currentCat.vfo/(1000*1000))+" MHz / "+currentCat.mode); if (((Date.now()-lastCat) > (30*60*1000)) || (!(isDeepEqual(oldCat,currentCat)))) { console.log(await informWavelog(currentCat)); + const { ipcRenderer } = require('electron'); + ipcRenderer.send('radio_status_update', currentCat); } + + // Send radio status to main process for WebSocket broadcasting + oldCat=currentCat; return currentCat; } From 9286bf08a0e4e64ea338671481d66d3189b07448 Mon Sep 17 00:00:00 2001 From: Joerg Date: Thu, 23 Oct 2025 10:32:49 +0200 Subject: [PATCH 2/3] Refine websocket --- main.js | 31 ++++++++----------------------- renderer.js | 8 ++++---- 2 files changed, 12 insertions(+), 27 deletions(-) diff --git a/main.js b/main.js index bddc278..9d41fb0 100644 --- a/main.js +++ b/main.js @@ -529,35 +529,21 @@ function startWebSocketServer() { } } -function broadcastFrequencyMode(frequency, mode, source = 'unknown') { - const message = { - type: 'frequency_mode_change', - frequency: parseInt(frequency), - mode: mode, - source: source, - timestamp: Date.now() - }; - - const messageStr = JSON.stringify(message); - wsClients.forEach((client) => { - if (client.readyState === WebSocket.OPEN) { - client.send(messageStr); - } - }); -} - function broadcastRadioStatus(radioData) { - const message = { + let message = { type: 'radio_status', - frequency: radioData.vfo ? parseInt(radioData.vfo) : null, + frequency: radioData.frequency ? parseInt(radioData.frequency) : null, mode: radioData.mode || null, power: radioData.power || null, - split: radioData.split || false, - vfoB: radioData.vfoB ? parseInt(radioData.vfoB) : null, - modeB: radioData.modeB || null, + radio: radioData.radio || 'wlstream', timestamp: Date.now() }; + // Only include frequency_rx if it's not null + if (radioData.frequency_rx) { + message.frequency_rx = parseInt(radioData.frequency_rx); + } + const messageStr = JSON.stringify(message); wsClients.forEach((client) => { if (client.readyState === WebSocket.OPEN) { @@ -659,7 +645,6 @@ async function settrx(qrg, mode = '') { } // Broadcast frequency/mode change to WebSocket clients - broadcastFrequencyMode(to.qrg, to.mode, 'wavelog'); return true; } diff --git a/renderer.js b/renderer.js index e9599f4..2d9533b 100644 --- a/renderer.js +++ b/renderer.js @@ -182,12 +182,8 @@ async function get_trx() { $("#current_trx").html((currentCat.vfo/(1000*1000))+" MHz / "+currentCat.mode); if (((Date.now()-lastCat) > (30*60*1000)) || (!(isDeepEqual(oldCat,currentCat)))) { console.log(await informWavelog(currentCat)); - const { ipcRenderer } = require('electron'); - ipcRenderer.send('radio_status_update', currentCat); } - // Send radio status to main process for WebSocket broadcasting - oldCat=currentCat; return currentCat; } @@ -314,6 +310,10 @@ async function informWavelog(CAT) { data.mode=CAT.mode; } + const { ipcRenderer } = require('electron'); + console.log(data); + ipcRenderer.send('radio_status_update', data); + let x=await fetch(cfg.profiles[active_cfg].wavelog_url + '/api/radio', { method: 'POST', rejectUnauthorized: false, From cf48cadd4b7b25b553e2be9b66c713d87e4b3a4b Mon Sep 17 00:00:00 2001 From: Joerg Date: Thu, 23 Oct 2025 17:57:43 +0200 Subject: [PATCH 3/3] Send last known Radio-CAT-Status on Connect to socket --- main.js | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/main.js b/main.js index 9d41fb0..bccbe67 100644 --- a/main.js +++ b/main.js @@ -12,6 +12,7 @@ let powerSaveBlockerId; let s_mainWindow; let msgbacklog=[]; let httpServer; +let currentCAT=null; var WServer; let wsServer; let wsClients = new Set(); @@ -518,6 +519,7 @@ function startWebSocketServer() { type: 'welcome', message: 'Connected to WaveLogGate WebSocket server' })); + broadcastRadioStatus(currentCAT); }); wsServer.on('error', (error) => { @@ -530,6 +532,7 @@ function startWebSocketServer() { } function broadcastRadioStatus(radioData) { + currentCAT=radioData; let message = { type: 'radio_status', frequency: radioData.frequency ? parseInt(radioData.frequency) : null, @@ -538,7 +541,6 @@ function broadcastRadioStatus(radioData) { radio: radioData.radio || 'wlstream', timestamp: Date.now() }; - // Only include frequency_rx if it's not null if (radioData.frequency_rx) { message.frequency_rx = parseInt(radioData.frequency_rx);