Ir al contenido
Español

Envío mediante SMTP

Antes de conectarte

Envía correos desde tu aplicación mediante SMTP con el usuario y la contraseña del buzón. Las claves API y los tokens de cuenta no sirven para SMTP.

Crea un buzón activo en un dominio conectado y completa la verificación de sus registros DNS. El usuario es la dirección completa, por ejemplo [email protected]. Usa la contraseña del buzón, no la de la cuenta de correo. Sustituye las direcciones de ejemplo por las tuyas; la contraseña se introduce al ejecutar el programa sin mostrarse.

Servidor, puertos y cifrado

Usa mail.adapt-mail.com para cualquier dominio conectado. El puerto 465 inicia TLS directamente; el puerto 587 utiliza STARTTLS antes de la autenticación. Elige una opción. Mantén activada la verificación del certificado.

En los ejemplos, la dirección From y el remitente del sobre SMTP coinciden con el usuario del buzón. Puedes cambiar el nombre visible del remitente. El puerto 25 se usa entre servidores de correo; para tu aplicación, usa 465 o 587.

SMTP_HOST = "mail.adapt-mail.com"
SMTP_PORT = 465
SMTP_USER = "[email protected]"
SMTP_PASSWORD = "<mailbox-password>"
SMTP_FROM = "[email protected]"
SMTP_FROM_NAME = "Example"
465: implicit TLS
587: STARTTLS

Python: envío por el puerto 465

El ejemplo solo utiliza la biblioteca estándar de Python 3. Guárdalo como send_mail.py y ejecuta python3 send_mail.py. Para envíos automáticos, obtén la contraseña de la configuración segura de tu aplicación; no la guardes en Git ni en los registros.

import smtplib
import ssl
from getpass import getpass
from email.message import EmailMessage
from email.utils import formataddr, make_msgid, formatdate
username = "[email protected]"
password = getpass("SMTP password: ")
recipient = "[email protected]"
message = EmailMessage()
message["From"] = formataddr(("Example", username))
message["To"] = recipient
message["Subject"] = "SMTP test"
message["Date"] = formatdate(localtime=False, usegmt=True)
message["Message-ID"] = make_msgid(domain=username.split("@")[1])
message.set_content("Hello! This message was sent through Adapt Mail SMTP.")
with smtplib.SMTP_SSL(
"mail.adapt-mail.com", 465, timeout=30,
context=ssl.create_default_context(),
) as smtp:
smtp.login(username, password)
refused = smtp.send_message(
message, from_addr=username, to_addrs=[recipient],
)
print("Rejected recipients:", refused)

Python: conexión por el puerto 587

Para STARTTLS, conserva la preparación del mensaje del ejemplo anterior y sustituye el bloque with smtplib.SMTP_SSL por el siguiente. Con smtplib.SMTP, la contraseña solo se envía después de que STARTTLS se complete correctamente.

with smtplib.SMTP("mail.adapt-mail.com", 587, timeout=30) as smtp:
smtp.ehlo()
smtp.starttls(context=ssl.create_default_context())
smtp.ehlo()
smtp.login(username, password)
refused = smtp.send_message(
message, from_addr=username, to_addrs=[recipient],
)
print("Rejected recipients:", refused)

HTML y archivos adjuntos

Añade la versión HTML después de set_content y el archivo adjunto antes del envío. Conserva la versión de texto para los clientes sin HTML. Usa HTML de confianza o escapa los datos que insertes.

message.add_alternative(
"<p>Hello! This message was sent through <strong>Adapt Mail</strong>.</p>",
subtype="html",
)
with open("document.pdf", "rb") as attachment:
message.add_attachment(
attachment.read(), maintype="application", subtype="pdf",
filename="document.pdf",
)

Resultado, límites y mensajes enviados

Si send_message termina correctamente, el servidor SMTP ha aceptado el mensaje; no significa que haya llegado a la bandeja de entrada del destinatario. El diccionario refused contiene los destinatarios rechazados; si se rechazan todos, Python lanza SMTPRecipientsRefused.

SMTP y API comparten los límites de cada buzón: hasta 30 mensajes en una ventana móvil de 60 segundos, 50 destinatarios por mensaje y 1000 destinatarios en una ventana móvil de 24 horas, o 5000 con el límite ampliado activado. Se cuentan todos los destinatarios To, Cc y Bcc.

El envío directo por SMTP no guarda por sí solo una copia en Enviados. Los clientes de correo lo hacen mediante IMAP; la API de Adapt Mail guarda la copia por separado.

Errores SMTP

535
Error de autenticación: comprueba la dirección completa, la contraseña del buzón y su disponibilidad.
451
Fallo temporal, incluido el exceso de los límites de envío. Reintenta más tarde, tras una espera.
550 / 5xx
Rechazo permanente: comprueba las direcciones, los permisos del remitente y el texto de la respuesta. Más de 50 destinatarios se rechazan después de DATA. Corrige la causa antes de reintentar.
TLS / timeout
Comprueba mail.adapt-mail.com, el puerto, el modo TLS y el acceso saliente desde el servidor de tu aplicación. Usa SMTP_SSL en 465 o SMTP con STARTTLS en 587.

Lee la respuesta completa del servidor SMTP. Reintenta los fallos temporales tras una espera. Si la conexión se corta después de transmitir el mensaje y se desconoce el resultado, no lo reenvíes a ciegas: SMTP no tiene Idempotency-Key y el reintento puede crear un duplicado.