diff --git a/index.js b/index.js index 3f93b39..5a16c7a 100644 --- a/index.js +++ b/index.js @@ -6,16 +6,13 @@ const tls = require("tls"); const httpProxy = require("http-proxy"); const { WebSocketServer } = require('ws') const path = require("path"); +const {default: forms} = require("forms") +const z = require("zod") // --------------------------- // Request Log Store // --------------------------- -let requests = []; - -// Mutex not required in Node (single-threaded) -function recordRequest(info) { - requests.push(info); -} +let store; // --------------------------- // IP Helpers @@ -25,10 +22,27 @@ function isLocalIP(ip) { return false; } -function cleanIP(remoteAddr) { - if (!remoteAddr) return ""; - let ip = remoteAddr.split(":")[0].replace("[", "").replace("]", ""); - if (ip.startsWith("::ffff:")) ip = ip.replace("::ffff:", ""); +function getIP(req) { + const headers = req.headers; + + let ip = + headers["cf-connecting-ip"] || + headers["x-real-ip"] || + headers["x-forwarded-for"]?.split(",")[0]?.trim() || + req.socket?.remoteAddress || + req.connection?.remoteAddress || + ""; + + // Normalize IPv6-mapped IPv4 + if (ip.startsWith("::ffff:")) { + ip = ip.slice(7); + } + + // Normalize localhost IPv6 + if (ip === "::1") { + ip = "127.0.0.1"; + } + return ip; } @@ -37,8 +51,7 @@ function cleanIP(remoteAddr) { // --------------------------- function loggingMiddleware(next) { return (req, res) => { - const rawIP = req.socket.remoteAddress; - const ip = cleanIP(rawIP); + const ip = getIP(req); let path = req.url.startsWith("/") ? req.url.slice(1) : req.url; if (path === "") path = "/"; @@ -57,13 +70,13 @@ function loggingMiddleware(next) { ); } - recordRequest({ - Timestamp: new Date().toISOString(), - Host: req.headers.host || "", - IP: ip, - Path: path, - Method: req.method - }); + store.add("log", { + time: new Date().toISOString(), + host: req.headers.host || "", + ip: ip, + path: path, + method: req.method + }) next(req, res); }; @@ -191,6 +204,21 @@ function startServer() { socket.destroy(); }); }); + + + async function connectToForms() { + await store.connect() + store.register("log", z.toJSONSchema(z.object({ + time: z.string(), + host: z.string(), + ip: z.string(), + path: z.string(), + method: z.string() + }))) + } + + store = new forms.client() + connectToForms() server.listen(3000, () => { console.log("🔒 HTTPS server running on port 3000"); diff --git a/package.json b/package.json index aae2e94..6509b91 100644 --- a/package.json +++ b/package.json @@ -4,6 +4,7 @@ }, "dependencies": { "http-proxy": "^1.18.1", - "ws": "^8.18.3" + "ws": "^8.18.3", + "zod": "^4.2.1" } }