Skip to content

sendry-dev/sendry-rust

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

2 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Sendry Rust SDK

The official Rust crate for the Sendry email API.

Crates.io docs.rs License

Installation

cargo add sendry

Or add to Cargo.toml:

[dependencies]
sendry = "0.1"
tokio = { version = "1", features = ["full"] }

Requires Rust 1.75+. Async only — built on reqwest + tokio.

Quick start

use sendry::{Sendry, SendEmail};

#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
    let client = Sendry::new(std::env::var("SENDRY_API_KEY")?);

    let resp = client.emails().send(SendEmail {
        from:    "hello@yourdomain.com".into(),
        to:      vec!["user@example.com".into()],
        subject: "Welcome".into(),
        html:    Some("<p>Thanks for signing up.</p>".into()),
        text:    Some("Thanks for signing up.".into()),
        ..Default::default()
    }).await?;

    println!("sent: {}", resp.id);
    Ok(())
}

Configuration

use std::time::Duration;

let client = Sendry::builder()
    .api_key(std::env::var("SENDRY_API_KEY")?)
    .base_url("https://api.sendry.online")
    .timeout(Duration::from_secs(30))
    .max_retries(2)
    .build()?;

Resources

client.emails()      // send, send_batch, get, list
client.domains()     // create, verify, get, list, delete
client.templates()   // create, get, list, delete
client.contacts()    // upsert, get, list, delete
client.audiences()   // create, get, list, delete
client.campaigns()   // create, get, list, send
client.webhooks()    // create, get, list, delete

Error handling

use sendry::Error;

match client.emails().send(req).await {
    Ok(resp) => println!("sent: {}", resp.id),
    Err(Error::Authentication(msg)) => eprintln!("auth: {msg}"),
    Err(Error::Validation { details, .. }) => eprintln!("validation: {details:?}"),
    Err(Error::RateLimit { retry_after, .. }) => {
        tokio::time::sleep(retry_after.unwrap_or_default()).await;
    }
    Err(Error::Api { status, message, .. }) => eprintln!("API {status}: {message}"),
    Err(Error::Network(e)) => eprintln!("network: {e}"),
    Err(e) => eprintln!("{e}"),
}

Error::is_retryable() returns true for Network, RateLimit, and Api errors with 5xx status.

Webhook signature verification

use sendry::verify_webhook_signature;

let valid = verify_webhook_signature(
    request_body.as_bytes(),
    request.headers().get("x-sendry-signature").unwrap().to_str()?,
    &webhook_secret,
);

if !valid {
    return Err(StatusCode::UNAUTHORIZED.into());
}

Constant-time comparison via the subtle crate.

Feature flags

Flag Default Description
native-tls yes Use the system TLS stack
rustls no Use pure-Rust TLS (no system deps)
[dependencies]
sendry = { version = "0.1", default-features = false, features = ["rustls"] }

License

MIT — see LICENSE.

About

Official Rust crate for the Sendry email API

Resources

License

Stars

Watchers

Forks

Packages

 
 
 

Contributors

Languages