diff options
Diffstat (limited to '')
-rwxr-xr-x | v2/src/bin/absolute | 2 | ||||
-rwxr-xr-x | v2/src/bin/collections | 69 | ||||
-rwxr-xr-x | v2/src/bin/conf (renamed from v2/src/development/genconf.sh) | 42 | ||||
-rwxr-xr-x | v2/src/bin/feed | 91 | ||||
-rwxr-xr-x | v2/src/bin/html (renamed from v2/src/development/genhtml.sh) | 21 | ||||
-rwxr-xr-x | v2/src/bin/lang-for | 73 | ||||
-rwxr-xr-x | v2/src/bin/langs | 69 | ||||
-rwxr-xr-x | v2/src/bin/makemake | 142 | ||||
-rwxr-xr-x | v2/src/bin/security-txt (renamed from v2/src/development/security-txt.sh.in) | 24 | ||||
-rwxr-xr-x | v2/src/bin/url-for | 30 | ||||
-rwxr-xr-x | v2/src/bin/xmlentry | 81 |
11 files changed, 528 insertions, 116 deletions
diff --git a/v2/src/bin/absolute b/v2/src/bin/absolute index 6434219..ecf5a64 100755 --- a/v2/src/bin/absolute +++ b/v2/src/bin/absolute @@ -62,6 +62,6 @@ done shift $((OPTIND - 1)) -. src/lib/base-conf +. src/lib/base.conf printf 'https://%s%s' "$domain" "$(cat)" diff --git a/v2/src/bin/collections b/v2/src/bin/collections new file mode 100755 index 0000000..1df0c39 --- /dev/null +++ b/v2/src/bin/collections @@ -0,0 +1,69 @@ +#!/bin/sh +set -eu + +usage() { + cat <<-'EOF' + Usage: + collections + collections -h + EOF +} + +help() { + cat <<-'EOF' + + + Options: + -h, --help show this message + + + List the registered collections to STDOUT. + + This is done by emiting the content of the "$COLLECTIONS" + environment variable. + + + Examples: + + Just run it: + + $ collections + tils + pastebins + EOF +} + + +for flag in "$@"; do + case "$flag" in + --) + break + ;; + --help) + usage + help + exit + ;; + *) + ;; + esac +done + +while getopts 'h' flag; do + case "$flag" in + h) + usage + help + exit + ;; + *) + usage >&2 + exit 2 + esac +done +shift $((OPTIND - 1)) + + +echo "$COLLECTIONS" | + tr ' ' '\n' | + grep . diff --git a/v2/src/development/genconf.sh b/v2/src/bin/conf index f9dfc14..ac02d98 100755 --- a/v2/src/development/genconf.sh +++ b/v2/src/bin/conf @@ -5,8 +5,8 @@ set -eu usage() { cat <<-'EOF' Usage: - src/development/genconf.sh FILENAME - src/development/genconf.sh -h + conf FILENAME + conf -h EOF } @@ -28,7 +28,7 @@ help() { Get the "frontmatter" of src/f.conf: - $ src/development/genconf.sh src/f.md > src/f.conf + $ conf src/f.md > src/f.conf EOF } @@ -63,7 +63,7 @@ while getopts 'h' flag; do done shift $((OPTIND - 1)) -. src/development/lib.sh +. src/lib.sh FILENAME="${1:-}" eval "$(assert_arg "$FILENAME" 'FILENAME')" @@ -73,7 +73,7 @@ escape() { sed 's|\([`"$]\)|\\\1|g' } -tee "$FILENAME".tmp < src/lib/base-conf +tee "$FILENAME".tmp < src/lib/base.conf DELIMITER=0 while read -r line; do if [ "$line" = '---' ]; then @@ -95,6 +95,11 @@ done < "$FILENAME" | tee -a "$FILENAME".tmp . "$FILENAME".tmp rm -f "$FILENAME".tmp + +lang="$(lang-for "$FILENAME")" +export lang +printf 'export lang="%s"\n' "$lang" + cat src/lib/base."${lang:?}".conf # shellcheck source=/dev/null . src/lib/base."$lang".conf @@ -104,19 +109,30 @@ if [ -z "${title:-}" ]; then fi if [ -n "${date:-}" ]; then - formatted_date="$(LANG="$lang" date -d "${date:?}" +"${date_fmt:?}")" + date_iso="$(date -ud "${date:?}" -Is)" + printf 'export date_iso="%s"\n' "$date_iso" + + formatted_date="$(LANG="$lang" date -ud "${date:?}" +"${date_fmt:?}")" export formatted_date printf 'export date_html="%s"\n' "$(envsubst < src/lib/date."$lang".html | escape)" + + echo "${FILENAME%.md}.xmlentry" > "$(dirname "$FILENAME")/$date_iso.sortdata" + touch "${FILENAME%.md}.sortref" fi if [ -n "${update:-}" ]; then - formatted_update="$(LANG="$lang" date -d "${update:?}" +"${date_fmt:?}")" + update_iso="$(date -ud "${update:?}" -Is)" + printf 'export update_iso="%s"\n' "$update_iso" + + formatted_update="$(LANG="$lang" date -ud "${update:?}" +"${date_fmt:?}")" export formatted_update printf 'export update_html="%s"\n' "$(envsubst < src/lib/update."$lang".html | escape)" + + printf 'export update_xml=" <updated>%s</updated>"\n' "$update_iso" fi -url_part="$(printf '%s' "${FILENAME%.md}.html" | sed 's|^src/content/||')" +url_part="$(printf '%s' "${FILENAME%.md}.html" | sed "s|^$CONTENT_PREFIX||")" title_uri="$(uri "$title")" printf 'export title_html="%s"\n' "$(printf '%s' "$title" | htmlesc | escape)" @@ -127,13 +143,13 @@ printf 'export mailto_uri="%s%s"\n' "${mailto_uri_prefix:?}" "$title_uri" printf 'export discussions_url="%s%s"\n' "${discussions_url_prefix:?}" "$title_uri" printf 'export sourcecode_url="%s%s"\n' "${sourcecode_url_prefix:?}" "$FILENAME" -printf 'export style_url="%s"\n' "$(url-for -g 'style.css')" -printf 'export favicon_url="%s"\n' "$(url-for -g 'favicon.svg')" -printf 'export pubkey_url="%s"\n' "$(url-for -g 'public.asc.txt')" +printf 'export style_url="%s"\n' "$(url-for 'style.css')" +printf 'export favicon_url="%s"\n' "$(url-for 'favicon.svg')" +printf 'export pubkey_url="%s"\n' "$(url-for 'public.asc.txt')" -for f in src/content/img/*.svg; do +for f in "$CONTENT_PREFIX"/img/*.svg; do name="$(basename "$f" .svg | sed 's|-|_|g')" - printf 'export icon_%s_url="%s"\n' "$name" "$(url-for -g "img/$(basename "$f")")" + printf 'export icon_%s_url="%s"\n' "$name" "$(url-for "img/$(basename "$f")")" done # FIXME: special treatment of root diff --git a/v2/src/bin/feed b/v2/src/bin/feed new file mode 100755 index 0000000..96c40a6 --- /dev/null +++ b/v2/src/bin/feed @@ -0,0 +1,91 @@ +#!/bin/sh +set -eu + +usage() { + cat <<-'EOF' + Usage: + feed FILENAME + feed -h + EOF +} + +help() { + cat <<-'EOF' + + + Options: + -h, --help show this message + + FILENAME the target feed to be generated + + + Generate FILENAME as an Atom feed. The collection type and + language are inferred by the name of FILENAME. + + + Examples: + + Generate a feed for TILs: + + $ feed src/en/feeds/til.xml + EOF +} + + +for flag in "$@"; do + case "$flag" in + --) + break + ;; + --help) + usage + help + exit + ;; + *) + ;; + esac +done + +while getopts 'h' flag; do + case "$flag" in + h) + usage + help + exit + ;; + *) + usage >&2 + exit 2 + ;; + esac +done +shift $((OPTIND - 1)) + +. src/lib.sh + +FILENAME="${1:-}" +eval "$(assert_arg "$FILENAME" 'FILENAME')" + + +COLLECTION="$(basename "$FILENAME" '.xml')" +LANGUAGE="$(lang-for "$FILENAME")" +DIR="$(dirname "$(dirname "$FILENAME")")/$COLLECTION" + + +. src/lib/base.conf +# shellcheck source=/dev/null +. src/lib/base."$LANGUAGE".conf + +now="$(date -uIs)" +url="$(url-for "${FILENAME#"$CONTENT_PREFIX"}" | absolute)" +site_name_html="$(htmlesc "${site_name:?}")" +export now url site_name_html + + +mkdir -p "$(dirname "$FILENAME")" +{ + envsubst < src/lib/feed.xml + find "$DIR"/*.sortdata | sort -nr | xargs cat | xargs cat + printf '</feed>\n' +} > "$FILENAME" diff --git a/v2/src/development/genhtml.sh b/v2/src/bin/html index 1b2718a..7e6809c 100755 --- a/v2/src/development/genhtml.sh +++ b/v2/src/bin/html @@ -4,34 +4,29 @@ set -eu usage() { cat <<-'EOF' Usage: - genhtml.sh FILENAME - genhtml.sh -h + html FILENAME + html -h EOF } help() { cat <<-'EOF' + Options: -h, --help show this message - FILENAME the name of the input file, to also be used as - URL + FILENAME the name of the input file .md file Process the FILENAME, and generate a full HTML page. - The FILENAME is used to infer the output URL, by removing the - `src/content/` prefix, and replacing the trailing `.md` with - `.html`. This URL is used to build the self-referencing - "canonical" link, extracting plaintext snippets, etc. - Examples: Generate the HTML for a pastebin: - $ sh genhtml.sh src/content/a-paste.md > src/content/a-paste.html + $ html src/a-paste.md > src/a-paste.html EOF } @@ -66,7 +61,7 @@ while getopts 'h' flag; do done shift $((OPTIND - 1)) -. src/development/lib.sh +. src/lib.sh FILENAME="${1:-}" eval "$(assert_arg "$FILENAME" 'FILENAME')" @@ -118,7 +113,7 @@ markdown_to_html() { extract_plaintext_snippets() { SNIPPETS="${FILENAME%.md}.snippets" - rm -f "$SNIPPETS" + printf '' > "$SNIPPETS" F="$(mkstemp)" cat > "$F" ( @@ -220,5 +215,5 @@ emit_body() { } envsubst < src/lib/preamble.html -emit_body +emit_body | tee "${FILENAME%.md}.htmlbody" envsubst < src/lib/postamble.html diff --git a/v2/src/bin/lang-for b/v2/src/bin/lang-for new file mode 100755 index 0000000..f7c57a9 --- /dev/null +++ b/v2/src/bin/lang-for @@ -0,0 +1,73 @@ +#!/bin/sh +set -eu + +usage() { + cat <<-'EOF' + Usage: + lang-for FILE + lang-for -h + EOF +} + +help() { + cat <<-'EOF' + + + Options: + -h, --help show this message + + FILE the path of the file to get the language for + + + Say the language of the given file, using the path of FILE. + + + Examples: + + Get "en" for "src/en/some-pt.md": + + $ lang-for src/en/some-pt.md + en + EOF +} + + +for flag in "$@"; do + case "$flag" in + --) + break + ;; + --help) + usage + help + exit + ;; + *) + ;; + esac +done + +while getopts 'h' flag; do + case "$flag" in + h) + usage + help + exit + ;; + *) + usage >&2 + exit 2 + ;; + esac +done +shift $((OPTIND - 1)) + +. src/lib.sh + + +FILE="${1:-}" +eval "$(assert_arg "$FILE" 'FILE')" + + +echo "${FILE#"$CONTENT_PREFIX"/}" | + cut -d/ -f1 diff --git a/v2/src/bin/langs b/v2/src/bin/langs new file mode 100755 index 0000000..8e8aa63 --- /dev/null +++ b/v2/src/bin/langs @@ -0,0 +1,69 @@ +#!/bin/sh +set -eu + +usage() { + cat <<-'EOF' + Usage: + langs + langs -h + EOF +} + +help() { + cat <<-'EOF' + + + Options: + -h, --help show this message + + + List the supported languages, including english, to STDOUT. + + This is done in the same way that po4a(1) does it: by listing + the po/*.po files, and getting the name from it. + + + Examples: + + Just run it: + + $ langs + en + pt + EOF +} + + +for flag in "$@"; do + case "$flag" in + --) + break + ;; + --help) + usage + help + exit + ;; + *) + ;; + esac +done + +while getopts 'h' flag; do + case "$flag" in + h) + usage + help + exit + ;; + *) + usage >&2 + exit 2 + esac +done +shift $((OPTIND - 1)) + + +echo po/en.po po/*.po | + tr ' ' '\n' | + sed 's|^po/\(.*\)\.po$|\1|' diff --git a/v2/src/bin/makemake b/v2/src/bin/makemake index e95a040..fdd0e68 100755 --- a/v2/src/bin/makemake +++ b/v2/src/bin/makemake @@ -64,84 +64,110 @@ varlist() { printf '\n' } -html_deps() { - "$@" | sed 's/^\(.*\)\.md$/\1.conf \1.content: \1.md/' - "$@" | sed 's/^\(.*\)\.md$/\1.snippets \1.html: \1.conf \1.content/' - printf '\n' -} - - -content_mds() { - { - if [ "$r" = 'pages' ]; then - echo src/content/*.md - else - echo src/content/"$r"/*.md - fi - } | tr ' ' '\n' -} - -RESOURCES=' -pages -pastebins -tils -' EXTENSIONS=' -.md .conf .content .html .snippets +.htmlbody ' -for r in $RESOURCES; do - content_mds "$r" | varlist "$r".md - for e in $EXTENSIONS; do - if [ "$e" = '.md' ]; then - continue +COLL_EXTENSIONS=' +.sortref +.xmlentry +' + +page_ext_filter="^($(echo "$COLL_EXTENSIONS" | + tr ' ' '\n' | + grep . | + paste -sd'|' +))\$" + + +extensions() { + echo "$EXTENSIONS" "$COLL_EXTENSIONS" "$@" | + tr ' ' '\n' | + grep . +} + + +printf '.POSIX:\n\n\n' +for lang in $(langs); do + for c in pages $(collections); do + if [ "$c" = 'pages' ]; then + filter="$page_ext_filter" + dir="$CONTENT_PREFIX/$lang" + else + filter='^$' + dir="$CONTENT_PREFIX/$lang/$c" fi - # shellcheck disable=2016 - printf '%s%s = $(%s.md:.md=%s)\n' "$r" "$e" "$r" "$e" - done - printf '%s =' "$r" - for e in $EXTENSIONS; do - if [ "$e" = '.md' ]; then + + mds() { + # find "$dir"/*.md # FIXME + find "$dir"/*.md 2>/dev/null + } + + exts() { + extensions | grep -Ev "$filter" + } + + mds | varlist "$c.$lang.md" + exts | sed "s|^\(.*\)\$|$c.$lang\1 = \$($c.$lang.md:.md=\1)|" + exts | sed "s|^\(.*\)\$|\$($c.$lang\1)|" | varlist "$c.$lang" + + mds | sed 's/^\(.*\)\.md$/\1.conf \1.content: \1.md/' + mds | sed 's/^\(.*\)\.md$/\1.snippets \1.htmlbody \1.html: \1.conf \1.content/' + if [ "$c" = 'pages' ]; then continue fi - # shellcheck disable=2016 - printf ' $(%s%s)' "$r" "$e" + + mds | sed 's/^\(.*\)\.md$/\1.sortref: \1.md/' + mds | sed 's/^\(.*\)\.md$/\1.xmlentry: \1.html/' + + echo "$CONTENT_PREFIX/$lang/feeds/$c.xml: \$($c.$lang.xmlentry)" + + printf '\n\n' done - printf '\n' - html_deps content_mds "$r" - printf '\n' -done + for e in $(extensions); do + { + if ! printf '%s\n' "$e" | grep -qE "$page_ext_filter"; then + echo pages + fi + collections + } | + sed "s|^\(.*\)\$|\$(\1.$lang$e)|" | + varlist "all-generated.$lang$e" + done -all_resources() { - echo "$RESOURCES" | tr ' ' '\n' | grep . -} + collections | + sed "s|^\(.*\)\$|$CONTENT_PREFIX/$lang/feeds/\1.xml|" | + varlist "all-generated.$lang.xml" -all_vars() { - EXT="$1" - # shellcheck disable=2016 - all_resources | - sed 's|^|$(|' | - sed "s|$|$EXT)|" | - varlist all-generated"$EXT" -} + extensions '.xml' | + sed "s|^\(.*\)\$|\$(all-generated.$lang\1)|" | + varlist "all-generated.$lang" -for e in $EXTENSIONS; do - all_vars "$e" + printf '\n' +done + +for e in $(extensions .xml); do + langs | + sed "s|^\(.*\)\$|\$(all-generated.\1$e)|" | + varlist "all-generated$e" done -all_vars '' + +# shellcheck disable=2016 +langs | + sed 's|^\(.*\)$|$(all-generated.\1)|' | + varlist 'all-generated' -git ls-files | - grep -v '^src/content/' | +git ls-files src/ | + grep -v ^"$CONTENT_PREFIX"/ | varlist 'non-content' -git ls-files src/content/ | +git ls-files "$CONTENT_PREFIX"/ | grep -v '\.md$' | - grep -Ev "src/content/($(all_resources | paste -sd'|'))/" | varlist 'static-content' diff --git a/v2/src/development/security-txt.sh.in b/v2/src/bin/security-txt index 8f6613f..7026969 100755 --- a/v2/src/development/security-txt.sh.in +++ b/v2/src/bin/security-txt @@ -4,8 +4,8 @@ set -eu usage() { cat <<-'EOF' Usage: - src/development/security-txt.sh - src/development/security-txt.sh -h + security-txt + security-txt -h EOF } @@ -25,7 +25,7 @@ help() { Just run it: - $ sh src/development/security-txt.sh > .well-known/security.txt + $ security-txt > .well-known/security.txt EOF } @@ -62,21 +62,21 @@ shift $((OPTIND - 1)) EXPIRES="$( - LANG=C.UTF-8 gpg --list-key eu@euandre.org | + LANG=C.UTF-8 gpg --list-key "$EMAIL" | awk '/^pub/ { print substr($(NF), 1, 10) }' )T00:00:00z" -LANGS="en$( - echo po/??.po | - sed 's|\.po$||' | - sed 's|^po/|, |' | - paste -sd, +LANGUAGES="$( + langs | + sed 's|^|, |' | + tr -d '\n' | + sed 's|^, ||' )" cat <<-EOF - Contact: mailto:@EMAIL@ - Encryption: https://@DOMAIN@/public.asc.txt + Contact: mailto:$EMAIL + Encryption: $(url-for 'public.asc.txt' | absolute) Expires: $EXPIRES - Preferred-Languages: $LANGS + Preferred-Languages: $LANGUAGES EOF diff --git a/v2/src/bin/url-for b/v2/src/bin/url-for index d4099bc..adaccd7 100755 --- a/v2/src/bin/url-for +++ b/v2/src/bin/url-for @@ -4,7 +4,7 @@ set -eu usage() { cat <<-'EOF' Usage: - url-for [-g] FILE + url-for FILE url-for -h EOF } @@ -13,7 +13,6 @@ help() { cat <<-'EOF' Options: - -g global file, not specific to a single language -h, --help show this message FILE the path for the URL to be constructed @@ -25,7 +24,7 @@ help() { Examples: - Get the URL for "about.html", when $base_url is "v2" and $lang is "en": + Get the URL for "en/about.html", when $base_url is "v2": $ url-for 'about.html' /v2/en/about.html @@ -33,8 +32,8 @@ help() { Get the URL for "static/favicon.svg", when $base_url is empty: - $ url-for -g 'static/favicon.svg' - /static/favicon.svg + $ url-for 'img/link.svg' + /img/link.svg EOF } @@ -54,12 +53,8 @@ for flag in "$@"; do esac done -GLOBAL=false -while getopts 'gh' flag; do +while getopts 'h' flag; do case "$flag" in - g) - GLOBAL=true - ;; h) usage help @@ -73,22 +68,19 @@ while getopts 'gh' flag; do done shift $((OPTIND - 1)) -. src/development/lib.sh - +. src/lib.sh FILE="${1:-}" +eval "$(assert_arg "$FILE" 'FILE')" + + if [ "$FILE" = '/' ]; then FILE='' fi -. src/lib/base-conf +. src/lib/base.conf # shellcheck source=/dev/null . src/lib/base."${lang:?}".conf -if [ "$GLOBAL" = true ]; then - L='' -else - L="${lang:?}/" -fi -printf '%s%s%s' "${base_url:-/}" "$L" "$FILE" +printf '%s%s' "${base_url:-/}" "$FILE" diff --git a/v2/src/bin/xmlentry b/v2/src/bin/xmlentry new file mode 100755 index 0000000..b0760ae --- /dev/null +++ b/v2/src/bin/xmlentry @@ -0,0 +1,81 @@ +#!/bin/sh +set -eu + +usage() { + cat <<-'EOF' + Usage: + xmlentry FILENAME + xmlentry -h + EOF +} + +help() { + cat <<-'EOF' + + + Options: + -h, --help show this message + + FILENAME the name of the input .md file + + + Process FILE, and generate an Atom feed entry. + + + Examples: + + Generate the XML entry for a TIL: + + $ xmlentry src/tils/a-til.md > src/tils/a-til.xml + EOF +} + + +for flag in "$@"; do + case "$flag" in + --) + break + ;; + --help) + usage + help + exit + ;; + *) + ;; + esac +done + +while getopts 'h' flag; do + case "$flag" in + h) + usage + help + exit + ;; + *) + usage >&2 + exit 2 + ;; + esac +done +shift $((OPTIND - 1)) + +. src/lib.sh + +FILENAME="${1:-}" +eval "$(assert_arg "$FILENAME" 'FILENAME')" + + +# shellcheck source=/dev/null +. "${FILENAME%.md}.conf" + +envsubst < src/lib/entry.xml + +head -n1 < "${FILENAME%.md}.htmlbody" | htmlesc +printf ' </summary>\n' +printf ' <content type="html" xml:base="%s">\n' "${url:?}" + +htmlesc < "${FILENAME%.md}.htmlbody" +printf ' </content>\n' +printf ' </entry>\n' |