Takt über public/cron.php: KAS-Cronjobs können nur URLs
Korrektur meiner eigenen Annahme von heute früh. Der Tarif hat SSH und Cronjobs, aber das KAS-Formular kennt nur ein Feld "Protokoll / Pfad" mit https:// — ein `php bin/…` ist dort nicht eintragbar. Der Endpoint, den ich vorhin stillgelegt hatte, ist damit wieder der einzige Takt-Geber, und zwar in einer besseren Form als geplant: Aufrufer ist der Hoster selbst, der Schlüssel verlässt den Webspace nie, kein Dritter ist beteiligt. Dritter Job 'logrotate' in der Whitelist, denn ohne ihn liefe die Logpflege nie automatisch und die 2-MB-Grenze samt 90-Tage-Frist wäre toter Code. Er passt in denselben Rahmen wie die Syncs: kein Parameter aus der URL, keine Verbindung nach außen, schreibt nur in storage/logs. bin/log-rotate.php trägt dafür denselben Riegel wie die Syncs (CRON_HTTP) und require_once. Eine vierte Ausnahme braucht wieder denselben Aufwand an Begründung. Geprüft: falscher Schlüssel 403, unbekannter Job 403, gültiger Aufruf 204 mit leerem Body, sofortige Wiederholung 204 plus WARN, Logdateien unversehrt. Zeitraster angepasst, weil das KAS Wochentage nicht mit Halbstunden kombiniert: Matchcenter stündlich statt 2x/Tag plus Wochenende, Instagram als zwei Tageseinträge, Logpflege täglich nachts. Die Abwägung steht in config.example.php und docs/deploy.md. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01NzeVVgMCrzCDJAKeLEdKr7
This commit is contained in:
43
CLAUDE.md
43
CLAUDE.md
@@ -7,8 +7,9 @@ selbst gehosteter Stack ohne Abhängigkeiten von Drittanbietern.
|
||||
|
||||
- **Frontend:** Natives HTML, Vanilla CSS, Vanilla JS. Kein Framework, keine Build-Pipeline, kein Node.
|
||||
- **Backend:** Vanilla PHP ≥ 8.1, Composer nur für `phpmailer/phpmailer`. Keine Template-Engine.
|
||||
- **Hosting-Ziel:** All-Inkl Shared Hosting, PHP 8.x, `.htaccess`, SSH **und** Shell-Cronjobs
|
||||
(seit 31.07.2026 im Tarif). Deploy-Anleitung Schritt für Schritt: **`docs/deploy.md`**.
|
||||
- **Hosting-Ziel:** All-Inkl Shared Hosting, PHP 8.x, `.htaccess`, SSH (seit 31.07.2026) und
|
||||
Cronjobs, die aber **nur URLs aufrufen können** — deshalb läuft der Takt über
|
||||
`public/cron.php`, siehe dort. Deploy-Anleitung Schritt für Schritt: **`docs/deploy.md`**.
|
||||
- **Lokales Dev:** `php -d upload_max_filesize=250M -d post_max_size=260M -S localhost:8000 -t public public/index.php`
|
||||
(index.php fungiert als Router-Script, weil `php -S` kein .htaccess kennt). Die beiden `-d`-Schalter
|
||||
brauchst du für die Dateiablage `/dateien`: der CLI-Server liest keine `.user.ini`, und mit den
|
||||
@@ -227,7 +228,9 @@ Funktion, sie ist die einzige Stelle, an der aus JSON HTML entsteht.
|
||||
Web wie CLI. Kein `error_log()`, kein `file_put_contents()` auf eine Logdatei, keine eigene
|
||||
Log-Closure in einem neuen Skript.
|
||||
- Kanal = Dateiname unter `storage/logs/`: `mail` · `spam` · `instagram` · `matchcenter` ·
|
||||
`stadionzeitung` · `veranstaltungen`
|
||||
`stadionzeitung` · `veranstaltungen` · `chronik` · `filesgallery` · `logrotate`
|
||||
(letzterer nur für den Übersprungen-Hinweis des Cron-Endpoints, der seinen Kanal aus dem
|
||||
Job-Namen bildet)
|
||||
(`php-errors.log` schreibt PHP selbst, eigenes Format).
|
||||
- Level mit klarer Bedeutung: **INFO** Normalbetrieb (auch ein geblockter Bot — der Schutz
|
||||
arbeitet, das ist kein Fehler) · **WARN** Auffälligkeit, Betrieb läuft weiter (Einzelbild
|
||||
@@ -341,23 +344,29 @@ Keine rohen Werte in `base/layout/components/utilities.css` — es gibt für all
|
||||
- [ ] Keine Duplikate: Inhalte/Werte aus den Single-Source-Dateien beziehen
|
||||
- [ ] `php -l` sauber; Seite lokal geprüft
|
||||
|
||||
## Cron-Endpoint `public/cron.php` (Ausnahme 3b) — **stillgelegt**
|
||||
## Cron-Endpoint `public/cron.php` (Ausnahme 3b) — **der Takt-Geber**
|
||||
|
||||
**Seit 31.07.2026 hat der Tarif SSH und echte Shell-Cronjobs.** Damit ist der Endpoint überflüssig:
|
||||
er war ausschließlich der Ersatz für den fehlenden Cron. `cron.key` steht in der Produktiv-Config auf
|
||||
`''`, der Endpoint antwortet also auf jeden Aufruf mit 403 — ein Geheimnis weniger, das bei einem
|
||||
externen Dienst liegt und leaken kann. Der Takt läuft über die Crontab-Zeilen aus
|
||||
`config/config.example.php` (Weg A), der Ablauf steht in **`docs/deploy.md`**, Teil D.
|
||||
**Die KAS-Cronjobs können ausschließlich URLs aufrufen, keine Shell-Befehle** (geprüft 31.07.2026:
|
||||
das Anlege-Formular hat nur ein Feld „Protokoll / Pfad" mit `https://`). Der Tarif hat inzwischen SSH
|
||||
und Cronjobs, aber ein `php bin/…` ist dort nicht eintragbar. Deshalb ruft der **KAS-Cron diesen
|
||||
Endpoint** auf, und er startet das Skript serverseitig. Der Ablauf steht in **`docs/deploy.md`**, Teil D,
|
||||
die drei Zeitpunkte in `config/config.example.php`.
|
||||
|
||||
**Der Code bleibt.** Er ist geprüft, kostet nichts (403 in drei Zeilen) und ist der Rückweg, falls der
|
||||
Shell-Cron ausfällt: neuen Schlüssel in `cron.key`, fertig. Deshalb sind die Grenzen unten weiter
|
||||
beschrieben, statt sie mit dem Code zu löschen — wer ihn je wieder aufschließt, braucht sie.
|
||||
`bin/preflight.php` warnt bei leerem Schlüssel und weist damit auf genau diese Entscheidung hin;
|
||||
die Warnung ist erwartet, kein Mangel.
|
||||
Das ist besser als der ursprünglich geplante externe Cron-Dienst: **der Aufrufer ist der Hoster
|
||||
selbst**, der Schlüssel verlässt den Webspace nie, es ist überhaupt kein Dritter beteiligt.
|
||||
`cron.key` muss also gesetzt sein — steht er leer, läuft **kein** Sync mehr.
|
||||
|
||||
Die Begründung von damals, weiterhin gültig für den Fall der Reaktivierung: ein externer Cron-Dienst ruft
|
||||
`https://…/cron.php?job=matchcenter` bzw. `?job=instagram` auf, der Endpoint startet das Skript
|
||||
serverseitig. Schlüssel aus `config('cron.key')`, per Header `X-Cron-Key` **oder** als `key`-Parameter.
|
||||
Ein externer Cron-Dienst ruft, falls je nötig, dieselben URLs auf:
|
||||
`https://…/cron.php?job=matchcenter` · `?job=instagram` · `?job=logrotate`. Schlüssel aus
|
||||
`config('cron.key')`, per Header `X-Cron-Key` **oder** als `key`-Parameter (im KAS notgedrungen als
|
||||
Parameter, das Formular kennt keine Header).
|
||||
|
||||
**Warum es drei Jobs sind:** `logrotate` kam am 31.07.2026 dazu, weil dieser Endpoint der einzige Weg
|
||||
ist, überhaupt etwas getaktet laufen zu lassen. Ohne ihn liefe die Logpflege nie automatisch und die
|
||||
2-MB-Grenze samt 90-Tage-Frist wäre toter Code. Der Job passt in denselben Rahmen wie die Syncs: kein
|
||||
Parameter aus der URL, keine Verbindung nach außen, er schreibt nur in `storage/logs`. Eine **vierte**
|
||||
Ausnahme braucht wieder denselben Aufwand an Begründung. `bin/log-rotate.php` trägt dafür denselben
|
||||
Riegel wie die Syncs (`PHP_SAPI !== 'cli' && !defined('CRON_HTTP')`) und `require_once`.
|
||||
|
||||
**Warum dieser Weg und nicht GitHub Actions mit FTP-Upload:** dort müsste ein Dritter Schreibzugang
|
||||
zum ganzen Webspace kennen. Hier kennt er einen Schlüssel, der ausschließlich „starte einen der beiden
|
||||
|
||||
Reference in New Issue
Block a user