आलसी डेवलपर्स के लिए रिच लिंक
जब मैं Twitter या Slack पर एक ब्लॉग लिंक साझा करता हूं, तो यह सादे टेक्स्ट के रूप में दिखाई देता है। कोई पूर्वावलोकन छवि नहीं। बस एक URL जैसे granda.org/en/2026/01/02/claude-code-on-the-go/।
मुझे Open Graph छवियों की आवश्यकता थी। मानक दृष्टिकोण: प्रत्येक पोस्ट के लिए मैन्युअल रूप से 1200x630 छवि बनाएं। यह थकाऊ है। मैंने Claude से इसे स्वचालित करने के लिए कहा।
flowchart LR
Push[git push] --> GHA[GitHub Actions]
GHA --> Hugo[Hugo Server]
GHA --> PW[Playwright]
PW -->|screenshot| Hugo
PW --> IMG[OG Image]
IMG --> Commit[git commit]
Commit --> Deploy[Deploy]
flowchart TB
Push[git push] --> GHA[GitHub Actions]
GHA --> Hugo[Hugo Server]
GHA --> PW[Playwright]
PW -->|screenshot| Hugo
PW --> IMG[OG Image]
IMG --> Commit[git commit]
Commit --> Deploy[Deploy]
सेटअप
मैंने Claude को समस्या बताई: पोस्ट को सोशल पूर्वावलोकन छवियों की आवश्यकता है, लेकिन मैं उन्हें मैन्युअल रूप से नहीं बनाना चाहता। लेख की सामग्री का स्क्रीनशॉट लें, इसे OG छवि के रूप में सहेजें, फ्रंटमैटर को स्वचालित रूप से अपडेट करें।
Claude ने क्या बनाया
| घटक | उद्देश्य |
|---|---|
generate-og-image.js | पोस्ट के स्क्रीनशॉट के लिए Playwright स्क्रिप्ट |
generate-og-images.yml | पोस्ट परिवर्तनों पर ट्रिगर होने वाला GitHub Action |
baseof.html परिवर्तन | सशर्त og:image मेटा टैग |
Playwright स्क्रिप्ट हेडलेस Chrome लॉन्च करती है, पोस्ट पर नेविगेट करती है, लाइट मोड को मजबूर करती है, हेडर और फुटर को छिपाती है, और 1200x630 पर स्क्रीनशॉट लेती है:
const browser = await chromium.launch({ headless: true });
const context = await browser.newContext({
viewport: { width: 1200, height: 630 },
deviceScaleFactor: 2, // Retina for crisp text
});
// Force light mode, hide nav
await page.evaluate(() => {
document.documentElement.setAttribute("data-theme", "light");
document.querySelector("header").style.display = "none";
document.querySelector("footer").style.display = "none";
});
await page.screenshot({ path: outputPath, type: "png" });
GitHub Action किसी भी .en.md फ़ाइल परिवर्तन पर ट्रिगर होता है, Hugo शुरू करता है, स्क्रिप्ट चलाता है, और उत्पन्न छवि को रेपो में वापस कमिट करता है:
on:
push:
branches: [main]
paths:
- "content/posts/**/*.md"
steps:
- name: Start Hugo server
run: hugo server --bind 0.0.0.0 --port 1313 &
- name: Generate OG images
run: node scripts/generate-og-image.js "$file"
- name: Commit changes
run: |
git add static/images/posts/ content/posts/
git commit -m "Generate Open Graph images for blog posts"
git push
टेम्पलेट सशर्त रूप से छवि शामिल करता है जब फ्रंटमैटर में image फ़ील्ड होता है:
{{- if .Params.image -}}
<meta property="og:image" content="{{ $canonical }}{{ .Params.image }}">
<meta name="twitter:card" content="summary_large_image">
<meta name="twitter:image" content="{{ $canonical }}{{ .Params.image }}">
{{- else -}}
<meta name="twitter:card" content="summary">
{{- end -}}
404: स्लग नहीं मिला
पहला रन। Playwright ने एक खाली पृष्ठ का स्क्रीनशॉट लिया। URL ने 404 लौटाया।
स्क्रिप्ट ने फ़ाइल नाम से URL बनाया था: automatic-blog-translations.en.md → /en/2025/12/23/automatic-blog-translations/
लेकिन Hugo स्लग के लिए फ़ाइल नाम का उपयोग नहीं करता है। यह शीर्षक का उपयोग करता है। वास्तविक URL /en/2025/12/23/automatic-blog-translations-with-claude-and-github-actions/ था।
मैं JavaScript में Hugo के slugify एल्गोरिदम को पुनर्कार्यान्वित कर सकता था। इसके बजाय: Hugo से पूछें।
const output = execSync("hugo list all", { encoding: "utf8" });
// CSV output includes the exact permalink Hugo generates
एक पंक्ति। कोई एज केस नहीं। Hugo पहले से ही अपने स्वयं के URL जानता है।
आगे क्या है
वर्तमान कार्यान्वयन केवल अंग्रेजी पोस्ट के लिए छवियां उत्पन्न करता है। अनुवादित संस्करण उसी छवि पथ का संदर्भ देते हैं, जो काम करता है, लेकिन इसका मतलब है कि स्पेनिश या जापानी संस्करण साझा करते समय भी OG छवि हमेशा अंग्रेजी पाठ दिखाती है।
सच्चा i18n समर्थन अगले PR में आ रहा है। अभी के लिए, प्रत्येक पोस्ट को एक सोशल छवि मिलती है, जो कुछ नहीं से बेहतर है।
निष्कर्ष
इसे बनाने और डीबग करने में 14 मिनट लगे। अब प्रत्येक पोस्ट को स्वचालित रूप से एक सोशल पूर्वावलोकन छवि मिलती है। प्रति पोस्ट कोई मैन्युअल काम नहीं। स्वचालन मुट्ठी भर पोस्ट के बाद खुद को चुका देता है।
काम करने वाले संस्करण को भेजें, अंतराल की खोज करें, पुनरावृत्ति करें।
संबंधित पोस्ट:
- Claude और GitHub Actions के साथ स्वचालित ब्लॉग अनुवाद - समान स्टैक, अलग स्वचालन
- मेरा QA इंजीनियर एक LLM है - Claude को अपने द्वारा लिखे गए कोड की समीक्षा करने देना
- Claude के साथ अपना स्वयं का न्यूज़लेटर रोल करना - एक और 30 मिनट का निर्माण