# envelopwd
[](https://crates.io/crates/envelopwd)
[](https://docs.rs/envelopwd)
[](LICENSE)
`envelopwd` is a robust, lightweight Rust library for parsing, validating, and manipulating email addresses and mailboxes.
It was created to address limitations encountered while using the [email_address](https://crates.io/crates/email_address) crate - particularly the lack of `sqlx` integration and the fact that both plain email addresses and name-addr formats were parsed into the same type, which can be awkward in certain contexts.
This crate provides a cleaner separation between address types, adds sqlx support, and introduces additional functionality aimed at improving ergonomics and practical usability.
A significant portion of the parsing logic and test coverage was inspired by and adapted from [email_address](https://crates.io/crates/email_address). Many thanks to its authors for building such a solid and well-tested foundation.
## Features
* **Strict Validation**: Checks local-part and domain lengths, character sets, and subdomain formatting.
* **Mailbox Support**: Easily parse "Name <email@example.com>" formats.
* **Serialization**: Optional Serde support for easy integration with JSON and other formats.
* **Internationalization**: Supports non-ASCII characters in local parts and domains (UTF-8).
* **Zero Dependencies**: Uses only `thiserror` for clean error reporting.
* **URI Encoding**: Built-in support for converting email addresses to `mailto:` links.
* **Case Sensitivity Awareness**: Properly handles case-insensitive domains while preserving the (rarely used but valid) case sensitivity of local parts.
## Installation
Add this to your `Cargo.toml`:
```toml
[dependencies]
envelopwd = "0.1"
```
To enable optional features like Serde or sqlx, use:
```toml
[dependencies]
envelopwd = { version = "0.1", features = ["serde", "sqlx"] }
```
## Quick Start
### Validating and Parsing an Email
```rust
use envelopwd::EmailAddress;
use std::str::FromStr;
fn main() -> Result<(), envelopwd::Error> {
// Parse an address
let addr = EmailAddress::from_str("alice@example.org")?;
println!("User: {}", addr.user()); // alice
println!("Domain: {}", addr.domain()); // example.org
// Convert to a mailto: URI
println!("URI: {}", addr.to_uri()); // mailto:alice@example.org
Ok(())
}
```
### Working with Mailboxes (Names + Emails)
```rust
use envelopwd::Mailbox;
use std::str::FromStr;
fn main() {
let input = "John Doe <john.doe@example.com>";
let mailbox = Mailbox::from_str(input).unwrap();
assert_eq!(mailbox.name(), Some("John Doe"));
assert_eq!(mailbox.email().user(), "john.doe");
// Display back to string
println!("{}", mailbox); // John Doe <john.doe@example.com>
}
```
### Optional Features
#### Serialization with Serde
When the `serde` feature is enabled, both `EmailAddress` and `Mailbox` implement `Serialize` and `Deserialize`. They are treated as transparent strings, ensuring they integrate seamlessly with web APIs and configuration files.
```rust
use envelopwd::EmailAddress;
use serde::{Serialize, Deserialize};
#[derive(Serialize, Deserialize)]
struct User {
name: String,
email: EmailAddress,
}
```
#### Database Integration with sqlx
Enable the `sqlx` feature to use `EmailAddress` and `Mailbox` directly in your database models.
#### Postgres arrays
Enable the `sqlx_postgres` feature to use `EmailAddress` and `Mailbox` in array queries.
#### Lettre Integration
Enable the `lettre` feature to allow converting types to their `lettre` counterparts:
```rust
let addr = EmailAddress::from_str("alice@example.org")?;
let lettre_addr: lettre::Address = addr.try_into()?;
let mb = Mailbox::from_str("Alice <alice@example.org>")?;
let lettre_mb: lettre::message::Mailbox = mb.try_into()?;
```
## Validation Logic
`envelopwd` ensures:
1. **Lengths**: Local part ≤ 64 octets, Domain ≤ 254 octets.
2. **Subdomains**: Each label is ≤ 63 characters and follows DNS-style alphanumeric rules.
3. **Quoted Parts**: Supports quoted local parts (e.g., `"john..doe"@example.org`).
4. **Literals**: Supports domain literals (e.g., `jsmith@[192.168.2.1]`).
## License
This project is licensed under Apache-2.0