Smart-Mail-Flow API
Diese Seite beschreibt die maschinenlesbare Ausgabe (API) von Smart-Mail-Flow ab Version 2.0.0. Sie richtet sich an Entwickler und an Programme oder KI-Systeme, die Testergebnisse automatisch auswerten. Was sich gegenüber älteren Versionen geändert hat, steht auf der Seite Smart-Mail-Flow API – Änderungen in Version 2.0.0.
1. Ablauf eines Tests
- Test-ID wählen. Die Test-ID (Kennung) ist der Teil der Empfängeradresse vor dem @. Sie bestimmt, unter welcher Adresse das Ergebnis abrufbar ist. Die Website erzeugt beim Klick auf „Test“ eine zufällige ID (z. B.
test-tmyn0ls7ona8). Eigene IDs sind erlaubt. - Mail senden an eine dieser Adressen:
<id>@smartmailflow.email– Zustellung über IPv4 oder IPv6, wie der sendende Server es wählt<id>@ip4.smartmailflow.email– nur über IPv4 erreichbar (prüft den IPv4-Versand)<id>@ip6.smartmailflow.email– nur über IPv6 erreichbar (prüft den IPv6-Versand)
- Ergebnis abrufen:
- für Menschen:
https://smartmailflow.de/test?token=<id> - für Programme (JSON):
https://smartmailflow.de/api?token=<id>
- für Menschen:
Regeln für die Test-ID
- mindestens 8 Zeichen, erlaubt sind nur
A–Z,a–z,0–9,_und- - Andere IDs werden schon beim Einliefern abgewiesen:
550 5.1.1 id too short (minimum 8 characters)550 5.1.1 invalid id (allowed: A-Z a-z 0-9 _ -)
- Wer die ID kennt, kann das Ergebnis sehen. Für eigene Tests deshalb einen zufälligen Anteil verwenden (z. B.
meinefirma-plus 12 Zufallszeichen) und keine erratbaren IDs wietest1234. - Jede neue Mail an dieselbe ID überschreibt das Ergebnis. Die API liefert immer die zuletzt eingegangene Mail. Für wiederkehrende Prüfungen (Monitoring) pro Durchlauf eine neue ID verwenden.
2. Abruf
GET https://smartmailflow.de/api?token=<id>
| HTTP | Antwort | Bedeutung |
|---|---|---|
| 200 | {"error": "", "data": {…}} |
Ergebnis vorhanden |
| 400 | {"error": "No token"} |
ID fehlt oder ist ungültig (unter 8 Zeichen, unerlaubte Zeichen) |
| 404 | {"error": "Token not found"} |
Zu dieser ID ist (noch) keine Mail eingegangen |
| 429 | {"error": "Rate limiter"} |
Mehr als 300 Abrufe pro Stunde von derselben IP |
| 500 | {"error": "internal error", "error_id": "…"} |
Interner Fehler, error_id bitte bei Rückfragen angeben |
Warten auf das Ergebnis: Eine Mail ist normalerweise wenige Sekunden nach dem Eingang ausgewertet. Die Prüfung selbst dauert 1–5 Sekunden. Bitte während des Wartens höchstens alle 10–15 Sekunden abfragen und nach einigen Minuten aufhören.
3. Aufbau der Antwort
data enthält den gespeicherten Datensatz. Die Rohmail wird nie ausgegeben (raw ist immer "Removed").
| Feld | Inhalt |
|---|---|
id |
laufende Nummer des Datensatzes |
mail_id |
die Test-ID |
queue_id |
Kennung der Mail beim Empfang (für Rückfragen) |
smtp_mail_from |
Absenderadresse aus dem SMTP-Umschlag (MAIL FROM, auch Envelope-From oder Return-Path genannt). Leer bei Null-Sender, z. B. bei Unzustellbarkeitsmeldungen |
smtp_rcpt_to |
Empfängeradresse aus dem SMTP-Umschlag (RCPT TO) |
header_from |
From:-Kopfzeile der Mail, wie sie der Empfänger sieht (eine Zeile, dekodiert) |
header_to |
To:-Kopfzeile (eine Zeile, dekodiert) |
subject |
Betreff (dekodiert) |
date_hdr |
Date:-Kopfzeile |
spf_status |
SPF-Ergebnis (wie debug.spf.result) |
dkim_status |
DKIM-Gesamtergebnis (wie debug.dkim.result) |
created |
Eingang der Mail (UTC) |
deleted_at |
gesetzt, wenn der Test gelöscht wurde. Inhalte sind dann entfernt (REMOVED, REPLACED_…) |
raw |
immer "Removed" |
debug |
alle Prüfergebnisse, siehe Abschnitt 4 |
4. Prüfergebnisse (debug)
Allgemeine Statuswerte, soweit nicht anders angegeben:
pass= in Ordnungwarn= Auffälligkeit, kein Fehlerfail= Fehlertemperror= vorübergehender DNS-Fehler, Ergebnis unbekanntpermerror= dauerhaft fehlerhafte Konfigurationnone/not_present= nicht konfiguriertnot_tested= nicht prüfbar
4.1 Allgemein
| Feld | Inhalt |
|---|---|
software_version |
Version von Smart-Mail-Flow, die die Mail geprüft hat (z. B. 2.0.0). Fehlt das Feld oder beginnt es mit 1., hat der Datensatz das ältere Format |
checked_at |
Zeitpunkt der Prüfung (UTC, ISO 8601) |
duration_ms |
Dauer der Prüfung in Millisekunden |
queue_id |
wie oben |
4.2 smtp – Verbindung zum Smart-Mail-Flow-Server
| Feld | Inhalt |
|---|---|
client_ip, ip_version |
IP-Adresse des einliefernden Servers und IP-Version (4 oder 6) |
helo |
Name, mit dem sich der Server gemeldet hat (HELO/EHLO) |
mail_from, rcpt_to |
SMTP-Umschlag (wie smtp_mail_from/smtp_rcpt_to) |
tls.protocol, tls.cipher |
Verschlüsselung dieser Verbindung, null = unverschlüsselt |
tls.status |
pass bei TLS 1.2 oder 1.3, warn bei älterem TLS, fail unverschlüsselt |
Grenze: Bewertet wird nur die letzte Übertragung zu Smart-Mail-Flow, nicht frühere Stationen der Mail.
4.3 header – Kopfzeilen der Mail
from[],to[]: je Adresseaddress,display_name(Anzeigename odernull) unddisplay_name_is_address.display_name_is_address = trueheißt: Der Anzeigename ist nur die Adresse selbst, oft in Anführungszeichen ("'a@b.de'" <a@b.de>). Outlook macht das häufig. Das ist kosmetisch und kein Fehler.
subject,date,message_id: Betreff, Datum und Message-ID der Mail.return_path:Return-Path:-Kopfzeile.
4.4 spf – Sender Policy Framework (RFC 7208)
| Feld | Inhalt |
|---|---|
result |
pass, fail, softfail, neutral, none, permerror, temperror |
identity, domain |
geprüfte Identität: mailfrom = Domain aus smtp.mail_from, helo = HELO-Name (nur bei Null-Sender) |
record |
ausgewerteter SPF-Eintrag der Domain (bei mehreren Einträgen eine Liste, dann permerror) |
mechanism |
der Teil des SPF-Eintrags, der das Ergebnis bestimmt hat (z. B. ip4:192.0.2.0/24, include:spf.protection.outlook.com, -all) |
dns_lookups, dns_lookup_limit |
benötigte DNS-Abfragen und Grenze laut RFC (10) |
explanation |
Erklärungstext |
4.5 dkim – DomainKeys Identified Mail (RFC 6376, 8463)
result: Gesamtergebnis.pass, wenn mindestens eine Signatur gültig ist, sonst das „beste“ Ergebnis der Signaturen (fail>temperror>permerror).none= nicht signiert.signatures[]: jede Signatur einzeln.
| Feld | Inhalt |
|---|---|
domain, selector |
d= und s= der Signatur |
signing_algorithm, canonicalization |
z. B. rsa-sha256, relaxed/relaxed |
signed_headers |
signierte Kopfzeilen |
body_length_limit |
l=-Tag (nur ein Teil des Inhalts signiert), sonst null |
dns_name, dns_txt |
abgefragter DNS-Name und gefundener Schlüssel-Eintrag |
key_algorithm, key_bits |
rsa oder ed25519 und Schlüssellänge |
key_strength |
ok (RSA ab 2048 Bit, ed25519), warning (RSA 1024–2047 Bit: gültig, aber zu kurz), weak (unter 1024 Bit) |
key_status |
ok, revoked (Schlüssel zurückgezogen), invalid, unsupported |
testing |
Schlüssel mit t=y (Testmodus) |
body_hash_ok |
false = Inhalt nach dem Signieren verändert, null = nicht prüfbar |
aligned_with_from |
Signaturdomain passt zur From-Domain (relaxed bzw. laut DMARC adkim) |
result, reason |
Ergebnis dieser Signatur. Ein fehlender Schlüssel ergibt permerror |
4.6 dmarc – DMARC (RFC 7489)
| Feld | Inhalt |
|---|---|
result |
pass, fail, none (kein Eintrag), permerror (z. B. mehrere From-Adressen), temperror |
from_domain, org_domain |
Domain aus header_from und ihre Organisationsdomain |
record, record_source |
gefundener DMARC-Eintrag und die Domain, bei der er stand |
published_policy, subdomain_policy |
veröffentlichte Werte p= und sp= |
effective_policy |
für diese From-Domain geltende Richtlinie (bei Subdomains sp=, sonst p=) |
pct, adkim, aspf |
Anteil sowie Ausrichtungsmodus (r = relaxed, s = strict) |
disposition |
was ein Empfänger nach DMARC mit dieser Mail tun soll. none bei pass oder bei p=none, sonst quarantine bzw. reject. Bei pct < 100 mit Anteil, z. B. reject (50%) |
spf_aligned, dkim_aligned |
ob SPF bzw. DKIM bestanden haben und zur From-Domain passen |
effective_policy = reject bei result = pass ist richtig: Die Richtlinie ist veröffentlicht, wird aber nicht angewendet (disposition = none). Ein Empfänger kann aus anderen Gründen trotzdem anders entscheiden.
4.7 arc – Authenticated Received Chain (RFC 8617)
ARC hilft bei weitergeleiteten Mails (Verteiler, Weiterleitungen), bei denen SPF oder DKIM unterwegs brechen. Jeder Weiterleiter hält fest, was er gesehen hat, und versiegelt das.
| Feld | Inhalt |
|---|---|
status |
not_present (keine ARC-Kopfzeilen, bei direkter Zustellung normal), pass (Kette vollständig und kryptografisch gültig), fail, permerror (Kopfzeilen fehlerhaft), temperror |
chain_validation |
Ergebnis der Kettenprüfung (none, pass, fail) |
sealer_trust |
immer unknown. Ob einem Weiterleiter vertraut wird, entscheidet jeder Empfänger selbst |
instances[] |
je Station i, seal_domain/seal_selector, ams_domain/ams_selector, ams_verified (Nachrichtensignatur gültig), as_verified (Siegel gültig), cv (gemeldeter Kettenstatus) und aar (vom Weiterleiter festgehaltene Ergebnisse spf/dkim/dmarc samt authserv_id) |
Das ARC-Ergebnis verändert nie das eigene DMARC-Ergebnis. Auch eine gültige Kette macht aus dmarc.result = fail kein pass.
4.8 return_path_dns – Kann die Absenderadresse Rückmeldungen empfangen?
Prüft die Domain aus smtp.mail_from (Unzustellbarkeitsmeldungen gehen dorthin).
status:pass,warn,fail,temperror,not_tested(Null-Sender).reasons[], mögliche Gründe:nxdomain: Domain existiert nichtnull_mx: Domain nimmt ausdrücklich keine Mails anno_mx_implicit_a: kein MX, nur A/AAAA vorhanden (warn)no_mx_no_a: weder MX noch A/AAAAmx_targets_unresolvable: MX-Ziele lösen nicht aufsome_mx_targets_unresolvable: einige MX-Ziele lösen nicht aufmx_is_cname:<host>: MX-Ziel ist ein CNAME (warn)cname_loop,cname_chain_too_long: Problem mit der CNAME-Kette
cname_chain,final_name,mx[](pref,host,is_cname,a,aaaa),implicit_mx: die gefundenen DNS-Daten.
Diese Prüfung ist unabhängig von SPF: Ein Server kann per SPF erlaubt sein, auch wenn die Domain keine Mails empfangen kann.
4.9 fcrdns und helo – Identität des sendenden Servers
fcrdns(Forward-Confirmed Reverse DNS): PTR der IP (ptr) und ob ein PTR-Name wieder auf dieselbe IP zeigt (confirmed).failheißt: kein PTR oder kein Rückverweis. Viele Empfänger lehnen solche Mails ab.helo, aufgeteilt in Teilprüfungen:syntax:fqdn,address_literal,invalidodermissingresolves: Name löst aufmatches_client_ip: zeigt auf die einliefernde IPstatus:pass(alles passt),warn(Name gültig, zeigt aber auf andere IPs oder ist ein Adressliteral),fail(fehlt, ungültig, nicht auflösbar)helo.status = warnist bei großen Anbietern (z. B. Microsoft 365) üblich und kein Fehler der Konfiguration.
4.10 ip_protocol – IPv4/IPv6
requested:ipv4bzw.ipv6, wenn anip4./ip6.gesendet wurde, sonstauto.used: tatsächlich genutzte Version.status:pass: wie angefordert bzw.autonot_tested: angeforderte Version konnte nicht genutzt werden. Praktisch nur bei Umwegen über Zwischenserver möglich, denn dieip4./ip6.-Adressen sind nur über die jeweilige Version erreichbar.
4.11 dnsbl – Blacklists
Eigene DNS-Abfrage bei jeder Liste:
- Spamhaus ZEN (über den Spamhaus Data Query Service, IPv4 und IPv6)
- SpamCop
- SpamRATS
- Mailspike
- PSBL
- UCEPROTECT Level 1
| Feld | Inhalt |
|---|---|
listed_count, error_count, no_response_count |
Zusammenfassung |
lists[].status |
listed (gelistet), not_listed (nur bei ausdrücklicher Negativantwort der Liste), no_response (Liste hat nicht geantwortet), error (Fehlerantwort, z. B. Abfrage abgelehnt), not_supported (Liste prüft keine IPv6-Adressen) |
codes, meaning, evidence |
Antwortcodes der Liste, ihre Bedeutung und ggf. Begründungstext |
query |
abgefragter DNS-Name. [key] steht für einen nicht veröffentlichten Zugangsschlüssel und ist kein Fehler im Abfragenamen |
rcode, resolver, duration_ms |
DNS-Antwortcode, abfragender Resolver (system oder list_nameservers) und Dauer |
blacklistmaster enthält zusätzlich das Ergebnis des externen Dienstes blacklistmaster.com (über 100 Listen, eigenes Format). Bei internen Selbsttests steht dort "status": "skipped".
4.12 domain_security – Konfiguration der Absenderdomain
Geprüft wird die Domain aus header_from. Das sind Konfigurationsprüfungen der Domain, kein Nachweis über diese Mail. MTA-STS und DANE schützen zum Beispiel Mails, die an diese Domain gehen.
| Feld | Inhalt |
|---|---|
mx |
MX-Server der Domain |
dnssec.status |
signed (Antwort DNSSEC-validiert), unsigned, bogus (Signatur fehlerhaft oder DNS-Ausfall), temperror |
mta_sts |
pass = TXT _mta-sts und Policy per HTTPS gültig, mode=enforce, alle MX abgedeckt. warn = mode=testing/none. fail = Policy nicht abrufbar, ungültig oder MX nicht abgedeckt (mx_not_covered) |
tls_rpt |
TXT _smtp._tls mit rua=: pass, fail, not_present |
dane |
TLSA-Einträge _25._tcp.<mx> je MX. pass = für alle MX vorhanden und DNSSEC-validiert, warn = nur für einige MX, fail = TLSA ohne gültiges DNSSEC (unwirksam) |
bimi |
TXT default._bimi mit Logo-URL (logo_url, vmc_url): pass, fail, not_present |
4.13 mta_checks – Gegenprobe
Ergebnisse der Standardfilter des Mailservers (SPF, DKIM, DMARC) zum Vergleich mit der eigenen Prüfung. In mismatch steht, wo sie abweichen. Erwartet ist eine Liste ohne Einträge. Eine bekannte Ausnahme: Fehlt ein DKIM-Schlüssel, meldet der Filter fail statt permerror.
5. Hinweise zur Bewertung
- Alle Ergebnisse gelten für diese eine Mail und den Zeitpunkt
checked_at. Andere Server oder Versandwege derselben Domain können anders konfiguriert sein. - Für die Zustellbarkeit am wichtigsten:
dmarc.result = passdkim.result = passmitkey_strength = okspf.result = passfcrdns.status = passreturn_path_dns.status = pass- keine Einträge in
dnsbl
warnist ein Hinweis, kein Fehler, besonders beihelounddomain_security.- Fehlende Felder in alten Datensätzen (
software_versionfehlt oder1.x) bedeuten nicht „nicht bestanden“, sondern „damals nicht geprüft“.