BlogHome

Como enviar emails en Rust

2022-05-25

Este post ilustra como usar la librería lettre para enviar emails con rust. Sigue los ejemplos de la documentación para enviar por smtp, usando credenciales de un correo de gmail:

Email simple

#Cargo.toml
[package]
name = "example-email"
version = "0.1.0"
edition = "2021"

[dependencies]
lettre = "0.10.0-rc.6"
anyhow = "1.0.57"
//example-email-simple.rs
use lettre::{transport::smtp::authentication::Credentials, Message, SmtpTransport, Transport};
use anyhow::Result;

fn main() -> Result<()> {
    let email = Message::builder()
        .from("NoBody <nobody@domain.tld>".parse()?)
        .to("Hei <hei@domain.tld>".parse()?)
        .subject("Simple email test from Rust")
        .body(String::from("Be happy!"))?;

    let creds = Credentials::new(
            "smtp_username".to_string(),
            "smtp_password".to_string()
            );

    // Open a remote connection to the SMTP relay server
    let mailer = SmtpTransport::relay("smtp.gmail.com")?
        .credentials(creds)
        .build();

    // Send the email
    match mailer.send(&email) {
        Ok(_) => Ok(println!("Email sent successfully!")),
        Err(e) => panic!("Could not send email: {:?}", e),
    }
}

Email con adjunto

Para componer un email con ficheros adjuntos usarermos los métodos Multipart, SinglePart y Attachment:

//example-mail.rs
use lettre::message::{header, Message};
use lettre::message::{header::ContentType, MultiPart, SinglePart, Attachment};
use lettre::transport::smtp::authentication::Credentials;
use lettre::{SmtpTransport, Transport};
use anyhow::Result;
use std::fs;

fn main() -> Result<()> {
    let filename = "invoice.pdf";
    let filebody = fs::read(&filename)?;
    let content_type = ContentType::parse("application/pdf").unwrap();
    let attachment = Attachment::new(filename.to_string())
        .body(filebody, content_type);
    let message = String::from("Hello there!!");

    let email = Message::builder()
        .from("mi_email@gmail.com".parse().unwrap())
        .to("desintatrio@email.com".parse().unwrap())
        .subject("Email with attachment test from Rust")
        .multipart(
            MultiPart::mixed()
                .singlepart(
                    SinglePart::builder()
                        .header(header::ContentType::TEXT_PLAIN)
                        .body(message), 
                )
                .singlepart(attachment),
        )
        .unwrap();

    let creds = Credentials::new(
            "smtp_username".to_string(),
            "smtp_password".to_string()
            );

    // Open a remote connection to gmail
    let mailer = SmtpTransport::relay("smtp.gmail.com")?
        .credentials(creds)
        .build();

    // Send the email
    match mailer.send(&email) {
        Ok(_) => Ok(println!("Email sent successfully!")),
        Err(e) => panic!("Could not send email: {:?}", e),
    }
}

Referencias:

This work is licensed under CC BY-NC-SA 4.0.