Gemini Text Format nach HTML umwandeln

➤ Martin Döring 13. Februar 2021

Einführung

Für meinen Blog herrdoering.de habe ich bisher Hugo als Werkzeug verwendet, um aus Markdown-Dateien HTML zu machen. Gewünscht hätte ich mir eigentlich einen Webserver, der diesen Übersetzungsprozess überflüssig macht, also am besten einen Webbrowser haben, der direkt Markdown versteht.

Sowas Ähnliches gibt es jetzt mit dem Gemini-Textformat und dem dazu passenden Browser Lagrange:

🌐 Lagrange desktop GUI client for browsing Geminispace
🌐 Wikipedia-Eintrag zum Geminispace
🌐 Awesome Gemini Informationssammlung (Englisch)

Gemini als Basis-Format

Da die Artikel, die ich schreibe, in der Regel sowieso kaum Bilder enthalten, habe ich mich nun entschlossen, meinen Blog auf das Gemini-Format umzustellen und dann, solange es das normale Web noch gibt, HTML-Seiten daraus zu generieren.

Auf der Suche nach einem passenden Konverter, bin ich auf die Webseite von Omar gestoßen, der für diesen Zweck ein kleines Awk-Programm geschrieben hat. Auf seiner Seite ist auch ein ähnliches Programm von dracometallium referenziert:

🌐 Omars Übersetzer
🌐 dracometallicums gmi2html.awk

Ich habe mir aus beiden Programmen jetzt etwas zusammengebaut, das für mich funktioniert und ebenso einen Wrapper als Shell-Script dazu entwickelt.

Funktionsweise

Der funktioniert so, dass man in das Verzeichnis hinein geht, welches die Gemini-Textdateien enthält und der Wrapper erzeugt dann ein Ausgabeverzeichnis eine Ebene darüber namens html, welches die erzeugten HTML-Seiten enthält, die auch untereinander verlinkt sind. Dass ich das letzte Mal etwas mit Awk gemacht habe, ist gute 20 Jahre her. Es gibt also sicher noch Verbesserungsmöglichkeiten.

Shell-Script namens gmi2html

#!/bin/bash

htmldir="../html"

for file in `find . -type f -name "*.gmi"`
do
   barefile=`basename -s .gmi $file`
   outfile="$htmldir/$file"
   outdir=`dirname $outfile`
   mkdir -p $outdir
   outfile="$outdir/$barefile.html"

   title=$(cat $file|grep -m 1 '^# '|sed 's/#//'|awk '{$1=$1;print}')
   gem2html.awk $file | sed "s/TITLEEE/$title/" > $outfile
done

Omars angepasster gmi2html.awk Konverter vom Gemini-Textformat nach HTML

#!/usr/bin/awk -f

BEGIN {
    print "<!DOCTYPE html>"
    print "<html>"
    print "<head>"
    print "    <meta charset=\"utf-8\">"
    print "    <meta name=\"referrer\" content=\"no-referrer\">"
    print "    <style>"
    print "        body{margin: auto; padding: 1em; max-width:40em; font-size: 150%;font-family: sans-serif;}"
    print "        pre {white-space:pre-wrap; background-color:#eee; margin-top:1em; margin-bottom:0; padding:0.5em; }"
    print "        hr  {color:#eee; background-color:#eee; border:#eee; height:4px; }"
    print "    </style>"
    print "    <title>TITLEEE</title>"
    print "</head>"
    print "<body>"

    in_pre = 0;
    in_list = 0;
}

!in_pre && /^```/ {
    in_pre = 1;
    if (in_list) {
       in_list = 0;
       print("</ul>");
    }
    print "<pre>";
    next
}
in_pre && /^```/    { in_pre = 0; print "</pre>"; next }
in_pre       { print san($0); next }

/^###/  { output("<h3>", substr($0, 4), "</h3>"); next }
/^##/   { output("<h2>", substr($0, 3), "</h2>"); next }
/^#/    { output("<h1>", substr($0, 2), "</h1>"); next }
/^>/    { output("<blockquote>", substr($0, 2), "</blockquote>"); next }
/^\*/   { output("<li>", substr($0, 2), "</li>"); next }
/^=>/   {
    $0 = substr($0, 3);
    link = $1;
    $1 = "";
    output_link(link, $0);
    next;
}
//  { output("<p>", $0, "</p>"); next }

END {
    if (in_list)
       print "</ul>"
    if (in_pre)
       print "</pre>"
    print "</body>\n</html>"
}

function trim(s) {
    sub("^[ \t]*", "", s);
    return s;
}

function san(s) {
    gsub("&", "\\&amp;", s)
    gsub("<", "\\&lt;", s)
    gsub(">", "\\&gt;", s)
    return s;
}

function output(ot, content, ct) {
    content = trim(content);

    if (!in_list && ot == "<li>") {
       in_list = 1;
       print "<ul>";
    }

    if (in_list && ot != "<li>") {
       in_list = 0;
       print "</ul>";
    }

    if (ot == "<p>" && content == "")
       return;

    printf("%s%s%s\n", ot, san(content), ct);
}

function output_link(link, content) {
    if (in_list) {
       in_list = 0;
       print "</ul>";
    }

   # If it's a local gemini file, link to the html:
    if((link !~ /^[a-zA-Z]*:\/\//) && (link ~ /\.gmi$/)){
        sub(/\.gmi$/, ".html", link)
    }


    if (content == "")
       content = link;

    printf("&#x2BA9; <a href=\"%s\">%s</a><br>\n", link, trim(san(content)));
}

Bis ich meinen gesamten Blog umgestellt habe, wird es sicher noch eine Weile dauern. Was mir auch noch fehlt sind Stichwörter und Kategorisierungen. Das macht Hugo natürlich toll.

🌐 Die Scripts sind unter der MIT-Lizenz lizenziert.

➤ Zurück
➤ Datenschutzinformation