RFC-5321 Email Address Parser
raw JSON →address-rfc2821 is a JavaScript/TypeScript library designed for parsing email addresses conforming to RFC-5321 (formerly RFC-821/2821) specifically for the SMTP envelope, found in `MAIL FROM:` and `RCPT TO:` commands. This module focuses on the nuances of envelope addressing, including handling null senders (`<>`) and correctly managing quoted local-parts. Since version 2.0.0, it transitioned from a regex-based parser to one built with Nearley, providing more robust and accurate parsing. It also supports UTF-8 email addresses according to RFCs 5890-5892, providing the domain in punycode when necessary. The current stable version is 2.1.5, with recent updates including the addition of TypeScript type definitions in v2.1.4 and a fix to `isNull()`'s return type in v2.1.5. The library maintains an active release cadence, reflecting ongoing development and maintenance for Haraka mail server components.
Common errors
error Error: Address cannot be parsed ↓
address-rfc2822 or email-addresses instead. error TypeError: Address is not a constructor ↓
Address class correctly: const { Address } = require('address-rfc2821'); or const Address = require('address-rfc2821').Address;. If using ESM, make sure to use named import: import { Address } from 'address-rfc2821';. Warnings
breaking Version 2.0.0 completely replaced the regular expression parser with a Nearley-based grammar. This resulted in more accurate parsing but could introduce subtle behavioral changes for edge cases. Double quote characters in the local-part are no longer stripped. ↓
breaking Version 2.0.0 increased the minimum required Node.js version to 11+. ↓
gotcha TypeScript type definitions were officially added in version 2.1.4. Prior to this, users either had to use `any` or provide custom type declarations. If upgrading from pre-2.1.4, remove any custom types. ↓
breaking In version 2.1.5, the `isNull()` method was updated to return a strict boolean (`true`/`false`) instead of a 'perlism' truthy/falsy value (e.g., `1`/`0`). ↓
Install
npm install address-rfc2821 yarn add address-rfc2821 pnpm add address-rfc2821 Imports
- Address wrong
const Address = require('address-rfc2821').Address;correctimport { Address } from 'address-rfc2821'; - Address (CommonJS)
const { Address } = require('address-rfc2821'); - Address (Type)
import type { Address } from 'address-rfc2821';
Quickstart
import { Address } from 'address-rfc2821';
try {
// Parse a standard email address
const addr1 = new Address('<user@example.com>');
console.log(`Parsed: ${addr1.format()} | User: ${addr1.user}, Host: ${addr1.host}`);
// Parse an address with a quoted local-part (handled correctly since v2.0.0)
const addr2 = new Address('<"first.last+tag"@sub.domain.com>');
console.log(`Parsed: ${addr2.format()} | User: ${addr2.user}, Host: ${addr2.host}`);
// Handle the null sender ('<>')
const nullSender = new Address('<>');
console.log(`Null Sender: ${nullSender.format()} | Is Null: ${nullSender.isNull()}`);
// Example with an internationalized domain name (IDN)
const internationalEmail = new Address('test@bücher.example');
console.log(`IDN Email (original host): ${internationalEmail.format()} (Host: ${internationalEmail.original_host})`);
console.log(`IDN Email (punycode host): ${internationalEmail.format(true)} (Host: ${internationalEmail.host})`);
// Create a new Address object from user and host parts
const newAddr = new Address('info', 'my-service.dev');
console.log(`Created: ${newAddr.toString()}`);
// This would throw an exception for unparseable addresses
// new Address('not-a-valid-email-address');
} catch (error) {
console.error('An error occurred during parsing:', error instanceof Error ? error.message : String(error));
}