Skip to content
Snippets Groups Projects

Header

Wie unsere Website tickt.

Die Chaotikum Website ist weit mehr als nur ein mit Jekyll betriebener Blog. So hat sie mal angefangen, aber inzwischen ist sie ein Bindeglied in verschiedenen Bereichen der Infrastruktur des Vereins. Man könnte sagen, ist das nicht zu viel? Ist eine Website wirklich immer das richtige Tool? Insbesondere eine statische? Vermutlich ist die Frage berechtigt.

Aber wie so häugfig nimmt man die Software die man gerade hat um Probleme zu lösen, und wir hatten diese Software.

Statischer Content - Semi-Dynamisch

Der Takt der Chaotikum Website ist ein Build alle 30 Minuten.

Die Chaotikum Website wird regelmäßig alle 30 Minuten gebaut. Egal ob sich was ändert oder nicht. Dafür gibt es einen Pipeline-Schedule

* /30 * * * *

Der Grund ist denkbar einfach: Release Zeiten für Blog-Posts oder Videos können für die Zukunft eingetragen werden. Sobald der Zeitpunkt überschritten ist, werden die Posts auftomatisiert öffentlich. Danach grreifen entsprechende Automatismen, z.B. durch das RSS Tröts im Fediverse usw...

Eine Sammlung von Sammlungen

Um unsere Website zu verstehen, hilft es sich grundsätzlich damit beschäftigt zu haben, wie Static Site Generators üblicherweise arbeiten. Da gibt es natürlich viel varianz, aber sehr, sehr häufig entsteht ein Blog indem man haufenweise Markdown dateien in einen Ordner wirft und ein paar Templates, wie diese dargestellt werden sollten.

So auch bei uns. Die Posts des Blogs finden sich im Ordner _posts.

Bei vielen Websites ist da mehr oder weniger Schluss. Nicht bei der Chaotikum Website. Wer sich die Datei-Struktur dieses Jekyll-Projekts ansieht bemerkt allerdingsn, die große Menge an weiteren Ordnern, welche alle mit einem Unterstrich beginnen.

_briefing
_categories
_conferencefrab
_conferences
_events
_imagemeta
_includes
_inventory
_layouts
_loan
_loancal
_media
_people
_plugins
_posts
_press
_projects
_sass
_sets
_site
_sponsors

Bis auf wenige ausnahmen finden sich darin viele Markdown-Dateien. Es handelt sich um Sammlungen (Jekyll Collections). Die Ausnahmen sind _includes und _layouts (darin befinden sich die html Templates zur Darstellung der Website), _plugins (Jekyll Plugins), _sass (CSS für die Seite), _site (In dem ordner befindet sich die gebaute Seite).

Alle anderen Ordner repräsentieren Inhalte (Content) der Website in Form von Collections, welche miteinander interagieren. Und große Menge an solchen miteinander interagierenden Sammlungen ist, was das Projekt komplex macht.

Wer einfach nur einen neuen Blogpost schreiben möchte, oder die Beschreibung eines Geräts oder Projektes verbessern will, der wird damit auch meist nicht in Berüfung kommen. Wer aber Templates verbessern will oder neue Logik einbauen möchte, muss sich damit beschäftigen.

Im Folgenden wird ein Überblick über einige Grundgedanken und Wiederkehrenden Elemente gegeben, danach auf andere Kapitel der Doku verwiesen.

UID für (so ziemlich) alles

Fast jedes Element in fast jeder Samlung erhält eine UID im Frontmatter Teil der Markdown-Datei. Dieses wird üblicherweise genutzt, um das Element zu referenzieren. Weil es deswegen wichtig ist, dass jede UID tatsächlich Unique ist, haben wir ein Skript in der Build-Pipeline, die das prüft.

Für alle Elementen in _events, _inventory, _loan, und _media gilt, dass sie über eine (innerhalb der Seite) eindeutige UID verfügen müssen. Sie wird verwendet, um die Inhalte miteinander zu verknüfen.

Wenn z.B. folgende Datei im ordner loan angelegt wird:

---
layout: loan
title:  "Verleih"
eventdate:   2024-02-13 00:00:00 +0200
eventend:    2024-02-14 23:59:59 +0200
#https://www.uuidgenerator.net/
uid: 466cbac6-1706-4f7d-add3-501037b1bed8
contact: verleih@chaotikum.org
devices:
 - ed7a8302-34af-429f-9736-86740a03962a
short: "Ausgeliehen"
---

So referenziert sie eindeutig das Objekt ed7a8302-34af-429f-9736-86740a03962a im Invantar:

---
layout: device
name: "ROEDE Mikrofone (Koffer Blau)"
#https://www.uuidgenerator.net/
uid: ed7a8302-34af-429f-9736-86740a03962a
wikilink: https://wiki.chaotikum.org/hackspace:equipment:rode_wireless_go_1
calcolor: "#322ce8"
sets: 
 - video
 - leihbar
 - kofferblau
---

ROEDE Mikrofone (Koffer Blau)

als entliehen.

Manchmal verknüft die Website Dinge allerdings auch mit lesbaren IDs oder Tags. Das ist zwar inkonsitent, aber eben lesbar. Diese Ausnahmen sind:

Relevante Ausnahmen

  • Personen (_people) haben keine UID sondern eine person_id welche einem selbst gewählten Nickname entspricht.
  • Aktivitäten (_projects) werden über ihr tag referenziert
  • Konferenzen (_conferences) haben eine acronym
  • Sets (_sets) existieren primär, um Gruppen von Geräten mit einem merkbaren Namen zu referenzieren, und haben daher ein tag anstelle eienr uid

Wie stellt sich das im Code dar

Angenommen, wir haben ein Decive im Inventar, welches durch feolgende Markdown Datei im ordner _inventory repräsentiert wird:

---
layout: device
name: "Bohr- und Fräsmaschine: KF 16 L Vario Bernardo"
#https://www.uuidgenerator.net/
uid: 10992f1f-fb14-491f-9e68-6b1b84154674
safetybriefing: true
wikilink: ""
calcolor: "#96aa3d"
imagetag: freaesebernardo
contact:
 - p1
 - p2
sets: 
 - werkstatt
 - holzundmetal
hints:
 - "Nutzung nur nach Einweisung bzw. Überprüfung deiner Kenntnisse"
 - "Gefahr durch rotierende Teile sowie Quetschungen."
 - "Niemals unbeaufsichtigt laufen lassen."
commandsigns:
 - M002
 - M003
 - M004
 - M016
---

So sind hier also Zwei Kontaktpersonen (_people) mit ihrer person_id angegeben. Wenn wir diese aber im Template anzeigen wollen, ist das nicht hilfreich. Daher finden sich im Liquid häufig kleine Schleifen, um die korrekten personen zu finden:

{% if page.contact -%}
	Ansprechpersonen:
    <div class="toolcontact" id="toolcontact">
    	<ul>
	        {% for con in page.contact -%}
	        	<li>{% include entity.html -%}</li>
	        {% endfor -%}
        </ul>
    </div>
{% endif -%}

(Aus _layouts/device.html)

sowie

{% assign found =  '' -%}
{% for person in site.people -%}
	{% if person.person_id == con -%}
		{% assign found =  person.name -%}
		{{person.name}}
		{% if person.email and person.email != '' -%}
			<a class="personlink" href="mailto:{{person.email}}"><span class="fa fa-envelope"></span></a>
      	{% endif -%}
      	{% if person.web and person.web != '' -%}
        	<a class="personlink" href="{{ person.web }}"><span class="fa fa-globe"></span></a>
      	{% endif %}
      	{% if person.mastodon and person.mastodon != '' -%}
        	<a class="personlink" href="{{ person.mastodon }}"><span class="fa fa-brands fa-mastodon"></span></a>
      	{% endif -%}
      	{% if person.matrix and person.matrix != '' -%}
	        <a class="navlink" href="{{ person.matrix }}"><span class="fa fa-matrix-org"></span></a>
	    {% endif -%}
      	{% if person.gitlab and person.gitlab != '' -%}
        	<a class="navlink" href="{{ person.gitlab }}"><span class="fa fa-brands fa-gitlab"></span></a>
      	{% endif %}
	{% endif -%}
{% endfor -%}
{% if found == nil or found == '' -%}
	{{con}}
{% endif -%}

(Aus _includes/entity.html)

In entity.html gehen wir also für jede person_id in der Variable con durch alle personen (_people) und schreiben Namen und Kontakdetails raus, sobald die korrekte Person gefunden wurde. Das ist teuer. Bei größeren Collections lohnt sich daher häufig eine Where-Syntax (eigentlich lohnt die sich immer, aber genutzt wird sie nicht immer.)

Where Syntax

Eine Where-Syntax ist in liquid etwas anstrengend, hier sind ein paar beispiele:

{% assign relevant_tools = site.inventory | where_exp: "rtools", "rtools.sets contains 'werkstatt'" -%}

(Aus _includes/tool_list.html)

Zieht sich alle geräte aus der Inventory-Liste, wenn im set das set werkstatt ist.

{% assign events = site.events | where: "uid", video.event -%}

(Aus _includes/media_in_list.html)

Zieht alle Events, deren UID die eines events ist (dies sollte lediglich eins sein).