From fdac5786787f3fc1d62b291591a016a2fe50aeec Mon Sep 17 00:00:00 2001
From: Dorian Niemiec
Date: Sat, 2 Sep 2023 19:12:46 +0200
Subject: [PATCH] Dropped support for HTTP to HTTPS redirect bypass headers
---
svr.js | 846 ++++++++++++++++++++++++++++-----------------------------
1 file changed, 421 insertions(+), 425 deletions(-)
diff --git a/svr.js b/svr.js
index 4f2102d..b000b72 100644
--- a/svr.js
+++ b/svr.js
@@ -2108,221 +2108,198 @@ if (!cluster.isPrimary) {
if (server2.requestTimeout !== undefined && server2.requestTimeout === 0) server2.requestTimeout = 300000;
function redirhandler(req, res) {
- if (req.headers["force-insecure"] == "true" || req.headers["x-force-insecure"] == "true" || req.headers["x-svr-js-force-insecure"] == "true") {
- reqhandler(req, res, false);
- } else {
- var reqIdInt = Math.round(Math.random() * 16777216);
- var reqId = "0".repeat(6 - reqIdInt.toString(16).length) + reqIdInt.toString(16);
- var serverconsole = {
- climessage: function (msg) {
- if (msg.indexOf("\n") != -1) {
- msg.split("\n").forEach(function (nmsg) {
- serverconsole.climessage(nmsg);
- });
- return;
- }
- console.log("SERVER CLI MESSAGE [Request Id: " + reqId + "]: " + msg);
- LOG("SERVER CLI MESSAGE [Request Id: " + reqId + "]: " + msg);
- return;
- },
- reqmessage: function (msg) {
- if (msg.indexOf("\n") != -1) {
- msg.split("\n").forEach(function (nmsg) {
- serverconsole.reqmessage(nmsg);
- });
- return;
- }
- console.log("\x1b[34mSERVER REQUEST MESSAGE [Request Id: " + reqId + "]: " + msg + "\x1b[37m\x1b[0m");
- LOG("SERVER REQUEST MESSAGE [Request Id: " + reqId + "]: " + msg);
- return;
- },
- resmessage: function (msg) {
- if (msg.indexOf("\n") != -1) {
- msg.split("\n").forEach(function (nmsg) {
- serverconsole.resmessage(nmsg);
- });
- return;
- }
- console.log("\x1b[32mSERVER RESPONSE MESSAGE [Request Id: " + reqId + "]: " + msg + "\x1b[37m\x1b[0m");
- LOG("SERVER RESPONSE MESSAGE [Request Id: " + reqId + "]: " + msg);
- return;
- },
- errmessage: function (msg) {
- if (msg.indexOf("\n") != -1) {
- msg.split("\n").forEach(function (nmsg) {
- serverconsole.errmessage(nmsg);
- });
- return;
- }
- console.log("\x1b[31mSERVER RESPONSE ERROR MESSAGE [Request Id: " + reqId + "]: " + msg + "\x1b[37m\x1b[0m");
- LOG("SERVER RESPONSE ERROR MESSAGE [Request Id: " + reqId + "]: " + msg);
- return;
- },
- locerrmessage: function (msg) {
- if (msg.indexOf("\n") != -1) {
- msg.split("\n").forEach(function (nmsg) {
- serverconsole.locerrmessage(nmsg);
- });
- return;
- }
- console.log("\x1b[41mSERVER ERROR MESSAGE [Request Id: " + reqId + "]: " + msg + "\x1b[40m\x1b[0m");
- LOG("SERVER ERROR MESSAGE [Request Id: " + reqId + "]: " + msg);
- return;
- },
- locwarnmessage: function (msg) {
- if (msg.indexOf("\n") != -1) {
- msg.split("\n").forEach(function (nmsg) {
- serverconsole.locwarnmessage(nmsg);
- });
- return;
- }
- console.log("\x1b[43mSERVER WARNING MESSAGE [Request Id: " + reqId + "]: " + msg + "\x1b[40m\x1b[0m");
- LOG("SERVER WARNING MESSAGE [Request Id: " + reqId + "]: " + msg);
- return;
- },
- locmessage: function (msg) {
- if (msg.indexOf("\n") != -1) {
- msg.split("\n").forEach(function (nmsg) {
- serverconsole.locmessage(nmsg);
- });
- return;
- }
- console.log("SERVER MESSAGE [Request Id: " + reqId + "]: " + msg);
- LOG("SERVER MESSAGE [Request Id: " + reqId + "]: " + msg);
+ var reqIdInt = Math.round(Math.random() * 16777216);
+ var reqId = "0".repeat(6 - reqIdInt.toString(16).length) + reqIdInt.toString(16);
+ var serverconsole = {
+ climessage: function (msg) {
+ if (msg.indexOf("\n") != -1) {
+ msg.split("\n").forEach(function (nmsg) {
+ serverconsole.climessage(nmsg);
+ });
return;
}
- };
+ console.log("SERVER CLI MESSAGE [Request Id: " + reqId + "]: " + msg);
+ LOG("SERVER CLI MESSAGE [Request Id: " + reqId + "]: " + msg);
+ return;
+ },
+ reqmessage: function (msg) {
+ if (msg.indexOf("\n") != -1) {
+ msg.split("\n").forEach(function (nmsg) {
+ serverconsole.reqmessage(nmsg);
+ });
+ return;
+ }
+ console.log("\x1b[34mSERVER REQUEST MESSAGE [Request Id: " + reqId + "]: " + msg + "\x1b[37m\x1b[0m");
+ LOG("SERVER REQUEST MESSAGE [Request Id: " + reqId + "]: " + msg);
+ return;
+ },
+ resmessage: function (msg) {
+ if (msg.indexOf("\n") != -1) {
+ msg.split("\n").forEach(function (nmsg) {
+ serverconsole.resmessage(nmsg);
+ });
+ return;
+ }
+ console.log("\x1b[32mSERVER RESPONSE MESSAGE [Request Id: " + reqId + "]: " + msg + "\x1b[37m\x1b[0m");
+ LOG("SERVER RESPONSE MESSAGE [Request Id: " + reqId + "]: " + msg);
+ return;
+ },
+ errmessage: function (msg) {
+ if (msg.indexOf("\n") != -1) {
+ msg.split("\n").forEach(function (nmsg) {
+ serverconsole.errmessage(nmsg);
+ });
+ return;
+ }
+ console.log("\x1b[31mSERVER RESPONSE ERROR MESSAGE [Request Id: " + reqId + "]: " + msg + "\x1b[37m\x1b[0m");
+ LOG("SERVER RESPONSE ERROR MESSAGE [Request Id: " + reqId + "]: " + msg);
+ return;
+ },
+ locerrmessage: function (msg) {
+ if (msg.indexOf("\n") != -1) {
+ msg.split("\n").forEach(function (nmsg) {
+ serverconsole.locerrmessage(nmsg);
+ });
+ return;
+ }
+ console.log("\x1b[41mSERVER ERROR MESSAGE [Request Id: " + reqId + "]: " + msg + "\x1b[40m\x1b[0m");
+ LOG("SERVER ERROR MESSAGE [Request Id: " + reqId + "]: " + msg);
+ return;
+ },
+ locwarnmessage: function (msg) {
+ if (msg.indexOf("\n") != -1) {
+ msg.split("\n").forEach(function (nmsg) {
+ serverconsole.locwarnmessage(nmsg);
+ });
+ return;
+ }
+ console.log("\x1b[43mSERVER WARNING MESSAGE [Request Id: " + reqId + "]: " + msg + "\x1b[40m\x1b[0m");
+ LOG("SERVER WARNING MESSAGE [Request Id: " + reqId + "]: " + msg);
+ return;
+ },
+ locmessage: function (msg) {
+ if (msg.indexOf("\n") != -1) {
+ msg.split("\n").forEach(function (nmsg) {
+ serverconsole.locmessage(nmsg);
+ });
+ return;
+ }
+ console.log("SERVER MESSAGE [Request Id: " + reqId + "]: " + msg);
+ LOG("SERVER MESSAGE [Request Id: " + reqId + "]: " + msg);
+ return;
+ }
+ };
- function matchHostname(hostname) {
- if (typeof hostname == "undefined" || hostname == "*") {
+ function matchHostname(hostname) {
+ if (typeof hostname == "undefined" || hostname == "*") {
+ return true;
+ } else if (req.headers.host && hostname.indexOf("*.") == 0 && hostname != "*.") {
+ var hostnamesRoot = hostname.substr(2);
+ if (req.headers.host == hostnamesRoot || req.headers.host.indexOf("." + hostnamesRoot) == req.headers.host.length - hostnamesRoot.length - 1) {
return true;
- } else if (req.headers.host && hostname.indexOf("*.") == 0 && hostname != "*.") {
- var hostnamesRoot = hostname.substr(2);
- if (req.headers.host == hostnamesRoot || req.headers.host.indexOf("." + hostnamesRoot) == req.headers.host.length - hostnamesRoot.length - 1) {
+ }
+ } else if (req.headers.host && req.headers.host == hostname) {
+ return true;
+ }
+ return false;
+ }
+
+ function getCustomHeaders() {
+ var ph = JSON.parse(JSON.stringify(customHeaders));
+ if(configJSON.customHeadersVHost) {
+ var vhostP = null;
+ configJSON.customHeadersVHost.every(function(vhost) {
+ if(matchHostname(vhost.host)) {
+ vhostP = vhost;
+ return false;
+ } else {
return true;
}
- } else if (req.headers.host && req.headers.host == hostname) {
- return true;
- }
- return false;
- }
-
- function getCustomHeaders() {
- var ph = JSON.parse(JSON.stringify(customHeaders));
- if(configJSON.customHeadersVHost) {
- var vhostP = null;
- configJSON.customHeadersVHost.every(function(vhost) {
- if(matchHostname(vhost.host)) {
- vhostP = vhost;
- return false;
- } else {
- return true;
- }
- });
- if(vhostP && vhostP.headers) {
- var phNu = JSON.parse(JSON.stringify(vhostP.headers));
- Object.keys(phNu).forEach(function (phNuK) {
- ph[phNuK] = phNu[phNuK];
- });
- }
- }
- Object.keys(ph).forEach(function (phk) {
- if (typeof ph[phk] == "string") ph[phk] = ph[phk].replace(/\{path\}/g, req.url);
});
- return ph;
- }
-
- if (req.headers["x-svr-js-from-main-thread"] == "true" && (!req.socket.remoteAddress || req.socket.remoteAddress == "::1" || req.socket.remoteAddress == "::ffff:127.0.0.1" || req.socket.remoteAddress == "127.0.0.1" || req.socket.remoteAddress == "localhost" || req.socket.remoteAddress == host || req.socket.remoteAddress == "::ffff:" + host)) {
- var headers = getCustomHeaders();
- res.writeHead(204, "No Content", headers);
- res.end();
- return;
- }
-
- req.url = fixNodeMojibakeURL(req.url);
-
- res.writeHeadNative = res.writeHead;
- res.writeHead = function (a, b, c) {
- if (parseInt(a) >= 400 && parseInt(a) <= 599) {
- serverconsole.errmessage("Server responded with " + a.toString() + " code.");
- } else {
- serverconsole.resmessage("Server responded with " + a.toString() + " code.");
- }
- res.writeHeadNative(a, b, c);
- };
-
- var finished = false;
- res.on("finish", function () {
- if (!finished) {
- finished = true;
- serverconsole.locmessage("Client disconnected.");
- }
- });
- res.on("close", function () {
- if (!finished) {
- finished = true;
- serverconsole.locmessage("Client disconnected.");
+ if(vhostP && vhostP.headers) {
+ var phNu = JSON.parse(JSON.stringify(vhostP.headers));
+ Object.keys(phNu).forEach(function (phNuK) {
+ ph[phNuK] = phNu[phNuK];
+ });
}
+ }
+ Object.keys(ph).forEach(function (phk) {
+ if (typeof ph[phk] == "string") ph[phk] = ph[phk].replace(/\{path\}/g, req.url);
});
+ return ph;
+ }
- serverconsole.locmessage("Somebody connected to " + (typeof port == "number" ? "port " : "socket ") + port + "...");
+ if (req.headers["x-svr-js-from-main-thread"] == "true" && (!req.socket.remoteAddress || req.socket.remoteAddress == "::1" || req.socket.remoteAddress == "::ffff:127.0.0.1" || req.socket.remoteAddress == "127.0.0.1" || req.socket.remoteAddress == "localhost" || req.socket.remoteAddress == host || req.socket.remoteAddress == "::ffff:" + host)) {
+ var headers = getCustomHeaders();
+ res.writeHead(204, "No Content", headers);
+ res.end();
+ return;
+ }
- if (req.socket == null) {
- serverconsole.errmessage("Client socket is null!!!");
- return;
+ req.url = fixNodeMojibakeURL(req.url);
+
+ res.writeHeadNative = res.writeHead;
+ res.writeHead = function (a, b, c) {
+ if (parseInt(a) >= 400 && parseInt(a) <= 599) {
+ serverconsole.errmessage("Server responded with " + a.toString() + " code.");
+ } else {
+ serverconsole.resmessage("Server responded with " + a.toString() + " code.");
}
+ res.writeHeadNative(a, b, c);
+ };
- var isProxy = false;
- if (req.url.indexOf("/") != 0 && req.url != "*") isProxy = true;
-
- var head = fs.existsSync("./.head") ? fs.readFileSync("./.head").toString() : (fs.existsSync("./head.html") ? fs.readFileSync("./head.html").toString() : ""); // header
- var foot = fs.existsSync("./.foot") ? fs.readFileSync("./.foot").toString() : (fs.existsSync("./foot.html") ? fs.readFileSync("./foot.html").toString() : ""); // footer
- var fd = "";
-
- function responseEnd(d) {
- if (d === undefined) d = fd;
- res.write(head + d + foot);
- res.end();
+ var finished = false;
+ res.on("finish", function () {
+ if (!finished) {
+ finished = true;
+ serverconsole.locmessage("Client disconnected.");
}
+ });
+ res.on("close", function () {
+ if (!finished) {
+ finished = true;
+ serverconsole.locmessage("Client disconnected.");
+ }
+ });
- //Error descriptions
- var serverErrorDescs = {
- 400: "The request you made is invalid.",
- 417: "Expectation in Expect property couldn't be satisfied.",
- 500: "The server had an unexpected error. Below, the error stack is shown:
{stack}
Please contact with developer/administrator at {contact}.",
- 501: "The request requires use of a function, which isn't currently implemented by the server."
- };
+ serverconsole.locmessage("Somebody connected to " + (typeof port == "number" ? "port " : "socket ") + port + "...");
- //Server error calling method
- function callServerError(errorCode, extName, stack, ch) {
- function getErrorFileName(list, callback, _i) {
- function medCallback(p) {
- if(p) callback(p);
- else {
- if(errorCode == 404) {
- fs.access(page404, fs.constants.F_OK, function(err) {
- if(err) {
- fs.access("." + errorCode.toString(), fs.constants.F_OK, function(err) {
- try {
- if(err) {
- callback(errorCode.toString() + ".html");
- } else {
- callback("." + errorCode.toString());
- }
- } catch(err2) {
- callServerError(500, undefined, generateErrorStack(err2));
- }
- });
- } else {
- try {
- callback(page404);
- } catch(err2) {
- callServerError(500, undefined, generateErrorStack(err2));
- }
- }
- });
- } else {
- fs.access("." + errorCode.toString(), fs.constants.F_OK, function(err) {
+ if (req.socket == null) {
+ serverconsole.errmessage("Client socket is null!!!");
+ return;
+ }
+
+ var isProxy = false;
+ if (req.url.indexOf("/") != 0 && req.url != "*") isProxy = true;
+
+ var head = fs.existsSync("./.head") ? fs.readFileSync("./.head").toString() : (fs.existsSync("./head.html") ? fs.readFileSync("./head.html").toString() : ""); // header
+ var foot = fs.existsSync("./.foot") ? fs.readFileSync("./.foot").toString() : (fs.existsSync("./foot.html") ? fs.readFileSync("./foot.html").toString() : ""); // footer
+ var fd = "";
+
+ function responseEnd(d) {
+ if (d === undefined) d = fd;
+ res.write(head + d + foot);
+ res.end();
+ }
+
+ //Error descriptions
+ var serverErrorDescs = {
+ 400: "The request you made is invalid.",
+ 417: "Expectation in Expect property couldn't be satisfied.",
+ 500: "The server had an unexpected error. Below, the error stack is shown:
{stack}
Please contact with developer/administrator at {contact}.",
+ 501: "The request requires use of a function, which isn't currently implemented by the server."
+ };
+
+ //Server error calling method
+ function callServerError(errorCode, extName, stack, ch) {
+ function getErrorFileName(list, callback, _i) {
+ function medCallback(p) {
+ if(p) callback(p);
+ else {
+ if(errorCode == 404) {
+ fs.access(page404, fs.constants.F_OK, function(err) {
+ if(err) {
+ fs.access("." + errorCode.toString(), fs.constants.F_OK, function(err) {
try {
if(err) {
callback(errorCode.toString() + ".html");
@@ -2333,248 +2310,267 @@ if (!cluster.isPrimary) {
callServerError(500, undefined, generateErrorStack(err2));
}
});
- }
- }
- }
-
- if(!_i) _i = 0;
- if(_i >= list.length) {
- medCallback(false);
- return;
- }
-
- if(list[_i].scode != errorCode || !matchHostname(list[_i].host)) {
- getErrorFileName(list, callback, _i+1);
- return;
- } else {
- fs.access(list[_i].path, fs.constants.F_OK, function(err) {
- if(err) {
- getErrorFileName(list, callback, _i+1);
- } else {
- medCallback(list[_i].path);
- }
- });
- }
- }
-
- getErrorFileName(errorPages, function(errorFile) {
- if (Object.prototype.toString.call(stack) === "[object Error]") stack = generateErrorStack(stack);
- if (stack === undefined) stack = generateErrorStack(new Error("Unknown error"));
- if (errorCode == 500 || errorCode == 502) {
- serverconsole.errmessage("There was an error while processing the request!");
- serverconsole.errmessage("Stack:");
- serverconsole.errmessage(stack);
- }
- if (stackHidden) stack = "[error stack hidden]";
- if (serverErrorDescs[errorCode] === undefined) {
- callServerError(501, extName, stack);
- } else {
- var cheaders = getCustomHeaders();
- if (ch) {
- var chon = Object.keys(cheaders);
- Object.keys(ch).forEach(function (chnS) {
- var nhn = chnS;
- for (var j = 0; j < chon.length; j++) {
- if (chon[j].toLowerCase() == chnS.toLowerCase()) {
- nhn = chon[j];
- break;
+ } else {
+ try {
+ callback(page404);
+ } catch(err2) {
+ callServerError(500, undefined, generateErrorStack(err2));
}
}
- if (ch[chnS]) cheaders[nhn] = ch[chnS];
});
+ } else {
+ fs.access("." + errorCode.toString(), fs.constants.F_OK, function(err) {
+ try {
+ if(err) {
+ callback(errorCode.toString() + ".html");
+ } else {
+ callback("." + errorCode.toString());
+ }
+ } catch(err2) {
+ callServerError(500, undefined, generateErrorStack(err2));
+ }
+ });
+ }
+ }
+ }
+
+ if(!_i) _i = 0;
+ if(_i >= list.length) {
+ medCallback(false);
+ return;
+ }
+
+ if(list[_i].scode != errorCode || !matchHostname(list[_i].host)) {
+ getErrorFileName(list, callback, _i+1);
+ return;
+ } else {
+ fs.access(list[_i].path, fs.constants.F_OK, function(err) {
+ if(err) {
+ getErrorFileName(list, callback, _i+1);
+ } else {
+ medCallback(list[_i].path);
}
- cheaders["Content-Type"] = "text/html; charset=utf-8";
- if (errorCode == 405 && !cheaders["Allow"]) cheaders["Allow"] = "GET, POST, HEAD, OPTIONS";
- fs.readFile(errorFile, function (err, data) {
- try {
- if (err) throw err;
- res.writeHead(errorCode, http.STATUS_CODES[errorCode], cheaders);
- fd += data.toString().replace(/{errorMessage}/g, errorCode.toString() + " " + http.STATUS_CODES[errorCode]).replace(/{errorDesc}/g, serverErrorDescs[errorCode]).replace(/{stack}/g, stack.replace(/&/g, "&").replace(//g, ">").replace(/\r\n/g, "
").replace(/\n/g, "
").replace(/\r/g, "
").replace(/ {2}/g, " ")).replace(/{path}/g, req.url.replace(/&/g, "&").replace(//g, ">")).replace(/{server}/g, "" + (exposeServerVersion ? "SVR.JS/" + version + " (" + getOS() + "; " + (process.isBun ? ("Bun/v" + process.versions.bun + "; like Node.JS/" + process.version) : ("Node.JS/" + process.version)) + ")" : "SVR.JS") + (extName == undefined ? "" : " " + extName) + ((req.headers.host == undefined || isProxy) ? "" : " on " + String(req.headers.host).replace(/&/g, "&").replace(//g, ">"))).replace(/{contact}/g, serverAdmin.replace(/\./g, "[dot]").replace(/@/g, "[at]"));
- responseEnd();
- } catch (err) {
- var additionalError = 500;
- if (err.code == "ENOENT") {
- additionalError = 404;
- } else if (err.code == "ENOTDIR") {
- additionalError = 404; // Assume that file doesn't exist
- } else if (err.code == "EACCES") {
- additionalError = 403;
- } else if (err.code == "ENAMETOOLONG") {
- additionalError = 414;
- } else if (err.code == "EMFILE") {
- additionalError = 503;
- } else if (err.code == "ELOOP") {
- additionalError = 508;
+ });
+ }
+ }
+
+ getErrorFileName(errorPages, function(errorFile) {
+ if (Object.prototype.toString.call(stack) === "[object Error]") stack = generateErrorStack(stack);
+ if (stack === undefined) stack = generateErrorStack(new Error("Unknown error"));
+ if (errorCode == 500 || errorCode == 502) {
+ serverconsole.errmessage("There was an error while processing the request!");
+ serverconsole.errmessage("Stack:");
+ serverconsole.errmessage(stack);
+ }
+ if (stackHidden) stack = "[error stack hidden]";
+ if (serverErrorDescs[errorCode] === undefined) {
+ callServerError(501, extName, stack);
+ } else {
+ var cheaders = getCustomHeaders();
+ if (ch) {
+ var chon = Object.keys(cheaders);
+ Object.keys(ch).forEach(function (chnS) {
+ var nhn = chnS;
+ for (var j = 0; j < chon.length; j++) {
+ if (chon[j].toLowerCase() == chnS.toLowerCase()) {
+ nhn = chon[j];
+ break;
}
- res.writeHead(errorCode, http.STATUS_CODES[errorCode], cheaders);
- res.write(("
{errorMessage}{errorMessage}
{errorDesc}
" + ((additionalError == 404) ? "" : "Additionally, a {additionalError} error occurred while loading an error page.
") + "{server}
").replace(/{errorMessage}/g, errorCode.toString() + " " + http.STATUS_CODES[errorCode]).replace(/{errorDesc}/g, serverErrorDescs[errorCode]).replace(/{stack}/g, stack.replace(/&/g, "&").replace(//g, ">").replace(/\r\n/g, "
").replace(/\n/g, "
").replace(/\r/g, "
").replace(/ {2}/g, " ")).replace(/{path}/g, req.url.replace(/&/g, "&").replace(//g, ">")).replace(/{server}/g, "" + (exposeServerVersion ? "SVR.JS/" + version + " (" + getOS() + "; " + (process.isBun ? ("Bun/v" + process.versions.bun + "; like Node.JS/" + process.version) : ("Node.JS/" + process.version)) + ")" : "SVR.JS") + (extName == undefined ? "" : " " + extName) + ((req.headers.host == undefined || isProxy) ? "" : " on " + String(req.headers.host).replace(/&/g, "&").replace(//g, ">"))).replace(/{contact}/g, serverAdmin.replace(/\./g, "[dot]").replace(/@/g, "[at]")).replace(/{additionalError}/g, additionalError.toString()));
- res.end();
}
+ if (ch[chnS]) cheaders[nhn] = ch[chnS];
});
}
- });
- }
-
- var reqport = "";
- var reqip = "";
- var oldport = "";
- var oldip = "";
- if (req.headers["x-forwarded-for"] != undefined && enableIPSpoofing) {
- reqport = null;
- reqip = req.headers["x-forwarded-for"].split(",")[0].replace(/ /g, "");
- if (reqip.indexOf(":") == -1) reqip = "::ffff:" + reqip;
- try {
- oldport = req.socket.remotePort;
- oldip = req.socket.remoteAddress;
- req.socket.realRemotePort = reqport;
- req.socket.realRemoteAddress = reqip;
- req.socket.originalRemotePort = oldport;
- req.socket.originalRemoteAddress = oldip;
- res.socket.realRemotePort = reqport;
- res.socket.realRemoteAddress = reqip;
- res.socket.originalRemotePort = oldport;
- res.socket.originalRemoteAddress = oldip;
- } catch (err) {
- //Nevermind...
- }
- } else {
- reqip = req.socket.remoteAddress;
- reqport = req.socket.remotePort;
- }
- reqcounter++;
- if (!isProxy) serverconsole.reqmessage("Client " + ((!reqip || reqip == "") ? "[unknown client]" : (reqip + ((reqport && reqport !== 0) && reqport != "" ? ":" + reqport : ""))) + " wants " + (req.method == "GET" ? "content in " : (req.method == "POST" ? "to post content in " : (req.method == "PUT" ? "to add content in " : (req.method == "DELETE" ? "to delete content in " : (req.method == "PATCH" ? "to patch content in " : "to access content using " + req.method + " method in "))))) + (req.headers.host == undefined ? "" : req.headers.host) + req.url);
- else serverconsole.reqmessage("Client " + ((!reqip || reqip == "") ? "[unknown client]" : (reqip + ((reqport && reqport !== 0) && reqport != "" ? ":" + reqport : ""))) + " wants " + (req.method == "GET" ? "content in " : (req.method == "POST" ? "to post content in " : (req.method == "PUT" ? "to add content in " : (req.method == "DELETE" ? "to delete content in " : (req.method == "PATCH" ? "to patch content in " : "to access content using " + req.method + " method in "))))) + req.url);
- if (req.headers["user-agent"] != undefined) serverconsole.reqmessage("Client uses " + req.headers["user-agent"]);
-
- try {
- if (req.headers["expect"] && req.headers["expect"] != "100-continue") {
- serverconsole.errmessage("Expectation not satified!");
- callServerError(417);
- return;
- }
- var hostx = req.headers.host;
- if (hostx === undefined) {
- serverconsole.errmessage("Bad request!");
- callServerError(400);
- return;
- }
-
- if (req.method == "CONNECT") {
- callServerError(501);
- serverconsole.errmessage("CONNECT requests aren't supported. Your JS runtime probably doesn't support 'connect' handler for HTTP library.");
- return;
- }
-
- if (isProxy) {
- callServerError(501);
- serverconsole.errmessage("This server will never be a proxy.");
- return;
- }
-
- function parseURL(uri) {
- if (typeof URL != "undefined" && url.Url) {
+ cheaders["Content-Type"] = "text/html; charset=utf-8";
+ if (errorCode == 405 && !cheaders["Allow"]) cheaders["Allow"] = "GET, POST, HEAD, OPTIONS";
+ fs.readFile(errorFile, function (err, data) {
try {
- var uobject = new URL(uri, "http" + (req.socket.encrypted ? "s" : "") + "://" + (req.headers.host ? req.headers.host : (domain ? domain : "unknown.invalid")));
- var nuobject = new url.Url();
- if (uri.indexOf("/") != -1) nuobject.slashes = true;
- if (uobject.protocol != "") nuobject.protocol = uobject.protocol;
- if (uobject.username != "" && uobject.password != "") nuobject.auth = uobject.username + ":" + uobject.password;
- if (uobject.host != "") nuobject.host = uobject.host;
- if (uobject.hostname != "") nuobject.hostname = uobject.hostname;
- if (uobject.port != "") nuobject.port = uobject.port;
- if (uobject.pathname != "") nuobject.pathname = uobject.pathname;
- if (uobject.search != "") nuobject.search = uobject.search;
- if (uobject.hash != "") nuobject.hash = uobject.hash;
- if (uobject.href != "") nuobject.href = uobject.href;
- if (uri.indexOf("/") != 0) {
- if (nuobject.pathname) {
- nuobject.pathname = nuobject.pathname.substr(1);
- nuobject.href = nuobject.pathname + (nuobject.search ? nuobject.search : "");
- }
- }
- if (nuobject.pathname) {
- nuobject.path = nuobject.pathname + (nuobject.search ? nuobject.search : "");
- }
- nuobject.query = {};
- uobject.searchParams.forEach(function (value, key) {
- nuobject.query[key] = value;
- });
- return nuobject;
+ if (err) throw err;
+ res.writeHead(errorCode, http.STATUS_CODES[errorCode], cheaders);
+ fd += data.toString().replace(/{errorMessage}/g, errorCode.toString() + " " + http.STATUS_CODES[errorCode]).replace(/{errorDesc}/g, serverErrorDescs[errorCode]).replace(/{stack}/g, stack.replace(/&/g, "&").replace(//g, ">").replace(/\r\n/g, "
").replace(/\n/g, "
").replace(/\r/g, "
").replace(/ {2}/g, " ")).replace(/{path}/g, req.url.replace(/&/g, "&").replace(//g, ">")).replace(/{server}/g, "" + (exposeServerVersion ? "SVR.JS/" + version + " (" + getOS() + "; " + (process.isBun ? ("Bun/v" + process.versions.bun + "; like Node.JS/" + process.version) : ("Node.JS/" + process.version)) + ")" : "SVR.JS") + (extName == undefined ? "" : " " + extName) + ((req.headers.host == undefined || isProxy) ? "" : " on " + String(req.headers.host).replace(/&/g, "&").replace(//g, ">"))).replace(/{contact}/g, serverAdmin.replace(/\./g, "[dot]").replace(/@/g, "[at]"));
+ responseEnd();
} catch (err) {
- return url.parse(uri, true);
+ var additionalError = 500;
+ if (err.code == "ENOENT") {
+ additionalError = 404;
+ } else if (err.code == "ENOTDIR") {
+ additionalError = 404; // Assume that file doesn't exist
+ } else if (err.code == "EACCES") {
+ additionalError = 403;
+ } else if (err.code == "ENAMETOOLONG") {
+ additionalError = 414;
+ } else if (err.code == "EMFILE") {
+ additionalError = 503;
+ } else if (err.code == "ELOOP") {
+ additionalError = 508;
+ }
+ res.writeHead(errorCode, http.STATUS_CODES[errorCode], cheaders);
+ res.write(("{errorMessage}{errorMessage}
{errorDesc}
" + ((additionalError == 404) ? "" : "Additionally, a {additionalError} error occurred while loading an error page.
") + "{server}
").replace(/{errorMessage}/g, errorCode.toString() + " " + http.STATUS_CODES[errorCode]).replace(/{errorDesc}/g, serverErrorDescs[errorCode]).replace(/{stack}/g, stack.replace(/&/g, "&").replace(//g, ">").replace(/\r\n/g, "
").replace(/\n/g, "
").replace(/\r/g, "
").replace(/ {2}/g, " ")).replace(/{path}/g, req.url.replace(/&/g, "&").replace(//g, ">")).replace(/{server}/g, "" + (exposeServerVersion ? "SVR.JS/" + version + " (" + getOS() + "; " + (process.isBun ? ("Bun/v" + process.versions.bun + "; like Node.JS/" + process.version) : ("Node.JS/" + process.version)) + ")" : "SVR.JS") + (extName == undefined ? "" : " " + extName) + ((req.headers.host == undefined || isProxy) ? "" : " on " + String(req.headers.host).replace(/&/g, "&").replace(//g, ">"))).replace(/{contact}/g, serverAdmin.replace(/\./g, "[dot]").replace(/@/g, "[at]")).replace(/{additionalError}/g, additionalError.toString()));
+ res.end();
}
- } else {
+ });
+ }
+ });
+ }
+
+ var reqport = "";
+ var reqip = "";
+ var oldport = "";
+ var oldip = "";
+ if (req.headers["x-forwarded-for"] != undefined && enableIPSpoofing) {
+ reqport = null;
+ reqip = req.headers["x-forwarded-for"].split(",")[0].replace(/ /g, "");
+ if (reqip.indexOf(":") == -1) reqip = "::ffff:" + reqip;
+ try {
+ oldport = req.socket.remotePort;
+ oldip = req.socket.remoteAddress;
+ req.socket.realRemotePort = reqport;
+ req.socket.realRemoteAddress = reqip;
+ req.socket.originalRemotePort = oldport;
+ req.socket.originalRemoteAddress = oldip;
+ res.socket.realRemotePort = reqport;
+ res.socket.realRemoteAddress = reqip;
+ res.socket.originalRemotePort = oldport;
+ res.socket.originalRemoteAddress = oldip;
+ } catch (err) {
+ //Nevermind...
+ }
+ } else {
+ reqip = req.socket.remoteAddress;
+ reqport = req.socket.remotePort;
+ }
+ reqcounter++;
+ if (!isProxy) serverconsole.reqmessage("Client " + ((!reqip || reqip == "") ? "[unknown client]" : (reqip + ((reqport && reqport !== 0) && reqport != "" ? ":" + reqport : ""))) + " wants " + (req.method == "GET" ? "content in " : (req.method == "POST" ? "to post content in " : (req.method == "PUT" ? "to add content in " : (req.method == "DELETE" ? "to delete content in " : (req.method == "PATCH" ? "to patch content in " : "to access content using " + req.method + " method in "))))) + (req.headers.host == undefined ? "" : req.headers.host) + req.url);
+ else serverconsole.reqmessage("Client " + ((!reqip || reqip == "") ? "[unknown client]" : (reqip + ((reqport && reqport !== 0) && reqport != "" ? ":" + reqport : ""))) + " wants " + (req.method == "GET" ? "content in " : (req.method == "POST" ? "to post content in " : (req.method == "PUT" ? "to add content in " : (req.method == "DELETE" ? "to delete content in " : (req.method == "PATCH" ? "to patch content in " : "to access content using " + req.method + " method in "))))) + req.url);
+ if (req.headers["user-agent"] != undefined) serverconsole.reqmessage("Client uses " + req.headers["user-agent"]);
+
+ try {
+ if (req.headers["expect"] && req.headers["expect"] != "100-continue") {
+ serverconsole.errmessage("Expectation not satified!");
+ callServerError(417);
+ return;
+ }
+ var hostx = req.headers.host;
+ if (hostx === undefined) {
+ serverconsole.errmessage("Bad request!");
+ callServerError(400);
+ return;
+ }
+
+ if (req.method == "CONNECT") {
+ callServerError(501);
+ serverconsole.errmessage("CONNECT requests aren't supported. Your JS runtime probably doesn't support 'connect' handler for HTTP library.");
+ return;
+ }
+
+ if (isProxy) {
+ callServerError(501);
+ serverconsole.errmessage("This server will never be a proxy.");
+ return;
+ }
+
+ function parseURL(uri) {
+ if (typeof URL != "undefined" && url.Url) {
+ try {
+ var uobject = new URL(uri, "http" + (req.socket.encrypted ? "s" : "") + "://" + (req.headers.host ? req.headers.host : (domain ? domain : "unknown.invalid")));
+ var nuobject = new url.Url();
+ if (uri.indexOf("/") != -1) nuobject.slashes = true;
+ if (uobject.protocol != "") nuobject.protocol = uobject.protocol;
+ if (uobject.username != "" && uobject.password != "") nuobject.auth = uobject.username + ":" + uobject.password;
+ if (uobject.host != "") nuobject.host = uobject.host;
+ if (uobject.hostname != "") nuobject.hostname = uobject.hostname;
+ if (uobject.port != "") nuobject.port = uobject.port;
+ if (uobject.pathname != "") nuobject.pathname = uobject.pathname;
+ if (uobject.search != "") nuobject.search = uobject.search;
+ if (uobject.hash != "") nuobject.hash = uobject.hash;
+ if (uobject.href != "") nuobject.href = uobject.href;
+ if (uri.indexOf("/") != 0) {
+ if (nuobject.pathname) {
+ nuobject.pathname = nuobject.pathname.substr(1);
+ nuobject.href = nuobject.pathname + (nuobject.search ? nuobject.search : "");
+ }
+ }
+ if (nuobject.pathname) {
+ nuobject.path = nuobject.pathname + (nuobject.search ? nuobject.search : "");
+ }
+ nuobject.query = {};
+ uobject.searchParams.forEach(function (value, key) {
+ nuobject.query[key] = value;
+ });
+ return nuobject;
+ } catch (err) {
return url.parse(uri, true);
}
- }
- var urlp = parseURL("http://" + hostx);
- try {
- if (urlp.path.indexOf("//") == 0) {
- urlp = parseURL("http:" + url.path);
- }
- } catch (err) {
- //URL parse error...
- }
- if (urlp.host == "localhost" || urlp.host == "localhost:" + port.toString() || urlp.host == "127.0.0.1" || urlp.host == "127.0.0.1:" + port.toString() || urlp.host == "::1" || urlp.host == "::1:" + port.toString()) {
- urlp.protocol = "https:";
- if (sport == 443) {
- urlp.host = urlp.hostname;
- } else {
- urlp.host = urlp.hostname + ":" + sport.toString();
- urlp.port = sport.toString();
- }
- } else if (urlp.host == (listenAddress ? listenAddress : host) || urlp.host == (listenAddress ? listenAddress : host) + ":" + port.toString()) {
- urlp.protocol = "https:";
- if (sport == 443) {
- urlp.host = urlp.hostname;
- } else {
- urlp.host = urlp.hostname + ":" + sport.toString();
- urlp.port = sport.toString();
- }
- } else if (urlp.host == pubip || urlp.host == pubip + ":" + pubport.toString()) {
- urlp.protocol = "https:";
- if (spubport == 443) {
- urlp.host = urlp.hostname;
- } else {
- urlp.host = urlp.hostname + ":" + spubport.toString();
- urlp.port = spubport.toString();
- }
- } else if (urlp.hostname == domain || urlp.hostname.indexOf(domain) != -1) {
- urlp.protocol = "https:";
- if (spubport == 443) {
- urlp.host = urlp.hostname;
- } else {
- urlp.host = urlp.hostname + ":" + spubport.toString();
- urlp.port = spubport.toString();
- }
} else {
- urlp.protocol = "https:";
+ return url.parse(uri, true);
}
- urlp.path = null;
- urlp.pathname = null;
- var lloc = url.format(urlp);
- var requestURL = req.url;
- try {
- if (requestURL.split("/")[1].indexOf(".onion") != -1) {
- requestURL = requestURL.split("/");
- requestURL.shift();
- requestURL.shift();
- requestURL.unshift("");
- requestURL = requestURL.join("/");
- }
- } catch (err) {
- //Leave URL as it is...
- }
- var rheaders = getCustomHeaders();
- rheaders["Location"] = lloc + requestURL;
- res.writeHead(301, "Redirect to HTTPS", rheaders);
- res.end();
- } catch (err) {
- serverconsole.errmessage("There was an error while processing the request!");
- serverconsole.errmessage("Stack:");
- serverconsole.errmessage(generateErrorStack(err));
- callServerError(500, undefined, generateErrorStack(err));
}
+ var urlp = parseURL("http://" + hostx);
+ try {
+ if (urlp.path.indexOf("//") == 0) {
+ urlp = parseURL("http:" + url.path);
+ }
+ } catch (err) {
+ //URL parse error...
+ }
+ if (urlp.host == "localhost" || urlp.host == "localhost:" + port.toString() || urlp.host == "127.0.0.1" || urlp.host == "127.0.0.1:" + port.toString() || urlp.host == "::1" || urlp.host == "::1:" + port.toString()) {
+ urlp.protocol = "https:";
+ if (sport == 443) {
+ urlp.host = urlp.hostname;
+ } else {
+ urlp.host = urlp.hostname + ":" + sport.toString();
+ urlp.port = sport.toString();
+ }
+ } else if (urlp.host == (listenAddress ? listenAddress : host) || urlp.host == (listenAddress ? listenAddress : host) + ":" + port.toString()) {
+ urlp.protocol = "https:";
+ if (sport == 443) {
+ urlp.host = urlp.hostname;
+ } else {
+ urlp.host = urlp.hostname + ":" + sport.toString();
+ urlp.port = sport.toString();
+ }
+ } else if (urlp.host == pubip || urlp.host == pubip + ":" + pubport.toString()) {
+ urlp.protocol = "https:";
+ if (spubport == 443) {
+ urlp.host = urlp.hostname;
+ } else {
+ urlp.host = urlp.hostname + ":" + spubport.toString();
+ urlp.port = spubport.toString();
+ }
+ } else if (urlp.hostname == domain || urlp.hostname.indexOf(domain) != -1) {
+ urlp.protocol = "https:";
+ if (spubport == 443) {
+ urlp.host = urlp.hostname;
+ } else {
+ urlp.host = urlp.hostname + ":" + spubport.toString();
+ urlp.port = spubport.toString();
+ }
+ } else {
+ urlp.protocol = "https:";
+ }
+ urlp.path = null;
+ urlp.pathname = null;
+ var lloc = url.format(urlp);
+ var requestURL = req.url;
+ try {
+ if (requestURL.split("/")[1].indexOf(".onion") != -1) {
+ requestURL = requestURL.split("/");
+ requestURL.shift();
+ requestURL.shift();
+ requestURL.unshift("");
+ requestURL = requestURL.join("/");
+ }
+ } catch (err) {
+ //Leave URL as it is...
+ }
+ var rheaders = getCustomHeaders();
+ rheaders["Location"] = lloc + requestURL;
+ res.writeHead(301, "Redirect to HTTPS", rheaders);
+ res.end();
+ } catch (err) {
+ serverconsole.errmessage("There was an error while processing the request!");
+ serverconsole.errmessage("Stack:");
+ serverconsole.errmessage(generateErrorStack(err));
+ callServerError(500, undefined, generateErrorStack(err));
}
}