#!/usr/bin/env node const fs = require("fs"); const path = require("path"); const { spawn } = require("child_process"); const https = require("https"); const crypto = require("crypto"); const size = 256; const outputDir = ".git/avatar"; if (!fs.existsSync(".git")) { console.error("No .git/ directory found in current path"); process.exit(1); } if (!fs.existsSync(outputDir)) { fs.mkdirSync(outputDir, { recursive: true }); } const processedAuthors = new Set(); const gitLogCommand = "git"; const gitLogArgs = ["log", "--pretty=format:%ae|%an"]; const gitLog = spawn(gitLogCommand, gitLogArgs); gitLog.stdout.on("data", (data) => { const lines = data.toString().trim().split("\n"); lines.forEach((line) => { const [email, author] = line.split("|"); if (processedAuthors.has(author)) { return; } processedAuthors.add(author); const authorImageFile = path.join(outputDir, `${author}.png`); console.log(`Author image file: ${authorImageFile}`); if (fs.existsSync(authorImageFile)) { return; } const emailHash = crypto .createHash("md5") .update(email.toLowerCase()) .digest("hex"); const gravUrl = `https://www.gravatar.com/avatar/${emailHash}?s=${size}`; console.log(`Gravatar URL: ${gravUrl}`); https .get(gravUrl, (response) => { if (response.statusCode === 200) { const writer = fs.createWriteStream(authorImageFile); response.pipe(writer); console.log("Image saved successfully"); } else { console.error( `Failed to save image: ${response.statusCode} ${response.statusMessage}`, ); fs.unlinkSync(authorImageFile); } }) .on("error", (error) => { console.error(`Failed to save image: ${error.message}`); fs.unlinkSync(authorImageFile); }); }); }); gitLog.stderr.on("data", (data) => { console.error(`Error executing git log: ${data}`); }); gitLog.on("close", (code) => { if (code !== 0) { console.error(`git log process exited with code ${code}`); } });