PostOmnia ← Zurück

Changelog

Alle nennenswerten Änderungen an PostOmnia.

Changelog

Alle nennenswerten Änderungen an diesem Projekt werden hier dokumentiert.

Format angelehnt an Keep a Changelog.

[Unveröffentlicht]

Verkaufsreife (Analyse in docs/VERKAUFSREIFE.md)

schreibt einen Tagger ins Tag-Objekt und scheitert ohne Git-Identität mit

„Committer identity unknown"; auf dem Actions-Runner ist keine gesetzt, und

actions/checkout setzt auch keine. Der Deploy-Workflow konfiguriert jetzt die

Identität des Actions-Bots, bevor das Skript läuft. Warum es so lange unentdeckt

blieb, war der zweite Teil des Fehlers: git tag -a … 2>/dev/null verschluckte

den Grund und meldete nur „konnte nicht gesetzt werden". Beide Fehlerpfade der

Marke (Tag und Push) nennen jetzt die tatsächliche Meldung. Ohne Tag ließ sich

nicht sagen, welcher Stand wann live ging — der Rollback selbst war nie

betroffen, der hängt am Zeitstempel der Server-Sicherung.

aus der Tarifliste ausgeblendet, solange ein bezahlter Tarif lief; der einzige

Weg heraus führte über das Stripe-Kundenportal. Die Tarifkarte steht jetzt

jedem Workspace offen und führt über POST /billing/downgrade.

Ein laufendes Stripe-Abo endet dabei zum Ende der bezahlten Periode — die

Periode ist bezahlt und darf genutzt werden —, alles andere (manueller

Provider, offene Zahlung, bereits gekündigt) wechselt sofort. Bestätigt wird

vorher mit dem, was der Wechsel kostet: verbundene Kanäle bleiben, geplante

Beiträge laufen aus, neue Beiträge, Kanäle, Teammitglieder, KI-Credits und

Analytics entfallen, die Link-in-Bio-Seite bleibt.

Stripe-Subscription fiel bisher auf Creator zurück — einen bezahlten Tarif.

Wer kündigte, behielt 30 Kanäle, Team und KI-Credits, ohne weiter zu zahlen,

und ein erklärter Wechsel auf Bio Free wäre am Periodenende still ein Wechsel

auf Creator geworden. Bio Free ist der Tarif ohne Vertrag; genau dorthin gehört

ein Team, dessen Vertrag ausgelaufen ist. Der verbrauchte Trial bleibt

verbraucht: Bio Free ist sonst der Weg zu beliebig vielen Testphasen.

waren im Ober-Admin am Status canceled erkennbar. Auf Bio Free ist der Status

wieder active — die Kündigung wäre als „Free-Kunde" verbucht worden und die

Abwanderung unsichtbar. traction.customers() zählt Kündigungen jetzt an

canceledAt, nicht am Status; die Churn-Auswertung tat das ohnehin schon.

Bestandsteams, die durch eine frühere Kündigung auf Creator stehen, bleiben

unangetastet — das ist eine Korrektur an Kundendaten, keine Codeänderung.

Vertragstext verweist für die Annahme auf „Einstellungen → Datenschutz →

Auftragsverarbeitung"; im Dashboard gab es diesen Bereich nicht. Status und

Annahme existierten nur als REST-Route (GET/POST /teams/current/dpa) —

erreichbar für Skripte, nicht für den Kunden. Der Datenschutz-Bereich zeigt

jetzt Fassung, Stand, Annahmestatus und die drei Vertragsdokumente; Inhaber

und Admins nehmen nach ausdrücklicher Bestätigung an, Mitglieder sehen den

Status samt Hinweis, wer annehmen darf.

mit Verantwortlichem, Auftragsverarbeiter, angenommener Fassung, Zeitpunkt und

handelnder Person — das zweite Versprechen des Vertragstexts („die

unterzeichnete Fassung mit Datum zum Download"), das bis dahin ebenfalls

unerfüllt war. Fassung und Stand kommen aus dem Annahmeprotokoll, nicht aus

der aktuellen Konstante: Der Beleg dokumentiert, was angenommen wurde, und

weist auf eine seither erschienene neuere Fassung hin.

Fakten, Optionen mit Empfehlung, fertiger Prüfauftrag an den Anwalt. Geprüft:

ein einziger Rechteinhaber (61 Commits, keine fremden Beitragenden), 118

Abhängigkeiten sämtlich permissiv (kein Copyleft, keine unbekannte Lizenz).

DEINE FIRMA]`). Eine MIT-Lizenz verpflichtet Lizenznehmer, „the above

copyright notice" mitzuliefern — nennt sie niemanden, geht die Erklärung ins

Leere. Eingetragen ist jetzt dieselbe Einheit, die package.json als Autor

führt; test/license.test.mjs hält Platzhalter und Abweichungen künftig auf.

aus, bereits veröffentlichte MIT-Stände ließen sich nicht zurückholen. Es gibt

keine: Das Repository ist privat, es wurde nie etwas herausgegeben — damit

existiert kein Lizenznehmer und keine erteilte Erlaubnis. Korrigiert.

Vorlagen in docs/OUTREACH.md bewerben PostOmnia als „quelloffen" bzw.

„open-source" — bei privatem Repository unzutreffend und damit ein UWG-Thema;

durch Veröffentlichen zutreffend gemacht, ist die MIT-Erteilung vollzogen und

unwiderruflich. Hinweis an den betroffenen Stellen ergänzt.

aktives Produkt derselben Kategorie (Social-Media-Publishing als SaaS). Ein

Buchstabe Unterschied bei identischen Dienstleistungen ist der Lehrbuchfall

der Verwechslungsgefahr. Ob daraus ein Anspruch folgt, kann nur ein Anwalt

klären — Einordnung, Umfeldanalyse (Postiz, Postoria, Postfity, …) und ein

ausformulierter Prüfauftrag samt Nizza-Klassen liegen bei.

unter Einrichtung: Folgenabschätzung, Trennen (nur Plattform-Apps, nur

Dienste und Firmendaten, oder alles) und Inbetriebnahme-Checkliste für den

neuen Betreiber. Kundendaten werden nie angefasst und nach dem Trennen zur

Kontrolle gezählt. Firmendaten gehören ausdrücklich zum Trennen — niemand

darf unter dem Impressum des Vorbesitzers verkaufen.

Oberfläche jetzt vor der Entscheidung: (1) Die OAuth-Tokens der Kunden wurden

von der Developer-App des bisherigen Betreibers ausgestellt und sind mit einer

neuen App wertlos — betroffene Konten werden deshalb **markiert statt

gelöscht** (ein Wechsel ist umkehrbar) und die Kunden bekommen einen Hinweis

in der Benachrichtigungszentrale, statt dass Beiträge still fehlschlagen.

(2) Ein neuer Stripe-Schlüssel ist ein neues Konto ohne die bestehenden Abos.

(3) Werte aus der .env auf dem Server kann der Adminbereich gar nicht

entfernen — die Antwort listet auf, welche Schlüssel dort noch scharf sind.

wechselbar: Er entschlüsselt die gespeicherten Kanal-Zugänge, ein Wechsel per

Weboberfläche hielte den Totalverlust aller Kundenverbindungen einen Klick

weit entfernt.

hat.** scripts/restore-test.sh spielt den dokumentierten Weg vollständig

durch: sichern wie backup-db.sh, entschlüsseln wie im Runbook, Inhalt

prüfen, Anwendung auf dem Bestand starten, Statusseite abrufen — mit

Zeitmessung. Der erste Lauf hat sofort geliefert, wofür es die Übung gibt: Die

Wiederherstellungsanleitung kannte nur POSTOMNIA_BACKUP_KEY für die

Sicherungsdatei, nicht aber POSTOMNIA_ENCRYPTION_KEY für die Kanal-Zugänge

darin. Eine Wiederherstellung nach der alten Anleitung wäre scheinbar

geglückt — Datei entschlüsselt, Struktur vollständig, /healthz grün — und

hätte trotzdem bei jedem Kunden tote Zugänge hinterlassen, bemerkt erst beim

ersten fehlgeschlagenen Beitrag mitten im Störfall.

Struktur UND Kanal-Zugänge brauchbar sind, und endet mit Exit-Code 1 statt

still durchzulaufen. docs/DEPLOY.md führt den zweiten Schlüssel jetzt in

einer eigenen Tabelle und den Prüfschritt in der Anleitung; die frühere

Angabe „byte-identisch durchgespielt" steht mit der Einordnung dort, dass sie

nur die Datei betraf, nicht die Brauchbarkeit.

Ehrlich getrennt: RPO (max. 24 h) folgt aus dem Cron-Intervall und ist

belastbar, ein RTO ist es nicht — die gemessenen Sekunden gelten für einen

Testbestand. Die Übung gegen eine echte Produktionssicherung bleibt offen,

samt Vorlage zum Ausfüllen. Das Backup-Repo wurde bewusst nicht angefasst: Es

enthält Kundendaten und hat in einer Testumgebung nichts verloren.

MRR/ARR, Kundenbestand, Abwanderung und Kohorten – gerechnet aus den

ausgestellten Belegen und den Abo-Zuständen, nicht geschätzt. Export über

GET /api/admin/traction und /api/admin/traction.csv samt mitgelieferten

Definitionen, damit die Gegenseite nachrechnen kann statt zu glauben.

Bewusste Festlegungen: Testphasen zählen nicht in den MRR (ein Trial ist

kein Umsatz, auch wenn er in jeder Pitch-Deck-Vorlage so aussieht),

maßgeblich ist netto (Umsatzsteuer ist durchlaufender Posten), Jahresabos

werden auf den Monat normalisiert statt im Abrechnungsmonat zu verschwinden,

und Kennzahlen ohne Grundlage sind null statt 0 – eine Abwanderungsquote

von „0 %" ohne Kundenbestand wäre eine Falschaussage. Der Snapshot benennt in

caveats selbst, was die Zahlen nicht hergeben.

Inventar aller externen Konten samt Übertragungsweg, Lizenz- und Markenstatus

sowie eine offene Liste der Punkte, die den Preis drücken. Zwei Befunde, die

vorher nirgends standen: Stripe-Abos lassen sich nicht einfach mitverkaufen

(ohne den beantragten Konto-Transfer müssen alle Kunden neu einwilligen), und

POSTOMNIA_ENCRYPTION_KEY ist der kritischste Wert der Übergabe – ohne ihn

sind die gespeicherten Kanal-Zugänge aller Kunden nicht mehr entschlüsselbar.

Das Dokument enthält bewusst nur Namen von Konten und Schlüsseln, nie Werte.

Prozess läuft – bei einem Totalausfall entsteht gar keine Stichprobe, der

Ausfall erschiene als Lücke und damit günstiger, als er war. scripts/uptime-probe.mjs

ruft die öffentliche Adresse von außerhalb auf und misst DNS, TLS, Reverse

Proxy und Anwendung gemeinsam; eingeliefert wird über

POST /api/public/uptime-probe mit POSTOMNIA_UPTIME_PROBE_TOKEN. Externe und

interne Reihe werden getrennt geführt, /status weist die externe aus, sobald

es sie gibt, und benennt die Messquelle – zusammengerechnet würden sie die

belastbare Zahl mit der schwachen verwässern.

an die ausgefallene Anwendung melden; sie puffert lokal und liefert rückdatiert

nach. Damit daraus kein Werkzeug zum Schönrechnen wird: Token im zeitkonstanten

Vergleich, keine Zeitpunkte aus der Zukunft, Rückdatierung höchstens 48 Stunden,

Deduplizierung über eine Stichproben-ID (eine erneut gesendete Charge zählt

nicht doppelt), Rate-Limit. Ohne gesetztes Token ist der Endpunkt aus.

Puffer überlebt den kurzlebigen Runner über actions/cache – ohne den ginge

genau die Stichprobe verloren, für die das Puffern gebaut wurde. Dass GitHubs

Scheduler Läufe auslässt, ist dokumentiert: Für ein Verhältnis aus erreichbaren

zu nicht erreichbaren Stichproben senkt das nur die Auflösung.

Agency-Tarif 99,5 % Monatsverfügbarkeit zu und staffelt eine Gutschrift –

gemessen wurde bisher nichts, und der Vertrag nahm „angekündigte

Wartungsfenster" aus, ohne dass es einen Weg gab, eines anzukündigen. Neues

Modul src/uptime.js: Stichprobe alle fünf Minuten, Tagesbilanzen über 90 Tage,

Monatsverfügbarkeit und Gutschrift nach der Staffel des § 8 AGB. /status und

neu /en/status zeigen die Zahl, einen Tagesbalken je Tag, die offene

Störungs- und Wartungsliste und benennen, was die Sonde messen kann und was

nicht. Tage ohne Messwert bleiben grau statt grün, und eine Messreihe unter

30 Tagen wird ausdrücklich als „im Aufbau" ausgewiesen.

angelegt werden, sonst nimmt die Messung es nicht aus der Zusage heraus – sonst

wäre der bequemste Weg zu guten Zahlen, einen Ausfall nachträglich zum

Wartungsfenster zu erklären. Anlegen und Schließen über

/api/admin/status/incidents, beides bewusst als Hand-off im Adminbereich:

Der Eintrag erscheint sofort öffentlich und verändert, was der Agency-Tarif

schuldet.

Reaktionszeit stehen in POSTOMNIA_SLA_TARGET und

POSTOMNIA_SLA_RESPONSE_DAYS (auch im Adminbereich pflegbar) und füllen die

AGB über {{SLA_TARGET}}/{{SLA_RESPONSE}} aus derselben Quelle wie die

Messung. Eine im Vertragstext einbetonierte Zahl wäre irgendwann von dem

weggelaufen, was die Statusseite belegt.

MERCHANT_TAX_COUNTRY, MERCHANT_TAX_RATE, MERCHANT_TAX_RATES und

STRIPE_AUTOMATIC_TAX waren die einzigen Größen des Abrechnungspfads, die

Serverzugang und Neustart verlangten – während Firmenname, Anschrift und

Steuernummer im selben Formularblock längst im Adminbereich standen. Der

Wechsel von der Kleinunternehmerregelung zur Regelbesteuerung ist ein

kaufmännischer Vorgang; jetzt ist er auch einer.

wurden mit der aus dem Pfad abgeleiteten Oberflächensprache gefüllt; /agb.html

trägt aber kein Sprachpräfix und fiel damit auf Englisch zurück. Gerendert wird

jetzt in der Sprache des Dokuments.

Kleinunternehmer (Standard), Regelbesteuerung, Reverse Charge für EU-Geschäfts-

kunden mit USt-IdNr., OSS-Satz für EU-Privatkunden, Drittland nicht steuerbar.

Der Beleg weist Netto, Steuersatz, Steuerbetrag und den Pflichthinweis nach

§ 14 UStG aus. Stripe Tax ist über STRIPE_AUTOMATIC_TAX=1 aktivierbar und dann

maßgeblich; die Preise tragen tax_behavior: inclusive, weil die Listenpreise

brutto sind. Belege erscheinen in der Sprache des Kontoinhabers statt nur auf

Englisch.

beim Checkout stillschweigend verworfen, während die Oberfläche den reduzierten

Preis anzeigte – der Kunde sah 15,20 € und zahlte 19 €. Der Stripe-Coupon wird

jetzt wie die Preise find-or-create angelegt; scheitert das, bricht der Checkout

ab. Die Laufzeit steht explizit in src/plans.js (duration).

Anmeldung erreichbar, im Footer und in § 5 der AGB verlinkt. Bestätigung in

Textform mit Inhalt und Eingangszeitpunkt, Kündigung zum Ende der bezahlten

Periode (bei Stripe via cancel_at_period_end), Protokoll im Store.

(TOM, /tom.html) und Anlage 2 (versionierte Subprozessorenliste,

/subprozessoren.html), jeweils auch englisch unter /en/. Annahme pro

Workspace mit Version, Zeitpunkt und handelnder Person

(GET/POST /api/teams/current/dpa).

MERCHANT_*-Werte sind ohne Zahlungsdienst nur ein Hinweis, mit aktivem Stripe

eine deutliche Warnung – dann gingen Impressum, AGB und AVV mit Platzhaltern live.

einzige Oberfläche, die aus der Agentur heraus zum Endkunden geht, und trug

bisher fest PostOmnia-Branding. Ab Pro (limits.portalBranding === false)

treten Name, Logo, Akzentfarbe und Fußnote der Agentur an die Stelle; das Portal

gibt es jetzt auf Deutsch und Englisch.

arbeitet sofort los statt auf incomplete blockiert zu werden. Abgelaufene

Testphasen sperren produktive Aktionen nur im Verkaufsbetrieb (Stripe

konfiguriert) – eine selbst betriebene Instanz sperrt sich nicht selbst aus.

Altes Verhalten über POSTOMNIA_REQUIRE_CARD_UPFRONT=1.

Reaktion binnen eines Werktags, gestaffelte Gutschrift) und

Sicherheits-Onepager unter /sicherheit-onepager.html für Einkauf und

Sicherheitsfragebögen.

entfallen).

Selbstregistrierung; beim Agency-Tarif geht dem Abschluss aber meist ein

Gespräch voraus. Formular mit Honeypot und Rate-Limit, Speicherung in der

bereits vorhandenen Sammlung agencyEnquiries, Eingangsbestätigung an die

Agentur und Meldung an den Betreiber.

gebrandetes Dokument mit Kanalentwicklung, Top-Beiträgen und Vergleich zur

gleich langen Vorperiode – plus Link mit Ablaufdatum für Kunden ohne Konto.

Maßgeblich ist der Veröffentlichungszeitpunkt, nicht updatedAt; sonst

tauchten alte Beiträge nach einer Bearbeitung erneut im Report auf.

Trennzeichen (Semikolon und Tab kommen aus deutschen Excel-Exporten), kennt die

Spaltennamen gängiger Redaktionsplan-Exporte, erlaubt eigene Zuordnung und legt

offen, was er ignoriert hat. Neue Vorschau-Route /api/imports/csv/preview

zeigt das Ergebnis, bevor etwas angelegt wird. Vergangene Termine werden zu

Entwürfen statt rückwirkend geplant.

werden (reviewer oder viewer). Ein solcher Zugang sieht nur Beiträge der

Kampagnen dieses Kunden und darf ausschließlich ausdrücklich freigegebene

Operationen aufrufen – Whitelist statt Filter, damit neue Operationen

automatisch gesperrt sind.

origin/main liegt (genau der Fall vom 07.08.2026), setzt nach erfolgreichem

Deploy ein Versions-Tag und nennt den Rollback-Befehl. Neues

scripts/rollback-hetzner.sh samt Workflow-Eingabe; der Deploy-Workflow liefert

standardmäßig main aus statt des auslösenden Branches und prüft das zusätzlich.

Die Datenbank wird beim Rollback nur auf ausdrückliche Anforderung angefasst.

content/, mit Canonical, hreflang, Article-JSON-LD und Sitemap-Eintrag. Drei

Startartikel zu AVV und KI-Kennzeichnung. Redaktion braucht ab jetzt keine

Codeänderung mehr.

Katalog geprüft statt gegen ein Literal – die Zahl veraltete sonst still.

Sicherheit

wird jetzt über die Umgebungsvariable ${ADAPTLY_MCP_TOKEN} geladen statt im

Klartext im Repo zu liegen (Token muss extern rotiert werden).

ist jetzt über die GitHub-Variable DEPLOY_HOST konfigurierbar; die

DEPLOY_KNOWN_HOSTS-Pinning-Empfehlung wurde deutlicher formuliert (TOFU-Warnung).

plus Dependabot für npm und GitHub-Actions.

Entfernt

ohne Bezug zu PostOmnia) samt Inhalten entfernt.

public/og-agency-light-2026.png und drei alte Screenshots

(postomnia-login/-settings-profile/-team.jpg).

Geändert

als opt-in @ts-check-Inseln, .nvmrc, npm-Scripts (lint, format,

typecheck, test:coverage), CI-Quality-Job und Dependabot ergänzt.

engines.node auf >=20 angehoben, Docker-Image auf node:22-alpine.

Version-Floors aktualisiert; bekannte Transitiv-CVEs per npm audit fix

bereinigt. Express 4 und zod 3 bewusst beibehalten (Majors zu risikoreich).

(escapeHtml, publicBaseUrl, localBaseUrl) ersetzt mehrfach kopierte

Funktionen; Connector-Ergebnisvertrag vereinheitlicht (discord) und

gemeinsamer composeText-Helfer in connectors/base.js.

Umschalter in Landing-Nav und Topbar, gespeicherte Wahl, sonst folgt die

Seite der Systemeinstellung (angewendet vor dem ersten Paint – kein

Aufblitzen). Consent-Banner, Hero, Sidebar und alle Karten folgen dem Theme;

QR-Codes bleiben bewusst auf Weiß (Scanbarkeit).

?v=-Versionen aller Frontend-Assets werden beim Serverstart aus den

Dateiänderungszeiten berechnet und in alle gerenderten Seiten geschrieben –

ein Deploy invalidiert von selbst. Versionierte Assets sind dafür ein Jahr

unveränderlich gecacht (immutable), HTML bleibt no-cache. Alle Skripte

laden jetzt mit defer; sanftes Scrollen zu Ankern mit korrektem Offset

unter der Sticky-Leiste.

Untertabs: Übersicht (Kennzahlen + Aufgaben), Einrichtung & Schlüssel

(Plattform-Apps + Integrationen), Wachstum & Tracking, E-Mail, Nutzer &

Kanäle, Audit-Log. Badges zeigen offene Aufgaben, unkonfigurierte Gruppen

und die Nutzerzahl; der zuletzt offene Tab bleibt gemerkt.

Hinzugefügt

/de/link-in-bio liefern ausgeloggt eine serverseitig gerenderte Marketing-Seite

mit eigenem Title, eigener Description, Canonical auf sich selbst, hreflang-Paar

und FAQ-Structured-Data; eingeloggt weiterhin die Bio-Verwaltung. Bisher lieferte

/link-in-bio die Startseite samt canonical auf „/" und schloss sich damit

selbst aus dem Google-Index aus – es gab keine Seite, die für den Suchbegriff

kandidieren konnte. Die Unterscheidung läuft über ein reines Anwesenheitsflag

(po_app-Cookie, kein Credential), weil das Auth-Token in localStorage liegt und

der Server den Login-Status sonst nicht kennt; die Route sendet dafür Vary: Cookie.

Beide URLs stehen in der Sitemap.

/fr und /pt lieferten bisher identische Meta-Angaben, weil die Übersetzung erst

im Browser stattfindet – Google sah fünf gleiche Seiten. Titel und Description

kommen jetzt serverseitig je Sprache.

sich jetzt die Fläche der ganzen Seite einfärben (bisher fest weiss bzw.

dunkelblau aus dem Theme). Schrift-, Karten- und Linienfarben werden aus der

gewählten Farbe abgeleitet: Die Helligkeit der Fläche entscheidet über helle

oder dunkle Schrift, nicht mehr allein die Theme-Auswahl – eine dunkle

Wunschfarbe bleibt also auch im Light-Theme lesbar. Ohne eigene Farbe bleibt

alles wie bisher.

Consent-Kategorie „Marketing" mit granularen Schaltern (Analyse und Marketing

getrennt wählbar); Meta Pixel, Google GA4/Ads und TikTok Pixel laden

ausschließlich nach erteilter Zustimmung. Pixel-IDs pflegt der Ober-Admin

(Settings → Werbe-Pixel); ein öffentlicher Endpoint liefert nur gesetzte IDs.

Die Content-Security-Policy wird nur dann für die Werbe-Domains geöffnet, wenn

tatsächlich ein Pixel hinterlegt ist – sonst bleibt sie eng. Datenschutz-

erklärung um die Drittanbieter ergänzt. Consent-Version auf 2 erhöht

(bestehende Nutzer werden erneut gefragt).

(postomnia.de/r/<code>). Wer sich darüber registriert, bekommt

7 zusätzliche Testtage; sobald der Geworbene seine E-Mail bestätigt

(Missbrauchsschutz), erhält der Werber 30 Bonus-KI-Credits – ein eigener

Credit-Topf, der nicht monatlich verfällt und erst nach dem Plan-Kontingent

verbraucht wird. Neue App-Ansicht „🎁 Empfehlen" mit Link, Kopier- und

Share-Buttons (WhatsApp, Telegram, X, LinkedIn, E-Mail) und Statistik

(Klicks, Anmeldungen, bestätigt, verdiente Credits) samt Empfehlungsliste

mit maskierten E-Mail-Adressen. Benachrichtigungen bei Anmeldung und

bestätigter Belohnung.

gelernt aus dem Engagement der eigenen veröffentlichten Posts (Wochentag +

Stunde, Europe/Berlin); mit wenig Daten bewährte Standard-Slots.

(KI-Umformulierung, falls konfiguriert) oder per 🌲 auf ein 28-Tage-Intervall

stellen – der Scheduler plant sie dann automatisch zum nächsten

Magic-Time-Slot neu.

mit Double-Opt-in per Mail, Abonnenten-Übersicht und CSV-Export im Editor.

ausgespielt; Impressionen und Klicks je Variante, CTR-Anzeige und

„Gewinner übernehmen" im Editor.

mit großem QR-Code, Profilbild und Titel – PDF-Export über den Druckdialog.

veröffentlichter Seiten (SSRF-sicher) plus „Links prüfen"-Button; kaputte

Links bekommen ein Warn-Badge und eine Benachrichtigung.

Navigation und Footer – eingebauter Standard (offizielles PostOmnia-Profil),

überschreibbar per Ober-Admin (SOCIAL_INSTAGRAM_URL). Neue fest kuratierte

Beispiel-Bio-Seite unter /bio/beispiel (Handle reserviert) mit Featured-Link,

Abschnitts-Überschrift, Teaser-Drop und Instagram-Profil; Profil- und

Headerbild kommen live von der Link-in-Bio-Seite des Ober-Admin-Kontos. Die

Telefon-Demo im Link-in-Bio-Abschnitt zeigt und verlinkt diese Seite, der

„Scan mich"-Chip trägt jetzt ihren echten, scannbaren QR-Code.

OAuth-Plattformen (X, LinkedIn, Meta/Facebook+Instagram, Threads, Pinterest,

Reddit, TikTok, Google/YouTube) sowie Integrations-Schlüssel (Anthropic,

Gemini, SMTP, Stripe, Turnstile, Firmendaten, Social-Links) direkt im

Adminbereich pflegbar: verschlüsselt gespeichert (AES-256-GCM), sofort aktiv

ohne Neustart, Vorrang vor der .env mit sauberem Fallback beim Löschen.

Je Plattform-App: Status-Badge, Link ins Developer-Portal, Einrichtungs-Hinweis

und kopierbare Redirect-URLs. Live-Verbindungstests für SMTP, Stripe,

Anthropic und Gemini. Secrets verlassen den Server nur maskiert; Änderungen

landen (ohne Werte) im Audit-Log.

[0.1.0] – 2026-07-04

Erste Veröffentlichung

Publishing & Kanäle

Facebook, LinkedIn, TikTok, YouTube, Pinterest, Threads, Reddit) mit OAuth 2.0

bzw. Credential-Auth.

Steuerung

Teams & Konto

Abrechnung

Analytics

Betrieb & Sicherheit

Marketing/Launch

Landing-/Pricing-Page, Rechtstexte (Impressum/Datenschutz/AGB inkl. Widerruf),

Cookie-Consent-Banner.

[0.1.0]: https://github.com/PhiFa96/postomnia/releases/tag/v0.1.0