From d7d795f076800465355d78d9a265edca2aa36a37 Mon Sep 17 00:00:00 2001
From: KoalaDev <6156589+Shik3i@users.noreply.github.com>
Date: Wed, 8 Jul 2026 16:53:57 +0200
Subject: [PATCH] build(website): integrate dynamic sitemap generation into
main build script
---
scripts/generate-sitemap.cjs | 109 -----------------------------------
website/build.cjs | 100 +++++++++++++++++++++++++++++++-
2 files changed, 99 insertions(+), 110 deletions(-)
delete mode 100644 scripts/generate-sitemap.cjs
diff --git a/scripts/generate-sitemap.cjs b/scripts/generate-sitemap.cjs
deleted file mode 100644
index 4668906..0000000
--- a/scripts/generate-sitemap.cjs
+++ /dev/null
@@ -1,109 +0,0 @@
-const fs = require('fs');
-const path = require('path');
-
-const sitemapPath = path.join(__dirname, '../website/sitemap.xml');
-
-const languages = [
- { code: 'en', prefix: '', hreflang: 'en' },
- { code: 'de', prefix: 'de/', hreflang: 'de' },
- { code: 'fr', prefix: 'fr/', hreflang: 'fr' },
- { code: 'es', prefix: 'es/', hreflang: 'es' },
- { code: 'pt-BR', prefix: 'pt-BR/', hreflang: 'pt-br' },
- { code: 'ru', prefix: 'ru/', hreflang: 'ru' },
- { code: 'it', prefix: 'it/', hreflang: 'it' },
- { code: 'pl', prefix: 'pl/', hreflang: 'pl' },
- { code: 'tr', prefix: 'tr/', hreflang: 'tr' },
- { code: 'nl', prefix: 'nl/', hreflang: 'nl' },
- { code: 'ja', prefix: 'ja/', hreflang: 'ja' },
- { code: 'ko', prefix: 'ko/', hreflang: 'ko' },
- { code: 'zh', prefix: 'zh/', hreflang: 'zh' },
- { code: 'uk', prefix: 'uk/', hreflang: 'uk' },
- { code: 'pt', prefix: 'pt/', hreflang: 'pt' }
-];
-
-const today = new Date().toISOString().split('T')[0];
-
-let xml = `
-`;
-
-// 1. Static Legal pages
-// Imprint
-xml += `
-
- https://sync.koalastuff.net/imprint
- ${today}
- monthly
- 0.3
- `;
-xml += `
-
- https://sync.koalastuff.net/privacy
- ${today}
- monthly
- 0.3
- `;
-xml += `
-
- https://sync.koalastuff.net/de/impressum
- ${today}
- monthly
- 0.3
- `;
-xml += `
-
- https://sync.koalastuff.net/de/datenschutz
- ${today}
- monthly
- 0.3
- `;
-
-// Helper function to build localized urls for a relative path
-function addPage(relativePath, changefreq, priority) {
- for (const lang of languages) {
- const loc = `https://sync.koalastuff.net/${lang.prefix}${relativePath}`;
- xml += `
-
- ${loc}
- ${today}
- ${changefreq}
- ${priority}`;
- for (const alt of languages) {
- const altHref = `https://sync.koalastuff.net/${alt.prefix}${relativePath}`;
- xml += `
- `;
- }
- // Add x-default
- const defaultHref = `https://sync.koalastuff.net/${relativePath}`;
- xml += `
-
- `;
- }
-}
-
-// 2. Landing Pages
-// For landing page, relative path is ''
-addPage('', 'weekly', '1.0');
-
-// 3. Alternatives Hub
-addPage('alternatives', 'weekly', '0.7');
-
-// 4. Alternatives Sub-pages
-const subpages = [
- 'alternatives/teleparty',
- 'alternatives/screen-sharing',
- 'alternatives/watch2gether',
- 'alternatives/scener',
- 'alternatives/kosmi',
- 'alternatives/twoseven'
-];
-for (const sub of subpages) {
- addPage(sub, 'weekly', '0.7');
-}
-
-xml += `
-
-`;
-
-fs.writeFileSync(sitemapPath, xml.trim() + '\n', 'utf8');
-console.log('Successfully generated sitemap.xml!');
diff --git a/website/build.cjs b/website/build.cjs
index 532f79c..e1c087d 100644
--- a/website/build.cjs
+++ b/website/build.cjs
@@ -380,13 +380,16 @@ async function compile() {
}
// ── 5. Copy generic static files and verification files ──
- const genericFiles = ['robots.txt', 'sitemap.xml', 'site.webmanifest', 'version.json', 'llms.txt'];
+ const genericFiles = ['robots.txt', 'site.webmanifest', 'version.json', 'llms.txt'];
for (const file of genericFiles) {
const src = path.join(websiteDir, file);
const dest = path.join(wwwDir, file);
if (fs.existsSync(src)) { fs.copyFileSync(src, dest); }
}
+ // ── 5.5 Generate dynamic sitemap ──
+ generateSitemap(wwwDir, websiteDir);
+
// Auto-copy Google verification files and IndexNow/txt key files from website source to www root
const websiteFiles = fs.readdirSync(websiteDir);
for (const file of websiteFiles) {
@@ -472,4 +475,99 @@ async function compile() {
console.log('KoalaSync build finished successfully! Output: website/www/');
}
+function generateSitemap(wwwDir, websiteDir) {
+ const languages = [
+ { code: 'en', prefix: '', hreflang: 'en' },
+ { code: 'de', prefix: 'de/', hreflang: 'de' },
+ { code: 'fr', prefix: 'fr/', hreflang: 'fr' },
+ { code: 'es', prefix: 'es/', hreflang: 'es' },
+ { code: 'pt-BR', prefix: 'pt-BR/', hreflang: 'pt-br' },
+ { code: 'ru', prefix: 'ru/', hreflang: 'ru' },
+ { code: 'it', prefix: 'it/', hreflang: 'it' },
+ { code: 'pl', prefix: 'pl/', hreflang: 'pl' },
+ { code: 'tr', prefix: 'tr/', hreflang: 'tr' },
+ { code: 'nl', prefix: 'nl/', hreflang: 'nl' },
+ { code: 'ja', prefix: 'ja/', hreflang: 'ja' },
+ { code: 'ko', prefix: 'ko/', hreflang: 'ko' },
+ { code: 'zh', prefix: 'zh/', hreflang: 'zh' },
+ { code: 'uk', prefix: 'uk/', hreflang: 'uk' },
+ { code: 'pt', prefix: 'pt/', hreflang: 'pt' }
+ ];
+
+ const today = new Date().toISOString().split('T')[0];
+
+ let xml = `
+`;
+
+ // Static legal pages
+ xml += `
+
+ https://sync.koalastuff.net/imprint
+ ${today}
+ monthly
+ 0.3
+
+
+ https://sync.koalastuff.net/privacy
+ ${today}
+ monthly
+ 0.3
+
+
+ https://sync.koalastuff.net/de/impressum
+ ${today}
+ monthly
+ 0.3
+
+
+ https://sync.koalastuff.net/de/datenschutz
+ ${today}
+ monthly
+ 0.3
+ `;
+
+ function addPage(relativePath, changefreq, priority) {
+ for (const lang of languages) {
+ const loc = `https://sync.koalastuff.net/${lang.prefix}${relativePath}`;
+ xml += `
+
+ ${loc}
+ ${today}
+ ${changefreq}
+ ${priority}`;
+ for (const alt of languages) {
+ const altHref = `https://sync.koalastuff.net/${alt.prefix}${relativePath}`;
+ xml += `
+ `;
+ }
+ const defaultHref = `https://sync.koalastuff.net/${relativePath}`;
+ xml += `
+
+ `;
+ }
+ }
+
+ addPage('', 'weekly', '1.0');
+ addPage('alternatives', 'weekly', '0.7');
+
+ const subpages = [
+ 'alternatives/teleparty',
+ 'alternatives/screen-sharing',
+ 'alternatives/watch2gether',
+ 'alternatives/scener',
+ 'alternatives/kosmi',
+ 'alternatives/twoseven'
+ ];
+ for (const sub of subpages) {
+ addPage(sub, 'weekly', '0.7');
+ }
+
+ xml += `\n\n`;
+
+ fs.writeFileSync(path.join(websiteDir, 'sitemap.xml'), xml.trim() + '\n', 'utf8');
+ fs.writeFileSync(path.join(wwwDir, 'sitemap.xml'), xml.trim() + '\n', 'utf8');
+ console.log(' ✓ Dynamically generated sitemap.xml with current date');
+}
+
compile().catch(err => { console.error('Build failed:', err); process.exit(1); });