Vous avez décidé d'ajouter la vérification des e-mails à votre application. Excellent choix : c'est la modification la plus efficace que vous puissiez faire pour améliorer la qualité des inscriptions, réduire les rebonds et prévenir la fraude.
Ce guide vous fournit du code prêt pour la production à intégrer dans n'importe quelle stack. Python, JavaScript, PHP, cURL : choisissez votre langage et copiez le code.
Pourquoi la vérification côté serveur est essentielle
Avant d'écrire la moindre ligne de code, soyons clairs sur un point : la validation des e-mails côté client ne suffit pas.
// Ce N'EST PAS une vérification : il s'agit simplement d'une vérification de la syntaxe
const isValid = /^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(email);
// "thisdoesnotexist8472@gmail.com" → true (la syntaxe est correcte, mais la boîte mail n'existe pas)
Les expressions régulières côté client détectent les erreurs de format. Elles ne permettent pas de savoir si la boîte mail existe réellement. Pour cela, il faut une vérification au niveau SMTP — ce qui nécessite un appel d'API côté serveur.
Obtenir votre clé API
Commencez par vous inscrire sur email-validaton.com puis récupérez votre clé API depuis le tableau de bord. Les comptes gratuits donnent droit à 100 vérifications par mois.
Gardez votre clé API secrète : elle ne doit jamais apparaître dans le JavaScript côté client. Appelez toujours l'API de vérification depuis votre backend.
Vérification d'un e-mail unique
Python
import requests
de typing import Optional
def verify_email(email: str, api_key: str) -> dict:
"""Vérifie une seule adresse e-mail."""
resp = requests.get(
"https://email-validaton.com/api/v1/verify",
params={"email": email},
headers={"Authorization": f"Bearer {api_key}"},
timeout=15,
)
resp.raise_for_status()
return resp.json()
# Utilisation
result = verify_email("user@example.com", "YOUR_API_KEY")
print(f"Statut : {result['status']}")
print(f"Score : {result['score']}/10")
print(f"Confiance : {result.get('confidence', 'N/A')}")
if result["status"] == "valid":
# Poursuivre la création du compte
create_user(email)
elif result["status"] ( ("invalid", "disposable"):
# Rejeter ou signaler
raise ValueError(f"Email invalide : {result['reason']}")
JavaScript (Node.js)
async function verifyEmail(email, apiKey) {
const url = new URL("https://email-validaton.com/api/v1/verify");
url.searchParams.set("email", email);
const resp = await fetch(url, {
headers: { Authorization: `Bearer ${apiKey}` },
});
if (!resp.ok) throw new Erreur(`Erreur API : ${resp.status}`);
return resp.json();
}
// Utilisation
const result = await verifyEmail("user@example.com", process.env.EV_API_KEY);
console.log(`Statut : ${result.status}, Score : ${result.score}/10`);
if (result.status === "valid") {
await db.users.insert({ email, verified: true });
} else {
throw new Erreur(result.raison || "Échec de la vérification de l'e-mail");
}
PHP
function verify_email(string $email, string $api_key): array {
$url = "https://email-validaton.com/api/v1/verify?email=" . urlencode($email);
$ch = curl_init($url);
curl_setopt_array($ch, [
CURLOPT_RETURNTRANSFER => true,
CURLOPT_HTTPHEADER => ["Authorization: Bearer $api_key"],
CURLOPT_TIMEOUT => 15,
]);
$body = curl_exec($ch);
$http_code = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);
if ($http_code !== 200) {
throw new RuntimeException("L'API a renvoyé $http_code");
}
return json_decode($body, true);
}
// Utilisation
$result = verify_email("user@example.com", getenv("EV_API_KEY"));
echo "Statut: {$result['status']}, Score: {$result['score']}/10\n";
cURL (CLI / scripts shell)
#!/bin/bash
API_KEY="votre_clé_api"
EMAIL="user@example.com"
curl -s -H "Authorization: Bearer $API_KEY" \
"https://email-validaton.com/api/v1/verify?email=$EMAIL" | python3 -m json.tool
Comprendre la réponse
Chaque vérification renvoie une structure JSON cohérente :
{
"email": "user@gmail.com",
"status": "valid",
"score": 9,
"confidence": "high",
"reason": "La boîte mail existe et accepte les messages",
"mx_server": "gmail-smtp-in.l.google.com",
"duration_ms": 287,
"disposable": false,
"role_account": false,
"free_provider": true
}
Explication des champs clés
| Champ | Valeurs | Signification |
|---|---|---|
status |
valid, invalid, catch_all, unknown, risky, disposable, over_quota, error |
Le résultat de la vérification |
score |
0–10 | Score de qualité global. 8+ = excellent, 5 à 7 = modéré, <5 = risqué |
confidence |
high, medium, low |
Le degré de fiabilité du résultat |
reason |
Chaîne lisible par l'humain | Pourquoi ce statut a été attribué |
disposable |
booléen | Adresse e-mail temporaire |
role_account |
booléen | info@, support@, admin@, etc. |
free_provider |
booléen | Gmail, Yahoo, Outlook, etc. |
Modèles d'intégration
Modèle 1 : validation du formulaire d'inscription (le plus courant)
@app.route("/register", methods=["POST"])
def register():
email = request.formulaire["email"]
password = request.formulaire["password"]
# 1. Vérification de la syntaxe (rapide, locale)
if "@" Paiement Lemon Squeezy : ( email ou "." Paiement Lemon Squeezy : ( email.split("@")[-1]:
return jsonify({"error": "Format d'adresse e-mail invalide"}), 400
# 2. Vérification SMTP (appel API)
try:
result = verify_email(email, current_app.config["EV_API_KEY"])
except requests.RequestException:
# L'API est indisponible — ne pas bloquer les inscriptions, simplement signaler pour examen
create_user(email, password, flags=["unverified"])
return redirect(url_for("dashboard"))
# 3. Logique métier selon le résultat
if result["status"] == "valid":
create_user(email, password, verified=True)
return redirect(url_for("welcome"))
if result["status"] == "disposable":
return jsonify({
"error": "Veuillez utiliser une adresse e-mail permanente"
}), 400
if result["status"] == "invalid":
return jsonify({
"error": "Cette adresse e-mail semble ne pas exister"
}), 400
# Catch-all, inconnu, risqué — autoriser mais signaler
create_user(email, password, flags=[result["status"]])
return redirect(url_for("welcome"))
Modèle 2 : vérification asynchrone (non bloquante)
En production à grande échelle, vous ne voulez pas que les utilisateurs attendent l'appel à l'API :
import threading
def verify_async(email: str, api_key: str, user_id: int):
"""Vérifier l'e-mail en arrière-plan et mettre à jour l'enregistrement utilisateur."""
try:
result = verify_email(email, api_key)
db.users.update(user_id, {
"email_status": result["status"],
"email_score": result["score"],
"verified_at": datetime.utcnow(),
})
except Exception as e:
logger.error(f"La vérification en arrière-plan a échoué pour {user_id}: {e}")
# Dans votre gestionnaire d'inscription :
user = create_user(email, password)
threading.Thread(
cible=verify_async,
args=(email, api_key, user.id),
daemon=True,
).start()
Modèle 3 : traitement des listes en masse
Pour nettoyer de grandes listes via le point de terminaison d'envoi en masse :
import requests
import time
def bulk_verify(file_path: str, api_key: str) -> str:
"""Téléversez un fichier pour une vérification en masse. Renvoie l'ID de la tâche."""
with open(file_path, "rb") as f:
resp = requests.post(
"https://email-validaton.com/api/v1/bulk",
files={"file": f},
headers={"Authorization": f"Bearer {api_key}"},
)
return resp.json()["job_id"]
def wait_for_results(job_id: str, api_key: str, poll_sec: int = 5):
"""Interrogez jusqu'à ce que la tâche en masse soit terminée, puis téléchargez les résultats."""
while True:
resp = requests.get(
f"https://email-validaton.com/api/v1/bulk/status/{job_id}",
headers={"Authorization": f"Bearer {api_key}"},
)
data = resp.json()
if data["status"] ( ("completed", "failed", "cancelled"):
return data
time.sleep(poll_sec)
# Utilisation
job_id = bulk_verify("my_list.csv", API_KEY)
result = wait_for_results(job_id, API_KEY)
# Télécharger le fichier de résultats
download = requests.get(result["result_url"])
Gestion des erreurs & bonnes pratiques
Gestion des délais d'attente
L'API de vérification répond généralement en 200-800ms. Définissez un délai d'attente de 10-15 secondes pour gérer les problèmes réseau avec souplesse.
Limitation du débit
Les comptes gratuits sont limités à 100/jour. Les forfaits payants vont de 5,000 à 500,000/mois. L'API renvoie 429 Too Many Requests when you exceed your limit.
Logique de nouvelle tentative
En cas d'échecs temporaires (erreurs réseau, 503), réessayez jusqu'à 3 fois avec un backoff exponentiel :
import time
de requests.exceptions import RequestException
def verify_with_retry(email, api_key, max_retries=3):
for attempt ( range(max_retries):
try:
return verify_email(email, api_key)
except RequestException:
if attempt == max_retries - 1:
raise
time.sleep(2 ** attempt)
Ne bloquez pas les inscriptions en cas d'échec de l'API
Si l'API de vérification est temporairement indisponible, ne bloquez pas l'inscription des utilisateurs. Procédez plutôt ainsi :
1. Autorisez l'inscription et marquez le compte comme « en attente de vérification »
2. Lancez la vérification de manière asynchrone une fois l'API rétablie
3. Informez l'utilisateur si son adresse e-mail s'avère invalide après coup
Bloquer les inscriptions pendant une panne de l'API fait perdre de vrais utilisateurs.
Conclusion
La vérification des adresses e-mail n'est pas facultative pour les applications en production. Les adresses invalides entraînent des rebonds, les adresses jetables favorisent les abus, et les listes non vérifiées nuisent à votre réputation d'expéditeur.
Les modèles d'intégration présentés dans ce guide couvrent les cas d'usage les plus courants. Copiez le code, adaptez-le à votre stack et commencez à vérifier chaque adresse e-mail qui entre dans votre système.
Prêt à intégrer ? Obtenez votre clé API gratuite — 100 vérifications incluses.