Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 7 additions & 5 deletions scripts/patch-ejs.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,10 @@ import { join } from "https://deno.land/std@0.224.0/path/mod.ts";

const EJS_SRC_DIR = join(Deno.cwd(), "ejs/src");

function timestamp() {
return new Date().toISOString().slice(5, 19).replace("T", " ");
}

async function patchFile(path: string) {
let content = await Deno.readTextFile(path);
let changed = false;
Expand All @@ -21,16 +25,14 @@ async function patchFile(path: string) {

if (changed) {
await Deno.writeTextFile(path, content);
console.log(`Patched ${path}`);
console.log(`[${timestamp()}] Patched ${path}`);
}
}

console.log(`Starting to patch files in ${EJS_SRC_DIR}...`);
console.log(`[${timestamp()}] Starting to patch files in ${EJS_SRC_DIR}...`);

for await (const entry of walk(EJS_SRC_DIR, { exts: [".ts"] })) {
if (entry.isFile) {
await patchFile(entry.path);
}
}

console.log("Patching complete.");
console.log(`[${timestamp()}] Patching complete.`);
4 changes: 3 additions & 1 deletion server.ts
Original file line number Diff line number Diff line change
Expand Up @@ -94,5 +94,7 @@ const host = Deno.env.get("HOST") || '0.0.0.0';
await initializeCache();
initializeWorkers();

console.log(`Server listening on http://${host}:${port}`);
const ts = new Date().toISOString().slice(5, 19).replace("T", " ");
console.log(`[${ts}] Server listening on http://${host}:${port}`);

await serve(handler, { port: Number(port), hostname: host });
37 changes: 30 additions & 7 deletions src/playerCache.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,31 @@ import { extractPlayerId } from "./utils.ts";

const ignorePlayerScriptRegion = Deno.env.get("IGNORE_SCRIPT_REGION") === "true";

export const CACHE_HOME = Deno.env.get("XDG_CACHE_HOME") || join(Deno.env.get("HOME"), '.cache');
export const CACHE_DIR = join(CACHE_HOME, 'yt-cipher', 'player_cache');
function getCacheHome(): string {
// XDG standard (Linux, optional on others)
const xdg = Deno.env.get("XDG_CACHE_HOME");
if (xdg) return xdg;

// Windows
if (Deno.build.os === "windows") {
const localAppData = Deno.env.get("LOCALAPPDATA");
if (localAppData) return join(localAppData, "cache");
}

// macOS / Linux fallback
const home = Deno.env.get("HOME") ?? Deno.env.get("USERPROFILE");
if (home) return join(home, ".cache");

throw new Error("Unable to determine cache directory");
}

export const CACHE_HOME = getCacheHome();
export const CACHE_DIR = join(CACHE_HOME, "yt-cipher", "player_cache");

// This is used for better logging
function timestamp() {
return new Date().toISOString().slice(5, 19).replace("T", " ");
}

export async function getPlayerFilePath(playerUrl: string): Promise<string> {
let cacheKey: string;
Expand All @@ -30,7 +53,7 @@ export async function getPlayerFilePath(playerUrl: string): Promise<string> {
return filePath;
} catch (error) {
if (error instanceof Deno.errors.NotFound) {
console.log(`Cache miss for player: ${playerUrl}. Fetching...`);
console.log(`[${timestamp()}] Cache miss for player: ${playerUrl}. Fetching...`);
const response = await fetch(playerUrl);
playerScriptFetches.labels({ player_url: playerUrl, status: response.statusText }).inc();
if (!response.ok) {
Expand All @@ -46,7 +69,7 @@ export async function getPlayerFilePath(playerUrl: string): Promise<string> {
}
cacheSize.labels({ cache_name: 'player' }).set(fileCount);

console.log(`Saved player to cache: ${filePath}`);
console.log(`[${timestamp()}] Saved player to cache: ${filePath}`);
return filePath;
}
throw error;
Expand All @@ -59,20 +82,20 @@ export async function initializeCache() {
// Since these accumulate over time just cleanout 14 day unused ones
let fileCount = 0;
const thirtyDays = 14 * 24 * 60 * 60 * 1000;
console.log(`Cleaning up player cache directory: ${CACHE_DIR}`);
console.log(`[${timestamp()}] Cleaning up player cache directory: ${CACHE_DIR}`);
for await (const dirEntry of Deno.readDir(CACHE_DIR)) {
if (dirEntry.isFile) {
const filePath = join(CACHE_DIR, dirEntry.name);
const stat = await Deno.stat(filePath);
const lastAccessed = stat.atime?.getTime() ?? stat.mtime?.getTime() ?? stat.birthtime?.getTime();
if (lastAccessed && (Date.now() - lastAccessed > thirtyDays)) {
console.log(`Deleting stale player cache file: ${filePath}`);
console.log(`[${timestamp()}] Deleting stale player cache file: ${filePath}`);
await Deno.remove(filePath);
} else {
fileCount++;
}
}
}
cacheSize.labels({ cache_name: 'player' }).set(fileCount);
console.log(`Player cache directory ensured at: ${CACHE_DIR}`);
console.log(`[${timestamp()}] Player cache directory ensured at: ${CACHE_DIR}`);
}
3 changes: 2 additions & 1 deletion src/workerPool.ts
Original file line number Diff line number Diff line change
Expand Up @@ -47,5 +47,6 @@ export function initializeWorkers() {
worker.isIdle = true;
workers.push(worker);
}
console.log(`Initialized ${CONCURRENCY} workers`);
const ts = new Date().toISOString().slice(5, 19).replace("T", " ");
console.log(`[${ts}] Initialized ${CONCURRENCY} workers`);
}