All checks were successful
Build and Push LST Docker Image / docker (push) Successful in 1m30s
181 lines
4.2 KiB
TypeScript
181 lines
4.2 KiB
TypeScript
import net from "node:net";
|
|
import { eq } from "drizzle-orm";
|
|
import { db } from "../db/db.controller.js";
|
|
import { printerData } from "../db/schema/printers.schema.js";
|
|
import { createLogger } from "../logger/logger.controller.js";
|
|
import { delay } from "../utils/delay.utils.js";
|
|
import { returnFunc } from "../utils/returnHelper.utils.js";
|
|
import { tryCatch } from "../utils/trycatch.utils.js";
|
|
import { type PrinterData, printerListen } from "./tcp.printerListener.js";
|
|
|
|
let tcpServer: net.Server;
|
|
const tcpSockets: Set<net.Socket> = new Set();
|
|
export let isServerRunning = false;
|
|
|
|
const port = parseInt(process.env.TCP_PORT ?? "2222", 10);
|
|
|
|
const parseTcpAlert = (input: string) => {
|
|
// guard
|
|
const colonIndex = input.indexOf(":");
|
|
if (colonIndex === -1) return null;
|
|
|
|
const condition = input.slice(0, colonIndex).trim();
|
|
const rest = input.slice(colonIndex + 1).trim();
|
|
|
|
// extract all [ ... ] blocks from rest
|
|
const matches = [...rest.matchAll(/\[(.*?)\]/g)];
|
|
|
|
const date = matches[0]?.[1] ?? "";
|
|
const name = matches[1]?.[1] ?? "";
|
|
|
|
// message = everything before first "["
|
|
const bracketIndex = rest.indexOf("[");
|
|
const message =
|
|
bracketIndex !== -1 ? rest.slice(0, bracketIndex).trim() : rest;
|
|
|
|
return {
|
|
condition,
|
|
message,
|
|
date,
|
|
name,
|
|
};
|
|
};
|
|
const log = createLogger({ module: "tcp", submodule: "create_server" });
|
|
export const startTCPServer = async () => {
|
|
tcpServer = net.createServer(async (socket) => {
|
|
tcpSockets.add(socket);
|
|
socket.on("data", async (data: Buffer) => {
|
|
const parseData = data.toString("utf-8").trimEnd();
|
|
|
|
// check where the data came from then we do something.
|
|
|
|
const ip = socket.remoteAddress ?? "127.0.0.1";
|
|
const { data: printer, error: pError } = await tryCatch(
|
|
db
|
|
.select()
|
|
.from(printerData)
|
|
.where(eq(printerData.ipAddress, ip.replace("::ffff:", ""))),
|
|
);
|
|
if (pError) {
|
|
log.error(
|
|
{ stack: pError },
|
|
"There was an error getting printer data for tcp check",
|
|
);
|
|
return;
|
|
}
|
|
|
|
if (printer?.length) {
|
|
const printerData = {
|
|
...parseTcpAlert(parseData),
|
|
ip,
|
|
printerSN: printer[0]?.printerSN,
|
|
name: printer[0]?.name,
|
|
};
|
|
|
|
printerListen(printerData as PrinterData);
|
|
}
|
|
});
|
|
|
|
socket.on("end", () => {
|
|
log.debug({}, "Client disconnected");
|
|
// just in case we dont fully disconnect
|
|
setTimeout(() => {
|
|
if (!socket.destroyed) {
|
|
socket.destroy();
|
|
}
|
|
}, 1000);
|
|
tcpSockets.delete(socket);
|
|
});
|
|
|
|
socket.on("error", (err: Error) => {
|
|
log.error({ stack: err }, `Socket error:", ${err}`);
|
|
// just in case we dont fully disconnect
|
|
setTimeout(() => {
|
|
if (!socket.destroyed) {
|
|
socket.destroy();
|
|
}
|
|
}, 1000);
|
|
tcpSockets.delete(socket);
|
|
});
|
|
});
|
|
|
|
tcpServer.listen(port, () => {
|
|
log.info({}, `TCP Server listening on port ${port}`);
|
|
});
|
|
|
|
isServerRunning = true;
|
|
return returnFunc({
|
|
success: true,
|
|
level: "info",
|
|
module: "tcp",
|
|
subModule: "create_server",
|
|
message: "TCP server started.",
|
|
data: [],
|
|
notify: false,
|
|
room: "",
|
|
});
|
|
};
|
|
|
|
export const stopTCPServer = async () => {
|
|
if (!isServerRunning)
|
|
return { success: false, message: "Server is not running" };
|
|
for (const socket of tcpSockets) {
|
|
socket.destroy();
|
|
}
|
|
tcpSockets.clear();
|
|
tcpServer.close(() => {
|
|
log.info({}, "TCP Server stopped");
|
|
});
|
|
isServerRunning = false;
|
|
return returnFunc({
|
|
success: true,
|
|
level: "info",
|
|
module: "tcp",
|
|
subModule: "create_server",
|
|
message: "TCP server stopped.",
|
|
data: [],
|
|
notify: false,
|
|
room: "",
|
|
});
|
|
};
|
|
|
|
export const restartTCPServer = async () => {
|
|
if (!isServerRunning) {
|
|
startTCPServer();
|
|
return returnFunc({
|
|
success: false,
|
|
level: "warn",
|
|
module: "tcp",
|
|
subModule: "create_server",
|
|
message: "Server is not running will try to start it",
|
|
data: [],
|
|
notify: false,
|
|
room: "",
|
|
});
|
|
} else {
|
|
for (const socket of tcpSockets) {
|
|
socket.destroy();
|
|
}
|
|
tcpSockets.clear();
|
|
tcpServer.close(() => {
|
|
log.info({}, "TCP Server stopped");
|
|
});
|
|
isServerRunning = false;
|
|
|
|
await delay(1500);
|
|
|
|
startTCPServer();
|
|
}
|
|
|
|
return returnFunc({
|
|
success: true,
|
|
level: "info",
|
|
module: "tcp",
|
|
subModule: "create_server",
|
|
message: "TCP server has been restarted.",
|
|
data: [],
|
|
notify: false,
|
|
room: "",
|
|
});
|
|
};
|