78 lines
2.7 KiB
JavaScript
78 lines
2.7 KiB
JavaScript
var {WebSocketServer} = require("ws");
|
|
var qs = require("qs");
|
|
var proxyaddr = require("proxy-addr");
|
|
var child_process = require("child_process");
|
|
var {app, server} = require("./web");
|
|
var {getList, uncacheList} = require("./metalist");
|
|
var fs = require("fs");
|
|
|
|
var wss = new WebSocketServer({ server });
|
|
|
|
wss.on("connection", function(ws, req) {
|
|
req.ip = proxyaddr(req, app.get("trust proxy"));
|
|
req.query = qs.parse(req.url.substring(req.url.indexOf('?')+1));
|
|
|
|
var log = (msg, e) => console[e?'error':'log'](`[${new Date().toLocaleString()}] ${req.ip} - ${msg}`);
|
|
log("socket open: " + req.url);
|
|
|
|
var yturl = req.query.url;
|
|
if (!yturl) { ws.send(color("red", "missing url")); ws.close(); return }
|
|
|
|
var alias = req.query.alias;
|
|
if (alias) {
|
|
alias = alias.toLowerCase();
|
|
if (!/^[a-z0-9-_]{1,32}$/.test(alias)) { ws.send(color("red", "alias must be no more than 32 chars of only letters, numbers, hypens or underscores.")); ws.close(); return }
|
|
if (fs.existsSync(`aliases/${alias}`)) { ws.send(color("red", `the alias ${alias} already exists.`)); ws.close(); return }
|
|
}
|
|
|
|
var ytid = yturl.match(/https:\/\/(?:(?:www\.)?youtube\.com\/(?:watch\?v=|shorts\/)|youtu\.be\/)([A-Za-z0-9_-]{11})/)?.[1];
|
|
if (!ytid) { ws.send(color("red", "youtube url not valid")); ws.close(); return }
|
|
|
|
ws.send(color("green", "spawning yt-dlp..."));
|
|
var cp = child_process.spawn("yt-dlp", ["--format=mp4", "--max-filesize=1G", `--match-filter=duration<7200`, "--no-mtime", `https://www.youtube.com/watch?v=${ytid}`], {cwd: "videos", shell: false});
|
|
|
|
cp.on("error", error => {
|
|
log(error.message, true);
|
|
ws.send(color("red", error.message));
|
|
});
|
|
cp.stdout.on("data", data => {
|
|
var msg = data.toString().trim();
|
|
if (msg) {
|
|
log(msg);
|
|
ws.send("yt-dlp: " + color("blue", msg));
|
|
}
|
|
});
|
|
cp.stderr.on("data", data => {
|
|
var msg = data.toString().trim();
|
|
if (msg) {
|
|
log(msg, true);
|
|
ws.send(color("orange", "yt-dlp: " + color("blue", msg)));
|
|
}
|
|
});
|
|
cp.on("close", (code, signal) => {
|
|
log(`cp exit ${code} (${signal})`);
|
|
ws.send(color("green", `yt-dlp exited with code ${code}`));
|
|
let files = fs.readdirSync("videos");
|
|
let file = files.find(file => file.includes(`[${ytid}]`));
|
|
if (file) {
|
|
if (alias) fs.writeFileSync(`aliases/${alias}`, file);
|
|
let url = `https://${req.headers.host}/v/${file}`;
|
|
ws.send(`MP4 URL (<button onclick="navigator.clipboard.writeText(\`${url}\`)">Copy</button>): <a href="${url}">${url}</a>`)
|
|
} else {
|
|
ws.send(color("red", "error: couldn't find file to alias"));
|
|
}
|
|
|
|
uncacheList();
|
|
ws.close();
|
|
});
|
|
|
|
ws.on("close", () => {
|
|
log("socket closed");
|
|
cp.kill();
|
|
});
|
|
});
|
|
|
|
function color(color, text) {
|
|
return `<span style="color: ${color}">${text}</span>`;
|
|
}
|