#!/bin/sh set -eu export LANG=POSIX.UTF-8 normalize() { xargs realpath --relative-to=. | sort } ## A language's front page is excluded: it is a listing now, and ## naming it here as well puts it in $(sources.adoc) twice. pages() { find src/pages/*/*.adoc -type f ! -name 'index.adoc' | normalize } ## The front page of each language, which lists what is newest ## across that language's collections rather than holding articles ## of its own. homes() { find src/pages/*/index.adoc -type f | normalize } articles() { find src/collections/*/*/*/ -type f -name '*.adoc' | normalize } slides() { find src/slides/*/*/ -type f -name '*.eslaides' | normalize } indexes() { find src/collections/*/*/index.adoc | normalize } categories() { grep -l '^:type: categories$' src/collections/*/*/*.adoc | normalize } media() { # src/content/music is excluded: those .ogg files are score # renderings, not published media, and the old site never # offered them over BitTorrent. find src/content/ -path 'src/content/music' -prune -or \ \( \( -type f -and \! -type l \) -and \( \ -name '*.flac' -or \ -name '*.ogg' -or \ -name '*.webm' \ \) -print \) } music() { find src/content/music/*.ly | normalize } tarballs() { find src/content/ \( -type f -and \! -type l \) -and \( \ -name '*.tar.gz' \ \) } extras() { media tarballs } listings() { indexes categories homes } ## Which pages are one another's translations. po4a already says ## so, set by set, so read it there rather than keep a second list ## that can quietly disagree with the first. po4a_sets() { awk ' /^\[type: asciidoc\]/ { set = "" } /^\[type: asciidoc\]/ || cont { line = $0 sub(/^\[type: asciidoc\][ \t]*/, "", line) cont = (line ~ /\\$/) sub(/[ \t]*\\$/, "", line) n = split(line, f, /[ \t]+/) for (i = 1; i <= n; i++) { if (f[i] == "" || f[i] ~ /^add_/) continue sub(/^[a-z]+:/, "", f[i]) set = set (set == "" ? "" : " ") f[i] } if (!cont && set != "") { print set; set = "" } } ' po/po4a.cfg } files() { pages articles listings } pages | varlist 'pages.adoc' homes | varlist 'homes.adoc' articles | varlist 'articles.adoc' slides | varlist 'slides.eslaides' categories | varlist 'categories.adoc' indexes | varlist 'indexes.adoc' indexes | sed 's|/index\.adoc$|/feed.xml|' | varlist 'feeds.xml' find src/content/img/ -name '*.svg' | sort | varlist 'images.svg' media | varlist 'sources.media' tarballs | varlist 'sources.tarballs' extras | varlist 'sources.extras' find po/*.po po/*.pot | varlist 'sources.po' music | varlist 'music.ly' find src/content/music/*.ogg | varlist 'music.ogg' find src/content/music/*.ly.include | varlist 'music.include' # lilypond emits the score alongside the MIDI, from one run. music | sed 's/^\(.*\)\.ly$/\1.pdf:\t\1.midi/' files | sed 's/^\(.*\)\.adoc$/\1.htmlbody\t\1.snippets\t\1.json:\t\1.adoc/' files | sed 's/^\(.*\)\.adoc$/\1.html:\t\1.json\t\1.htmlbody/' printf '\n' files | sed 's/^\(.*\)\.adoc$/\1.updatedat-check:\t\1.json/' files | sed 's/^\(.*\)\.adoc$/\1.links-internal-check:\t\1.links/' files | sed 's/^\(.*\)\.adoc$/\1.caslinks:\t\1.links/' printf '\n' articles | sed 's/^\(.*\)\.adoc$/\1.feedentry:\t\1.json\t\1.htmlbody/' articles | sed 's/^\(.*\)\.adoc$/\1.sortdata:\t\1.json/' articles | sed 's/^\(.*\)\.adoc$/\1.categorydata:\t\1.json/' printf '\n' listings | sed 's/^\(.*\)\.adoc$/\1.htmlheader\t\1.htmlfooter:\t\1.json/' listings | sed 's/^\(.*\)\.adoc$/\1.htmllisting:\t\1.json/' listings | sed 's/^\(.*\)\.adoc$/\1.html:\t\1.htmlheader\t\1.htmlfooter/' listings | sed 's/^\(.*\)\.adoc$/\1.html:\t\1.htmllisting\t\1.htmlbody/' printf '\n' media | sed 's/^\(.*\)$/\1.torrent:\t\1/' printf '\n' slides | sed 's/^\(.*\)\.eslaides$/\1.ps:\t\1.eslaides/' slides | sed 's/^\(.*\)\.eslaides$/\1.pdf:\t\1.ps/' printf '\n' collectionentries() { langlink="$1" colllink="$2" lang="$(basename "$langlink")" c="$(printf '%s' "$colllink" | normalize)" plural="$(cat src/names/categories/"$lang".txt)" printf '\n\n' name="$(basename "$c")" art=articles."$lang" # A collection with no articles yet -- every non-English one -- # has no YYYY/ directories for the glob to match. find "$c"/*/ -type f -name '*.adoc' 2>/dev/null | varlist "$art.$name.adoc" echo "$art.$name.sortdata = \$($art.$name.adoc:.adoc=.sortdata)" echo "$art.$name.indexentry = \$($art.$name.adoc:.adoc=.indexentry)" echo "$art.$name.feedentry = \$($art.$name.adoc:.adoc=.feedentry)" echo "$art.$name.categorydata = \$($art.$name.adoc:.adoc=.categorydata)" echo "$art.$name.homeentry = \$($art.$name.adoc:.adoc=.homeentry)" printf '%s/sortdata.txt:\tdeps.mk\n' "$c" printf '\tprintf %s $(%s.%s.sortdata) > $@\n\n' "'%s\n'" "$art" "$name" listings=" feed.xml index.htmllisting $plural.htmllisting $plural.txt " for lst in $listings; do printf '%s/%s:\t%s/sortdata.txt\n' "$c" "$lst" "$c" printf '%s/%s:\t$(%s.%s.sortdata)\n' "$c" "$lst" "$art" "$name" done printf '%s/index.htmllisting\t' "$c" printf '%s/%s.htmllisting:\t' "$c" "$plural" printf '$(%s.%s.indexentry)\n' "$art" "$name" printf '%s/%s.txt:\t' "$c" "$plural" printf '$(%s.%s.categorydata)\n' "$art" "$name" printf '%s/%s.txt\t' "$c" "$plural" printf '%s/feed.xml:\t' "$c" printf '$(%s.%s.feedentry)\n' "$art" "$name" printf '%s/%s.htmllisting\t' "$c" "$plural" printf '%s/%s.xml:\t' "$c" "$plural" printf '%s/%s.txt\n' "$c" "$plural" } for langlink in src/collections/*; do for colllink in "$langlink"/*; do collectionentries "$langlink" "$colllink" done done ## A front page lists each collection, so it is rebuilt when any ## of that language's collections gains an entry. printf '\n' for langlink in src/collections/*; do lang="$(basename "$langlink")" deps= for colllink in "$langlink"/*; do [ -d "$colllink" ] || continue name="$(basename "$colllink")" deps="$deps src/content/$lang/$name/sortdata.txt" deps="$deps \$(articles.$lang.$name.homeentry)" done [ -n "$deps" ] || continue printf 'src/content/%s/index.htmllisting:%s\n\n' "$lang" "$deps" done ## The map mkwb conf reads to link a page to its translations, ## written out here so it cannot drift from po4a.cfg. printf '\ntranslations.map = src/translations.map\n\n' printf 'src/translations.map: deps.mk\n' printf '\tprintf %s \\\n' "'%s\\n'" po4a_sets | sed "s/^/\t\t'/; s/\$/' \\\\/" printf '\t\t> $@\n\n' ## The canonical rules, inlined so no include is needed ## at make time. echo mkwb rules