SSR control center: auto-purge webhook, dashboard tiles, backend module

Package 1: SsrPurgeService posts to the node /__purge (endpoint+secret in var/vitec-ssr-purge.env, outside git) and logs every attempt to tx_vitec_ssrpurgelog. DataHandler hooks queue per request and flush once: pages with nav-relevant field changes and all tx_news_/tx_vitec_ records purge everything, other page/content edits purge the hosting page path. Gated by the routing flag and the new Site Set switch vitec.ssr.autoPurge. Flipping the SSR switch ON purges everything once. CLI: vitec:ssr-purge, vitec:ssr-health (samples /__health into tx_vitec_ssrhealthlog, 14 days kept, scheduler-ready). Package 2: dashboard widgets vitecSsrStatus (live health, release, switch, last purge) and vitecSsrStats (purge counts, failures, uptime, response time). Package 3: backend module web_vitecssr with manual purge (paths or everything) and both protocols. Tested end to end against the running node (purge single/all 200, health sample logged).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
orascheandClaude Fable 5 committed 2026-11-09 20:46:16 +01:00
1 parent d52d49974f
commit 63f950f9db
14 files changed
+1003

No files matched your search

@@ -0,0 +1,108 @@
<html xmlns:f="http://typo3.org/ns/TYPO3/CMS/Fluid/ViewHelpers" data-namespace-typo3-fluid="true">
<h1>VITEC SSR — Steuerung &amp; Protokoll</h1>
<div class="row">
<div class="col-md-6">
<h3>Status</h3>
<table class="table table-striped">
<tr>
<th>SSR-Auslieferung</th>
<td>
<f:if condition="{flagOn}">
<f:then><span class="badge badge-success">AN — Seiten kommen vom VPS</span></f:then>
<f:else><span class="badge badge-secondary">AUS — SPA wie bisher</span></f:else>
</f:if>
<br><small>Umschalten: Site Management &rsaquo; Settings &rsaquo; VITEC</small>
</td>
</tr>
<tr>
<th>SSR-Server</th>
<td>
<f:if condition="{health}">
<f:then>
<span class="badge badge-success">läuft</span> {health.responseMs} ms<br>
Release <strong>{health.release.release}</strong>
(Commit {health.release.commit})<br>
Cache: {health.cachedPages} Seiten / {health.cacheMB} MB
</f:then>
<f:else>
<span class="badge badge-danger">nicht erreichbar</span> {healthError}
</f:else>
</f:if>
</td>
</tr>
<tr>
<th>Purge-Konfiguration</th>
<td>
<f:if condition="{configured}">
<f:then><span class="badge badge-success">ok</span></f:then>
<f:else><span class="badge badge-warning">var/vitec-ssr-purge.env fehlt</span></f:else>
</f:if>
</td>
</tr>
</table>
</div>
<div class="col-md-6">
<h3>Cache leeren (Purge)</h3>
<form action="{f:be.uri(route: 'web_vitecssr.purge')}" method="post" class="form-group">
<label for="purge-paths">Pfade (einer je Zeile oder kommagetrennt):</label>
<textarea class="form-control" id="purge-paths" name="paths" rows="3"
placeholder="/products/aligo&#10;/insights/news"></textarea>
<input type="hidden" name="mode" value="paths">
<div style="margin-top:8px">
<button type="submit" class="btn btn-primary">Diese Pfade purgen</button>
</div>
</form>
<form action="{f:be.uri(route: 'web_vitecssr.purge')}" method="post"
onsubmit="return confirm('Wirklich den KOMPLETTEN SSR-Cache leeren?');">
<input type="hidden" name="mode" value="all">
<button type="submit" class="btn btn-warning">Alles purgen (*)</button>
<small class="text-muted"> — nötig nach Menü-/Footer-Änderungen bei abgeschaltetem Auto-Purge</small>
</form>
</div>
</div>
<h3>Purge-Protokoll <small>(letzte 30)</small></h3>
<table class="table table-striped table-sm">
<thead><tr><th>Zeit</th><th>Auslöser</th><th>Pfade</th><th>Ergebnis</th><th>Dauer</th></tr></thead>
<tbody>
<f:for each="{purgeLog}" as="row">
<tr>
<td><f:format.date format="d.m.Y H:i:s">@{row.crdate}</f:format.date></td>
<td>{row.trigger_source}</td>
<td><code>{row.paths}</code></td>
<td>
<f:if condition="{row.success}">
<f:then><span class="badge badge-success">ok</span></f:then>
<f:else><span class="badge badge-danger">HTTP {row.http_code}</span> {row.message}</f:else>
</f:if>
</td>
<td>{row.duration_ms} ms</td>
</tr>
</f:for>
</tbody>
</table>
<h3>Gesundheits-Messungen <small>(letzte 10 — Historie via Scheduler-Task <code>vitec:ssr-health</code>)</small></h3>
<table class="table table-striped table-sm">
<thead><tr><th>Zeit</th><th>Status</th><th>Release</th><th>Cache</th><th>Antwortzeit</th></tr></thead>
<tbody>
<f:for each="{healthLog}" as="row">
<tr>
<td><f:format.date format="d.m.Y H:i:s">@{row.crdate}</f:format.date></td>
<td>
<f:if condition="{row.ok}">
<f:then><span class="badge badge-success">ok</span></f:then>
<f:else><span class="badge badge-danger">down</span></f:else>
</f:if>
</td>
<td>{row.release_id}</td>
<td>{row.cached_pages} Seiten / {row.cache_mb} MB</td>
<td>{row.response_ms} ms</td>
</tr>
</f:for>
</tbody>
</table>
</html>