Ich habe am Wochenende im Forum aufgeräumt. Richtig aufgeräumt...
Das Angebot Forum steht seit einiger Zeit auf wackligen Beinen, gerade mit (m)einem Businessthema.
Meine Hauptseite sind jetzt die "Letzten Beiträge" - aber in einem neuen Outfit. Das Ziel war:
Beitragsbild aus dem jeweiligen Thread anzeigen
die ersten Sätze des Beitrags als kurzen Teaser anzeigen
einen „Weiterlesen“-Link ergänzen
die Ladezeit der Seite möglichst gering halten
die Aktualisierung automatisch laufen lassen
Der erste Ansatz
Zuerst haben wir versucht, Bilder und Texte direkt im Browser per JavaScript aus den einzelnen Threads auszulesen.
Das hat grundsätzlich funktioniert. Der Nachteil war aber: Der Browser musste bei jedem Besucher mehrere Thread-Seiten im Hintergrund laden und durchsuchen.
Das war für die Ladezeit nicht optimal.
Die bessere Lösung
Deshalb haben wir auf eine andere Lösung umgestellt.
Die originale Xobor-Liste „Letzte Beiträge“ bleibt bestehen. Sie wird nicht ersetzt und nicht ausgeblendet.
Stattdessen erzeugt ein kleines PHP-Script auf einem externen Webspace automatisch eine Vorschau-Datei. Diese Datei enthält für die neuesten Threads jeweils:
Thread-ID
Titel
Link zum Thread
Beitragsbild
Teasertext aus den ersten Sätzen
Diese Vorschau-Datei heißt zum Beispiel:
1
latest-preview.js
Der Ablauf Schritt für Schritt
Xobor erzeugt wie gewohnt die Seite „Letzte Beiträge“.
Ein PHP-Generator ruft diese Xobor-Seite ab.
Der Generator findet dort die neuesten Thread-Links.
Danach ruft er die einzelnen Threads auf.
Aus dem echten Beitragsbereich wird das eingebundene Bild gesucht.
Aus dem Beitragstext werden die ersten Sätze als Teaser erzeugt.
Das Ergebnis wird als kleine JavaScript-Datei gespeichert.
Das Xobor-Forum lädt später nur noch diese fertige Datei.
Ein kleines Xobor-Plugin ergänzt dann die vorhandenen Xobor-Zeilen mit Bild, Teaser und „Weiterlesen“.
Warum ist das schneller?
Der große Vorteil ist: Die Besucher müssen nicht mehr viele Threadseiten im Hintergrund laden.
Stattdessen wird nur eine kleine fertige Vorschau-Datei geladen.
Das bedeutet:
weniger Hintergrundabfragen
weniger Last im Browser
schnellere Anzeige
stabilere Lösung
Wie wird das automatisch aktualisiert?
Da im aktuellen Strato-Tarif kein Cronjob enthalten ist, wird die automatische Aktualisierung über einen externen Web-Cron-Dienst gelöst.
Zum Beispiel über:
1
cron-job.org
Dieser Dienst ruft alle 30 Minuten die Generator-URL auf, zum Beispiel:
Ich bin an einer einfacherer Möglichkeit interessiert, da man zu meiner Variante einen externen Anbieter braucht. Also es ist schon ein gewisser Aufwand... Tüftelt mal, vielleicht bekommt ihr was einfacheres hin!
LG vom Arndt
Themen bei der Community für Transportunternehmer und Führungskräfte der Transport- und Logistikbranche:
ich hatte eine eigene Inspiration und Idee zu diesem Thema und habe ein selbst geschriebenes Skript entwickelt, um die Themen mit Bild und Text anzuzeigen!
Es ist eine reine In-House-Lösung, die komplett ohne externe Server auskommt und weder die Server-Last noch die CPU belastet.
Ich habe diesen Code speziell für das Xobor Business v4 Template entwickelt und optimiert!
Ich präsentiere euch das Skript hier als meine Idee und Inspiration.
======================================================================== 💡 MEINE IDEE UND UMSETZUNG IM SKRIPT FÜR BUSINESS V4: ========================================================================
1. Im normalen Forum setzt das Skript das Vorschaubild (oder den Autoren-Avatar als Fallback) schick links neben den Titel.
2. Im Activity Feed bleibt der Avatar des Schreibers ganz vorne unberührt. Das Vorschaubild des Themas rutscht im Code automatisch dezent nach hinten rechts neben den Titel, damit es nicht irritiert (siehe meine Screenshots im Anhang!).
3. Gibt es kein Bild, baut meine Engine automatisch ein edles farbiges Icon mit dem Anfangsbuchstaben des Themas.
======================================================================== 💻 MEIN CODE FÜR "GLOBALES JAVASCRIPT (PC-FOOTER)": ========================================================================
var threadUrl = topicLink.href; var idMatch = threadUrl.match(/\/t(\d+)/i) || threadUrl.match(/id=(\d+)/i) || threadUrl.match(/thread=(\d+)/i); if (!idMatch) return;
var threadId = idMatch[1]; var cleanFetchUrl = window.location.protocol + '//' + window.location.hostname + '/topic.php?id=' + threadId;
topicLink.setAttribute('data-teaser-done', 'loading'); if (cell !== topicLink) cell.setAttribute('data-teaser-done', 'loading');
var isActivityFeed = cell.classList.contains('activity_feed_line') || cell.closest('.boxcontent, .sidebar, #activity_feed');
var previewElement = document.createElement('div'); previewElement.className = 'daishi-teaser-thumb';
Ich hab durch Klaus und Ingeborg mal die API_xobor_plugin_getDeep-Funktion durchleuchten lassen. Da hat es mir nach Skripteinspielungen in der Konsole immer Fehlermeldungen gebracht. null heißt: Der Aufruf funktioniert technisch, aber Xobor liefert zu diesem Beitrag über getDeep() keine Daten zurück.
Also:
xobor.plugin ist da ✅ getDeep-Funktion ist da ✅ Callback läuft ✅ Ergebnis ist null ❌ Zitat: Die API-Seite ist hilfreich, aber nicht wegen getDeep(). Der bessere Hebel ist: Xobor-Template-Elemente / Inline-Elemente / Template-Variablen.
Aber wir sind ja erst am Anfang...
LG vom Arndt
Themen bei der Community für Transportunternehmer und Führungskräfte der Transport- und Logistikbranche:
moin zusammen, sehe, @Wolfgang hat am Wochenende fleißig an diesem Projekt gearbeitet. so elegant wie hier sieht's bei mir nicht aus.
mein Teasertext ist nun vollkommenen unformatiert ohne irgendwelche Links. Ich speichere ihn zusammen mit der Bildadresse in einer Datavar im Thread ab. das klappt auch mehr oder weniger gut. Aber auch den Text zu speichern hat wahrscheinlich mehr Nach- als Vorteile.
Dieses Projekt zwingt einen gut formulierte Starttexte zu formulieren. Bei den meisten meiner Themen hapert es daran.
für die MobilVariante muss man wahrscheinlich die Texte kürzer halten. Die Bildgröße hatte ich schon an die Bildschirmgröße gekoppelt.
text = text .replace(/\s+/g, " ") .replace(/"/g, "") .replace(/^[-–—\s]+/, "") .trim();
/* Typische Überschriften oder leere Anfangsreste entfernen. Falls der Beitrag mit dem H1-Titel beginnt, soll der Teaser danach starten. */ text = text.replace(/^Brenner-Sperre.*?wird\s*/i, "");
return text.trim(); }
function getFirstSentences(text, count, maxChars) { text = cleanText(text);
function extractTextFromPostAreas(postAreas) { for (var i = 0; i < postAreas.length; i++) { var clone = postAreas[i].cloneNode(true);
removeUnwantedTextParts(clone);
/* H1/H2/H3 entfernen, damit nicht die Überschrift als Teaser kommt. */ var headings = clone.querySelectorAll("h1, h2, h3"); headings.forEach(function (h) { h.remove(); });
function findPostImageOnly(postAreas, threadUrl) { if (!postAreas || !postAreas.length) return "";
/* Hauptfall bei deinen Beiträgen: <a class="xembedded float-left" href="https://files.homepagemodules.de/...png"></a> */ for (var a = 0; a < postAreas.length; a++) { var embedded = postAreas[a].querySelectorAll("a.xembedded[href]");
for (var i = 0; i < embedded.length; i++) { var href = makeUrl(embedded[i].getAttribute("href"), threadUrl);
if (isImageUrl(href) && !isBlockedImage(href)) { return href; } } }
/* Reserve: echte img-Tags im Beitragsbereich. */ for (var b = 0; b < postAreas.length; b++) { var imgs = postAreas[b].querySelectorAll("img");
for (var x = 0; x < imgs.length; x++) { var src = imgs[x].getAttribute("src") || imgs[x].getAttribute("data-src") || imgs[x].getAttribute("data-original") || imgs[x].getAttribute("data-lazy-src") || "";
if (!src && imgs[x].getAttribute("srcset")) { src = imgs[x].getAttribute("srcset").split(",")[0].trim().split(" ")[0]; }
src = makeUrl(src, threadUrl);
if (isImageUrl(src) && !isBlockedImage(src)) { return src; } } }
return ""; }
function extractPostData(html, threadUrl) { var result = { image: "", teaser: "" };
if (!html) return result;
var doc = new DOMParser().parseFromString(html, "text/html");
/* Keine Suche im Header. Keine Suche im gesamten HTML. Nur echte Beitragsboxen. */ var postAreas = doc.querySelectorAll( ".message_rightcol .xquoteable, " + ".message_rightcol, " + ".message .xquoteable" );
function start() { /* Kurze Verzögerung, damit Xobor die Letzten Beiträge fertig aufgebaut hat. Keine Dauerschleife. */ setTimeout(loadAutomaticPreviews, 1200); setTimeout(loadAutomaticPreviews, 3200); }