Jyavani Core stellt die Mail API als zentralen E-Mail-Versandweg für CMS-Funktionen und Plugins bereit. Funktions-Plugins müssen Core lediglich eine strukturierte Nachricht übergeben; Transportauswahl, Absenderidentität, Fallback und Versandprotokollierung werden getrennt verwaltet.
Warum die Mail API verwenden
Der Aufruf von mail(), SMTP oder einer Provider-API direkt aus jedem Plugin verteilt die Versandkonfiguration über das gesamte System. Wenn der Provider wechselt, muss jedes Plugin einzeln angepasst werden. Die Mail API trennt die Anforderungen einer Funktion von der Art, wie Nachrichten versendet werden.
- Funktions-Plugins müssen nicht von einem bestimmten SMTP-Plugin abhängen.
- Der Site Owner kann den Transport wechseln, ohne den aufrufenden Code zu ändern.
- Nachrichtenvalidierung, Versandergebnisse, Fallback und Protokollierung verwenden denselben Core-Vertrag.
- Zusätzliche Transporte können als optionale Plugins installiert oder deaktiviert werden.
Einstellungen unter Settings > Email
Die Seite E-Mail-Zustellung steht nur einem Site Owner mit Zugriff auf die Core-Einstellungen zur Verfügung. Diese Seite verwaltet:
- Primärer Transport als primären Versandweg.
- Fallback-Transport der versucht wird, wenn der primäre Transport nicht verfügbar ist oder vorübergehend fehlschlägt.
- Absendername und Absender-E-Mail-Adresse als standardmäßige Absenderidentität.
- Antwortadresse ist optional und trennt die Antwortadresse von der Absenderadresse.
- Versandprotokollierung mit deaktivierter Protokollierung, nur Fehlern oder allen Versuchen mit geschwärzten sensiblen Daten.
Der integrierte Transport native übergibt die Nachricht an mail() von PHP und die Hosting-Infrastruktur. SMTP-Zugangsdaten werden nicht auf der Core-Seite gespeichert. Ein Transport-Plugin stellt eine eigene Konfigurationsseite bereit und registriert anschließend einen Adapter bei der Mail API.
E-Mails aus einem Plugin senden
Ein Funktions-Plugin ruft jy_mail_send() auf und muss nicht wissen, ob die Website nativen Mailversand, SMTP oder einen anderen Provider verwendet.
$result = jy_mail_send($pdo, [
'to' => ['[email protected]'],
'subject' => 'Notifikasi Jyavani',
'body' => 'Proses telah selesai.',
'content_type' => 'text/plain',
]);
if (!$result['ok']) {
// Tampilkan pesan umum atau jadwalkan penanganan sesuai fitur.
}
Eine Nachricht akzeptiert eine Empfängerliste, Betreff, Inhalt, Inhaltstyp, einen strukturierten Absender und eine optionale Antwortadresse. Raw-Header des Aufrufers werden absichtlich nicht akzeptiert. Core weist Adressen oder Header-Felder mit Steuerzeichen zurück, bevor der Transport ausgeführt wird.
Vertrag für Transport-Plugins
Ein Adapter-Plugin registriert einen Transport über jy_mail_register_transport(). Der Callback erhält eine normalisierte Nachricht und den Versandkontext und gibt anschließend einen stabilen Status zurück:
acceptedwenn der Transport die Verantwortung für die Nachricht übernimmt.temporary_failurebei einem vorübergehenden Fehler, der sicher über den Fallback erneut versucht werden kann.permanent_failurebei einer Ablehnung oder einem Konfigurationsfehler, die nicht über den Fallback erneut versucht werden dürfen.
Core akzeptiert im Ergebnisobjekt keine Provider-Details, Zugangsdaten, Protokolltranskripte oder Nachrichteninhalte. Transport-Plugins müssen sensible Diagnosedaten aus der Antwort heraushalten und weiterhin schwärzen.
Explizites Fallback-Verhalten
Der Fallback wird nur ausgeführt, wenn der primäre Transport nicht verfügbar ist, einen vorübergehenden Fehler meldet oder eine Exception auslöst. Eine dauerhafte Ablehnung und ein ungültiger Transportvertrag lösen keinen Fallback aus. Diese Richtlinie verringert das Risiko einer doppelten Zustellung, wenn ein Provider die Nachricht bereits verarbeitet hat, die Verbindung jedoch vor der Bestätigung an die Anwendung abbricht.
Primärer Transport und Fallback dürfen nicht auf denselben Transport verweisen. Wenn kein Fallback erforderlich ist, wählen Sie Kein Fallback damit Fehler klar sichtbar bleiben.
Sicherheit und Datenschutz
- Empfänger, Absender, Antwortadresse, Betreff, Inhalt, Inhaltstyp und Nachrichtengröße werden vor dem Versand validiert.
- Über Filter geänderte Nachrichten werden erneut normalisiert und validiert.
- Plugins können den integrierten Transport
nativenicht ersetzen oder denselben Transportnamen zweimal registrieren. - Core-Protokolle erfassen nur ID, Status, Code, Transportnamen, Fallback-Nutzung und Anzahl der Empfänger.
- Protokolle enthalten keine Empfängeradressen, Betreffzeilen, Nachrichteninhalte, Zugangsdaten oder OTP-Werte.
- Einstellungen und Test-E-Mail werden durch die Site-Owner-Richtlinie, POST und CSRF-Validierung geschützt.
Versand testen
- Speichern Sie die Absenderidentität und den Transport unter Settings > Email.
- Wenn Sie SMTP oder eine Provider-API verwenden, schließen Sie die Konfiguration auf der Seite des Transport-Plugins ab.
- Geben Sie eine Empfängeradresse im Bereich Test-E-Mail senden.
- Senden Sie den Test und prüfen Sie die Serverprotokolle oder das Provider-Dashboard, wenn der Transport die Nachricht nicht akzeptiert.
Test-E-Mails sind frequenzbegrenzt und verwenden nur den vom Server festgelegten Betreff und Inhalt. Der Status accepted bedeutet, dass der Transport die Nachricht angenommen hat; er garantiert nicht die Zustellung im Posteingang. Konfigurieren Sie SPF, DKIM und DMARC für die Absenderdomain und prüfen Sie die Reputation und Richtlinien des Providers.
Aktuelle Funktionsgrenzen
Der Mail-API-Vertrag konzentriert sich auf einfache Transaktions-E-Mails im Format text/plain oder text/html. CC, BCC, Anhänge, Raw-MIME-Teile und beliebige Header sind noch nicht Bestandteil der API. Plugins sollten keinen zweiten Versandweg erstellen, um die Core-Validierung zu umgehen; schlagen Sie eine Vertragserweiterung vor, wenn diese Anforderung tatsächlich transportübergreifend unterstützt werden muss.
Mit diesem Muster können Funktionen wie OTP, Kontobenachrichtigungen, Formulare oder Berichte dieselbe API verwenden. Der Website-Betrieb kann weiterhin frei zwischen nativem Mailversand, SMTP oder einem anderen Provider wählen, ohne Funktions-Plugins voneinander abhängig zu machen.