UNPKG

internet-information-services

Version:

internet-information-services

398 lines (224 loc) 9.11 kB
"use strict"; var fs, sites; exports.service = function (api) { fs = api.fs; sites = api.sites; if (!fs.existsSync(api.projectDir + "/certificate")) fs.mkdirSync(api.projectDir + "/certificate"); return function (request, response) { var auth = {}; if (request.headers.cookie) request.headers.cookie.split("; ").forEach(function (cookie) { var arr = cookie.split("="); auth[arr[0]] = arr[1]; }); switch (request.method.toLowerCase()) { case "get": response.writeHead(200); if (String(api.admin) === auth.admin && request.url !== "/logout") response.write(fs.readFileSync(__dirname + "/admin.html")); else { if (request.url === "/logout") response.writeHead(302, { "Set-Cookie": "admin=; expires=Thu, 01 Jan 1970 00:00:00 GMT; path=/; samesite=lax", Location: "/" }); else { response.writeHead(200, { "Set-Cookie": "admin=; expires=Thu, 01 Jan 1970 00:00:00 GMT; path=/; samesite=lax" }); response.write(fs.readFileSync(__dirname + "/login.html")); } } response.end(); break; case "post": var chunks = []; var size = 0; request.on("data", function (chunk) { chunks.push(chunk); size += chunk.length; }); request.on("end", function () { var obj = parsePost( request.headers["content-type"] || "application/x-www-form-urlencoded", Buffer.concat(chunks, size), api.projectDir ); if (obj.type) { response.write(handle(obj, api)); } else { if (obj.uid.length >= 4 && obj.pwd === String(api.admin)) { setAuth(obj.pwd, response); response.write(fs.readFileSync(__dirname + "/admin.html")); } else { response.write(fs.readFileSync(__dirname + "/login.html")); } } response.end(); }); break; } } }; function handle(obj, api) { var data = {}; switch (obj.type) { case "getSites": data = sites; break; case "caList": data = fs.readdirSync(api.projectDir + "/certificate"); break; case "delFile": var path = api.projectDir + "/certificate/" + obj.fileName; if (fs.existsSync(path)) fs.unlinkSync(path); data = {rc: 0}; break; case "uploadCa": obj.file.save("/certificate", obj.name + obj.file.filename.substr(obj.file.filename.lastIndexOf("."))); data = {rc: 0}; break; case "add": if (!sites.hasOwnProperty(obj.name)) { sites[obj.name] = JSON.parse(obj.site); api.writeSites(); } break; case "del": if (sites.hasOwnProperty(obj.site)) { delete sites[obj.site]; setTimeout(function () { rmdir(api.projectDir + "/wwwroot/" + obj.site); }, 1); api.updatePort(); api.writeSites(); } break; case "save": if (sites.hasOwnProperty(obj.name)) { var service = sites[obj.name].domains.service; sites[obj.name] = JSON.parse(obj.site); sites[obj.name].domains.service = service; api.updatePort(); api.writeSites(); } break; case "stop": if (sites.hasOwnProperty(obj.name)) { if (obj.stop === "true") sites[obj.name].stop = true; else delete sites[obj.name].stop; api.writeSites(); } break; case "restart": if (sites.hasOwnProperty(obj.name)) { api.updatePort(); api.restart(obj.name); } break; case "rename": if (sites.hasOwnProperty(obj.old)) { fs.renameSync(api.projectDir + "/wwwroot/" + obj.old, api.projectDir + "/wwwroot/" + obj.new); var temp = sites[obj.old]; sites[obj.new] = temp; delete sites[obj.old]; } break; } return JSON.stringify(data); } function rmdir(dir) { var children = fs.readdirSync(dir); if (children.length) children.forEach(function (path) { path = dir + "/" + path; var stat = fs.statSync(path); if (stat.isDirectory()) rmdir(path); else fs.unlinkSync(path); }); fs.rmdirSync(dir); } function setAuth(admin, response) { var date = new Date(); date.setTime(date.getTime() + 2 * 24 * 3600 * 1000); date = date.toGMTString(); response.writeHead(200, { "Set-Cookie": "admin=" + admin + "; expires=" + date + "; path=/; samesite=lax; httponly" }); } function parsePost(enctype, data, staticDir) { var arr = enctype.split(";"); var obj = {}; switch (arr[0]) { case "text/plain": data.toString().split("\r\n").forEach(function (value) { if (value.length) { obj[value.substring(0, value.indexOf("="))] = value.substring(value.indexOf("=") + 1); } }); break; case "application/x-www-form-urlencoded": obj = querystring.parse(data.toString()); break; case "multipart/form-data": var boundary = new Buffer("--" + arr[1].substring(arr[1].indexOf("=") + 1)); var i = data.indexOf(boundary); while (data.indexOf(boundary, i + 1) >= 0) { parsePostData(data.slice(i + boundary.length + 2, data.indexOf(boundary, i + 1)), obj, staticDir); i = data.indexOf(boundary, i + 1); } break; } return obj; } function parsePostData(buffer, obj, staticDir) { var key = new Buffer("\r\n\r\n"); var head = buffer.slice(0, buffer.indexOf(key)).toString(); var body = buffer.slice(buffer.indexOf(key) + 4, buffer.length - 2); key = " name=\""; var i = head.indexOf(key) + key.length; var name = head.substring(i, head.indexOf("\"", i)); obj[name] = {name: name}; key = " filename=\""; if (head.indexOf(key, i) > 0) { i = head.indexOf(key) + key.length; obj[name].filename = head.substring(i, head.indexOf("\"", i)); } key = "Content-Type:"; if (head.indexOf(key, i) > 0) { i = head.indexOf(key) + key.length; obj[name].type = head.substring(i).trim(); } if (obj[name].filename && obj[name].type) { obj[name].data = body; obj[name].save = function (path, filename, sync) { path = String(path || "temp"); if (!fs.existsSync("{0}/{1}".format(staticDir, path))) fs.mkdirSync("{0}/{1}".format(staticDir, path)); if (!filename) { path = "{dir}/{name}.{suffix}" .format({ dir: path, name: this.name, suffix: this.type.substring(this.type.indexOf("/") + 1) }) } else if (filename.indexOf(".") < 0) path = "{0}/{1}.{2}".format(path, filename, this.type.substring(this.type.indexOf("/") + 1)); else path = "{0}/{1}".format(path, filename); if (sync) fs.writeFileSync("{0}/{1}".format(staticDir, path), this.data); else fs.writeFile("{0}/{1}".format(staticDir, path), this.data, function () { }); return "/" + path; }; } else obj[name] = body.toString(); }