77 lines
2.7 KiB
JavaScript
77 lines
2.7 KiB
JavaScript
#!/usr/bin/env node
|
|
const http = require("http");
|
|
const fs = require("fs");
|
|
const path = require("path");
|
|
|
|
const PORT = parseInt(process.argv[2] || "7777", 10);
|
|
const ROOT = __dirname;
|
|
|
|
const MIME = {
|
|
".html": "text/html",
|
|
".css": "text/css",
|
|
".js": "application/javascript",
|
|
".json": "application/json",
|
|
".png": "image/png",
|
|
".svg": "image/svg+xml",
|
|
".md": "text/plain",
|
|
};
|
|
|
|
http.createServer((req, res) => {
|
|
let urlPath = req.url === "/" ? "/index.html" : req.url;
|
|
// auto-serve directory listing if no index
|
|
if (urlPath === "/index.html" && !fs.existsSync(path.join(ROOT, "index.html"))) {
|
|
const files = fs.readdirSync(ROOT).filter(f => !f.startsWith(".") && f !== "serve.js");
|
|
const links = files
|
|
.sort((a, b) => {
|
|
const aHtml = a.endsWith(".html");
|
|
const bHtml = b.endsWith(".html");
|
|
if (aHtml && !bHtml) return -1;
|
|
if (!aHtml && bHtml) return 1;
|
|
return a.localeCompare(b);
|
|
})
|
|
.map(f => {
|
|
const isHtml = f.endsWith(".html");
|
|
const icon = isHtml ? "🖼" : f.endsWith(".json") ? "📋" : f.endsWith(".md") ? "📄" : "📁";
|
|
return `<li><a href="/${f}">${icon} ${f}</a></li>`;
|
|
})
|
|
.join("\n");
|
|
|
|
res.writeHead(200, { "Content-Type": "text/html" });
|
|
res.end(`<!DOCTYPE html>
|
|
<html>
|
|
<head>
|
|
<meta charset="UTF-8">
|
|
<title>Age of Dwarves — Designs</title>
|
|
<link href="https://fonts.googleapis.com/css2?family=Grenze+Gotisch:wght@900&family=Bitter:wght@700&display=swap" rel="stylesheet">
|
|
<style>
|
|
body { background:#171219; color:#e0d8c8; font-family:'Bitter',serif; padding:48px; max-width:600px; margin:0 auto; }
|
|
h1 { font-family:'Grenze Gotisch',serif; color:#f2d973; font-size:36px; margin-bottom:6px; }
|
|
p { color:#b2b2b2; font-size:13px; margin-bottom:32px; }
|
|
ul { list-style:none; padding:0; }
|
|
li { margin-bottom:10px; }
|
|
a { color:#d9b33f; text-decoration:none; font-size:15px; padding:10px 16px; display:block;
|
|
background:#17121e; border:1px solid #73591fcc; border-radius:3px; transition:all 150ms ease; }
|
|
a:hover { background:#331a0d; border-color:#d9b33f; color:#ffeb80; }
|
|
</style>
|
|
</head>
|
|
<body>
|
|
<h1>Age of Dwarves</h1>
|
|
<p>Design System · .project/designs/</p>
|
|
<ul>${links}</ul>
|
|
</body>
|
|
</html>`);
|
|
return;
|
|
}
|
|
|
|
const filePath = path.join(ROOT, urlPath);
|
|
if (!filePath.startsWith(ROOT)) { res.writeHead(403); res.end(); return; }
|
|
|
|
fs.readFile(filePath, (err, data) => {
|
|
if (err) { res.writeHead(404, { "Content-Type": "text/plain" }); res.end("Not found"); return; }
|
|
const ext = path.extname(filePath);
|
|
res.writeHead(200, { "Content-Type": MIME[ext] || "application/octet-stream" });
|
|
res.end(data);
|
|
});
|
|
}).listen(PORT, () => {
|
|
console.log(`\n Age of Dwarves designs → http://localhost:${PORT}\n`);
|
|
});
|