Guide de migration
Migrer de Postmark vers Mail.Land
Postmark et Mail.Land acceptent tous deux un appel d’envoi en JSON : la plupart des champs se correspondent donc un à un. Ce guide liste chaque champ courant, les réglages SMTP à modifier et les différences qui demandent une modification du code.
# Before (Postmark)
SMTP_HOST=smtp.postmarkapp.com # broadcasts: smtp-broadcasts.postmarkapp.com
SMTP_PORT=587 # STARTTLS
SMTP_USER=<Server API token, or SMTP token access key>
SMTP_PASS=<Server API token, or SMTP token secret key>
# After (Mail.Land)
SMTP_HOST=smtp.mail.land
SMTP_PORT=587 # STARTTLS
SMTP_USER=apikey # any value; Mail.Land ignores it
SMTP_PASS=ml_pet_... # transactional; use an ml_pem_ key for broadcastsLes notions de Postmark dans Mail.Land
| Postmark | Mail.Land |
|---|---|
| Server et Server API token | Espace de travail et clés API (identifiants), chacune limitée à l’API ou au SMTP, à des domaines et à des adresses IP |
| Flux de messages (transactionnel, diffusion) | Le flux de la clé : transactionnel (ml_pet_) ou marketing (ml_pem_) |
| Signatures d’expéditeur et domaines | Domaine vérifié (SPF, DKIM, DMARC et chemin de retour) |
| Modèles et mises en page (Mustachio) | Modèles avec variables {{name}} |
| Suppressions par flux de messages | Suppressions avec un type et une portée |
| Webhooks | Webhooks signés en HMAC-SHA256, avec un secret par webhook |
| Flux entrant | Routes entrantes |
Créer les bonnes clés API
Chez Postmark, le champ ou l’en-tête MessageStream choisit le flux. Chez Mail.Land, c’est la clé : son préfixe indique son mode et son flux. Créez une clé par application et par flux.
| Préfixe | Usage |
|---|---|
ml_pet_ | Production, transactionnel : reçus, réinitialisations de mot de passe, alertes. Jusqu’à 5 destinataires par requête. |
ml_pem_ | Production, marketing : newsletters et envois en masse avec send-batch, jusqu’à 10 000 destinataires par appel. |
ml_set_ | Test, transactionnel : avec sandboxBehavior sur LogOnly (valeur par défaut), les requêtes sont acceptées et journalisées mais jamais livrées. Utilisez-la pour vos tests d’intégration. |
Chaque clé peut être limitée à l’API, au SMTP ou aux deux, à des domaines choisis et à des adresses IP connues. Une clé n’est affichée qu’une fois, et Mail.Land n’en conserve qu’une empreinte (hash).
Basculer le SMTP : changer l’hôte et les identifiants
Postmark utilise un Server API token ou un SMTP token, et un en-tête pour choisir le flux. Mail.Land utilise votre clé API comme mot de passe, ignore le nom d’utilisateur et déduit le flux de la clé.
| Paramètre | Postmark | Mail.Land |
|---|---|---|
| Hôte | smtp.postmarkapp.com, ou smtp-broadcasts.postmarkapp.com pour les diffusions | smtp.mail.land |
| Port | 25, 587 ou 2525, avec STARTTLS | 587 avec STARTTLS |
| Nom d’utilisateur | Server API token, ou access key du SMTP token | N’importe quelle valeur, par exemple apikey |
| Mot de passe | Server API token, ou secret key du SMTP token | Une clé API Mail.Land avec SMTP activé |
| Flux | En-tête X-PM-Message-Stream | La clé : ml_pet_ pour le transactionnel, ml_pem_ pour le marketing |
Mail.Land n’accepte l’authentification qu’après STARTTLS. Mail.Land ne tient pas compte de l’en-tête X-PM-Message-Stream : c’est la clé qui détermine le flux. Les messages peuvent atteindre 15 Mio.
Basculer l’appel d’API
Les deux API acceptent du JSON. Postmark utilise des noms en PascalCase et l’en-tête X-Postmark-Server-Token ; Mail.Land utilise des noms en camelCase et l’en-tête X-API-Key. Voici le même message dans les deux, ainsi qu’un envoi avec modèle.
curl -X POST https://api.postmarkapp.com/email \
-H "X-Postmark-Server-Token: $POSTMARK_SERVER_TOKEN" \
-H "Accept: application/json" \
-H "Content-Type: application/json" \
-d '{
"From": "Your Shop <[email protected]>",
"To": "[email protected]",
"ReplyTo": "[email protected]",
"Subject": "Order 12345 has shipped",
"TextBody": "Your order is on its way.",
"HtmlBody": "<p>Your order is on its way.</p>",
"Tag": "order-shipped",
"MessageStream": "outbound"
}'curl -X POST https://api.mail.land/v1/transactional/send \
-H "X-API-Key: $MAILLAND_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"from": { "email": "[email protected]", "name": "Your Shop" },
"to": [{
"email": "[email protected]", "name": "Jane",
"variables": { "orderNumber": "12345" }
}],
"replyTo": "[email protected]",
"subject": "Order {{orderNumber}} has shipped",
"textContent": "Your order {{orderNumber}} is on its way.",
"htmlContent": "<p>Your order {{orderNumber}} is on its way.</p>",
"tags": ["order-shipped"]
}'
# MAILLAND_API_KEY=ml_pet_... (production, transactional)Correspondance des champs de l’appel d’envoi
De POST /email et /email/withTemplate à POST /v1/transactional/send.
| Postmark | Mail.Land | Remarque |
|---|---|---|
X-Postmark-Server-Token: <token> | X-API-Key: <key> | Un autre en-tête. |
From | from.email, from.name | Séparez le nom affiché de l’adresse. L’adresse doit appartenir à un domaine vérifié. |
To | to[].email, to[].name | Un tableau d’objets au lieu d’une chaîne séparée par des virgules. Jusqu’à 5 destinataires par requête avec une clé transactionnelle ; chacun reçoit une copie distincte. |
Cc, Bcc | Aucun | Non pris en charge. Envoyez un message distinct à chaque destinataire. |
Subject | subject | Obligatoire, sauf si vous utilisez un modèle. |
HtmlBody | htmlContent | |
TextBody | textContent | |
ReplyTo | replyTo | Une seule chaîne d’adresse. Si vous utilisiez plusieurs adresses reply-to séparées par des virgules, gardez-en une. |
Tag | tags | Un tableau : un message peut donc porter plusieurs tags. |
Metadata | Aucun | Il n’y a pas de champ de métadonnées clé-valeur. Utilisez tags, ou un en-tête personnalisé. |
Headers [{ Name, Value }] | customHeaders | Un objet de noms et de valeurs d’en-têtes au lieu d’un tableau. |
TrackOpens | tracking.opens | Le choix propre au domaine pour le suivi des ouvertures est prioritaire. |
TrackLinks | tracking.clicks | Un booléen au lieu de None, HtmlAndText, HtmlOnly ou TextOnly. |
Attachments[].Name, Content, ContentType, ContentID | attachments[].fileName, content, contentType, contentId, inline | Contenu Base64 comme avant. Indiquez inline: true pour une image intégrée. Jusqu’à 10 pièces jointes et 10 Mio au total. |
MessageStream | Aucun | La clé détermine le flux : ml_pet_ ou ml_pem_. |
TemplateId, TemplateAlias | templateId | Recréez d’abord le modèle dans Mail.Land ; il reçoit un nouvel identifiant. |
TemplateModel | variables, to[].variables | Valeurs plates uniquement, car les variables n’ont ni sections ni boucles. |
POST /email/batch (jusqu’à 500 messages) | POST /v1/transactional/send-batch | Un modèle différent : un contenu commun pour jusqu’à 10 000 destinataires, chacun avec ses variables, envoyé avec une clé marketing. Pour des messages différents, faites un appel d’envoi pour chacun. |
Aucun équivalent | scheduledAt | Programmez un message jusqu’à 7 jours à l’avance. |
Aucun équivalent | En-tête X-Idempotency-Key | Pendant la durée de conservation, une nouvelle tentative avec la même clé renvoie la réponse d’origine au lieu d’envoyer à nouveau. |
Mail.Land répond 202 Accepted avec un jobId, un identifiant de message par destinataire accepté, et les listes des destinataires acceptés et refusés.
Ajouter votre domaine et les enregistrements DNS
Ajoutez le domaine dans Mail.Land et publiez les enregistrements affichés par le tableau de bord. SPF, DKIM et DMARC doivent être vérifiés avant de pouvoir envoyer. Vous pouvez le faire pendant que Postmark envoie encore.
| Enregistrement | Nom | Valeur | Remarque |
|---|---|---|---|
| SPF (TXT) | yourdomain.com | include:spf.mlnd.net | Ajoutez l’include à votre enregistrement SPF existant. Un domaine ne doit avoir qu’un seul enregistrement SPF. |
| DKIM (TXT) | mlnd._domainkey.yourdomain.com | v=DKIM1; k=rsa; p=... | Le sélecteur est mlnd : l’enregistrement coexiste donc avec l’enregistrement DKIM de Postmark. |
| DMARC (TXT) | _dmarc.yourdomain.com | v=DMARC1; p=... | Obligatoire. Gardez un seul enregistrement DMARC ; un enregistrement existant avec une politique suffit. |
| Chemin de retour (CNAME) | bounce.yourdomain.com | bounce.mlnd.net | Réglez-le en DNS only, sans proxy. Vérifiez que ce nom n’est pas déjà utilisé. |
Gardez les enregistrements DNS de Postmark jusqu’à la fin de la migration, et supprimez-les seulement après le départ de son dernier message.
Importer d’abord vos listes de suppression
Postmark conserve les suppressions par flux de messages. Exportez la liste de chaque flux, par exemple avec GET /message-streams/<stream>/suppressions/dump, puis importez-la dans Mail.Land avec le type et la portée correspondants, dans le tableau de bord ou avec POST /v1/transactional/suppressions/import.
| Motif chez Postmark | Type Mail.Land | Portée |
|---|---|---|
| HardBounce | HardBounce | Global |
| SpamComplaint | Complaint | Global |
| ManualSuppression sur un flux de diffusion (désabonnements) | Unsubscribe | Marketing ; ou List, qui ne s’applique qu’aux campagnes envoyées à la liste de diffusion Mail.Land correspondante |
| ManualSuppression sur un flux transactionnel | Manual | Transactional |
Importez avant votre premier envoi via Mail.Land, pour que les personnes désinscrites restent bloquées dès le départ. Les adresses déjà présentes sont ignorées, sans doublon.
Diriger vos webhooks vers Mail.Land
Ajoutez votre endpoint dans Mail.Land, choisissez les événements et vérifiez l’en-tête X-MLND-Signature avec le secret de ce webhook. Si vous protégiez votre endpoint Postmark par authentification Basic ou liste d’IP autorisées, vérifiez plutôt la signature.
| Webhook Postmark | Événement Mail.Land | Remarque |
|---|---|---|
Livraison (Delivery) | message.delivered | |
Rebond (Bounce) | message.bounced | Couvre les rebonds définitifs et temporaires. Les retards temporaires sont des message.deferred. |
Plainte pour spam (Spam complaint) | message.complained | |
Changement d’abonnement (Subscription change) | message.unsubscribed | Envoyé lorsque le destinataire se désabonne lui-même, pas pour les changements que vous faites via l’API. |
Ouverture, clic (Open, Click) | Pas encore disponible | Les événements d’ouverture et de clic figurent au catalogue mais ne sont pas envoyés aujourd’hui. |
Entrant (Inbound) | inbound.received | Configurez une route entrante pour l’adresse de réception. |
Erreur SMTP API | Aucun | Le relais SMTP refuse le message pendant la session, avec un code de réponse. |
Dédupliquez sur event_id, car une livraison relancée porte le même identifiant d’événement. Un statut peut être corrigé plus tard : continuez à traiter les événements après un événement final et comparez status_version.
Recréer vos modèles
Créez chaque modèle dans le tableau de bord Mail.Land ou avec l’API des modèles, puis envoyez-le avec templateId et variables. Chaque variable doit avoir une valeur, sinon l’envoi est refusé avec un code 422 et les noms manquants.
| Postmark | Mail.Land |
|---|---|
{{firstName}} | {{firstName}} |
{{#each items}} ... {{/each}} | Aucun |
{{#section}}, {{^section}} | Aucun |
Modèles de mise en page (layout) | Aucun |
Les variables Mail.Land sont simples : ni sections, ni boucles, ni mises en page. Passez des valeurs plates, construisez les listes dans votre application, et répétez le HTML commun d’en-tête et de pied de page dans chaque modèle.
Basculer étape par étape
- Ajoutez et vérifiez votre domaine d’envoi dans Mail.Land, en ajoutant include:spf.mlnd.net à votre enregistrement SPF existant.
- Exportez les suppressions de chaque flux de messages Postmark et importez-les.
- Créez une clé transactionnelle pour chaque application, et une clé marketing si vous envoyez des diffusions.
- Recréez vos modèles et vos webhooks.
- Créez une clé de test avec sandboxBehavior sur LogOnly, et lancez vos tests d’intégration sur Mail.Land sans livrer d’e-mail.
- Envoyez de vrais messages à des adresses que vous contrôlez et vérifiez-les dans le journal des e-mails.
- Déplacez une application ou une petite part du trafic, puis surveillez la livraison, les rebonds et les plaintes.
- Tant que les deux fournisseurs fonctionnent, synchronisez les désinscriptions dans les deux sens : copiez les nouveaux désabonnements, plaintes et rebonds de Postmark vers Mail.Land et de Mail.Land vers Postmark, et faites une synchronisation finale avant de déplacer le trafic restant.
- Vérifiez le préchauffage de votre domaine : en Free et Pro, un nouveau domaine a une limite quotidienne qui augmente par paliers, et les envois au-delà sont refusés. Planifiez la migration dans ces limites, ou demandez-nous un calendrier sur mesure. Max n’a pas de préchauffage.
- Déplacez ensuite le reste, et gardez Postmark actif jusqu’au départ de ses derniers messages.
Sources
Pages publiques de Postmark utilisées pour ce guide.
- [1]Postmark Email APIhttps://postmarkapp.com/developer/api/email-apivérifié le 4 novembre 2026
- [2]Postmark Templates APIhttps://postmarkapp.com/developer/api/templates-apivérifié le 4 novembre 2026
- [3]Postmark : envoyer des e-mails avec SMTPhttps://postmarkapp.com/developer/user-guide/send-email-with-smtpvérifié le 4 novembre 2026
- [4]Postmark : présentation des webhookshttps://postmarkapp.com/developer/webhooks/webhooks-overviewvérifié le 4 novembre 2026
- [5]Postmark Suppressions APIhttps://postmarkapp.com/developer/api/suppressions-apivérifié le 4 novembre 2026
Questions fréquentes
Puis-je continuer à envoyer via Postmark pendant mes tests ?
Oui. Vérifier un domaine dans Mail.Land n’empêche pas Postmark d’envoyer pour lui : vous pouvez faire tourner les deux et déplacer le trafic progressivement.
Mail.Land prend-il en charge cc et bcc ?
Pas dans l’appel d’envoi. Chaque destinataire reçoit une copie distincte : envoyez donc un message séparé là où vous utilisiez cc ou bcc.
Comment remplacer mon flux de diffusion ?
Utilisez une clé marketing (ml_pem_) avec send-batch pour les envois par API, ou créez une campagne dans le tableau de bord avec le plan Pro ou Max.
Existe-t-il un SDK officiel Mail.Land ?
Pas encore. La documentation propose des exemples prêts à copier pour l’API REST en cURL, Node.js, Python, PHP, C#, Java et Go, et toute bibliothèque SMTP fonctionne avec le relais.
Prêt à quitter Postmark ?
Créez un compte gratuit et envoyez votre premier test dès aujourd’hui. Si vous souhaitez de l’aide, décrivez-nous votre configuration.