RFC 9228

Delivered-To Email Header Field

πŸ“… published April 2022, from ietf

RFC 9228: Delivered-To Email Header Field πŸ’Œβœ¨

Okay bestie, here's the title block πŸŽ€ This is RFC 9228, titled "Delivered-To Email Header Field," written by D. Crocker, Ed. of Brandenburg InternetWorking. It's an Experimental RFC from the Independent Submission stream, dated April 2022, with ISSN 2070-1721. The header doesn't list any Obsoletes or Updates entries, so it doesn't replace or change any other RFC πŸ¦‹

Abstract 🌸

Okay so, the address an email actually gets delivered to can be totally different from every address in the content headers the sender wrote 😭 The transport address is handed over separately (think SMTP's "RCPT TO" command), and it might not match anything in the To: or cc: fields at all. Plus, before final delivery, a message can go through a whole sequence of submission/delivery events, using different destination addresses that (eventually) lead to the recipient. And a receiving system's delivery process can do its own local address transformations πŸ™ˆ

It's super helpful for a message to have one common way to record each delivery in that sequence, noting each address used for that recipient. That's useful for (1) analyzing the path a message took, (2) loop detection, or (3) working out the author's address in a reply message πŸ’… This document defines a header field for exactly that ✨

Email handling info reveals details about the email infrastructure AND about a specific recipient, so privacy concerns can totally come up πŸ‘€

Ngl, a header field like this isn't automatically guaranteed to get widespread use. So this doc is being published as an Experimental RFC, looking for constituency and operational utility 🧚 It came through the Independent Submission Stream and wasn't subject to the IETF's approval process.

Status of This Memo πŸ“œ

This document isn't an Internet Standards Track specification. It's published for examination, experimental implementation, and evaluation πŸ’œ

It defines an Experimental Protocol for the Internet community. It's a contribution to the RFC Series, independent of any other RFC stream. The RFC Editor chose to publish it at their discretion and makes no statement about its value for implementation or deployment. Documents approved for publication by the RFC Editor aren't candidates for any level of Internet Standard, see Section 2 of RFC 7841 🌈

Info about the current status of this document, any errata, and how to give feedback on it lives at https://www.rfc-editor.org/info/rfc9228 πŸ”₯

Copyright (c) 2022 IETF Trust and the persons identified as the document authors. All rights reserved.

This document is subject to BCP 78 and the IETF Trust's Legal Provisions Relating to IETF Documents (https://trustee.ietf.org/license-info) in effect on the date of publication. Please review these documents carefully, since they describe your rights and restrictions with respect to this document 🫢

Table of Contents πŸ—‚οΈ

1.  Introduction
2.  Background
3.  Framework & Terminology
4.  Delivered-To
5.  Multi-Delivery Example
6.  Security Considerations
7.  IANA Considerations
8.  Experimental Goals
9.  References
  9.1.  Normative References
  9.2.  Informative References
Acknowledgements
Author's Address

1. Introduction 🌷

Okay, so the address an email is delivered to might be different from every address shown in the content header fields [Mail-Fmt], like the To: and cc: fields the author's Message User Agent (MUA) created [Mail-Arch]. The address used by the Message Handling Service (MHS) is given separately, in envelope information, like a "RCPT TO" command in [SMTP] πŸ’Œ

As noted in Section 4.3.3 of [Mail-Arch], 'A transfer of responsibility from the MHS to a Recipient's environment (mailbox) is called "delivery".' So when the destination address is fully and successfully processed, and any extra processing is done by an agent working on that address's behalf, the message has been delivered. But instead of dropping the message into a recipient inbox or otherwise finishing the handling, that agent might create additional processing, including sending to one or more different addresses. Each handoff of responsibility from the MHS to an agent of a current addressee counts as a distinct delivery πŸ¦‹ With handling sequences that can include aliasing, mailing lists, and the like, a message going from its author to a final recipient might involve a whole series of submission/delivery events. The delivery process at a receiving system can also produce local (internal) address transformations 🧚

Header fields that carry handling info are super useful when assessing email traffic issues and diagnosing specific handling problems πŸ” So it's helpful for a message to have a common way to indicate each delivery in the handling sequence, and to include each address that led to the final delivery. That can really help with analyzing a message's transit handling πŸ’…

Another use is detecting a delivery sequence loop based on a specific address. In a problematic loop, the same copy of a message is delivered to the same email address more than once πŸŒ€ That's different from different copies being delivered to the same address, which happens when a message is sent directly to an address and also through a mailing list. It's also different from two copies of the same message arriving at the same ultimate destination address after being posted to two different addresses. And it's different from noticing when a message simply passes through the same Message Transfer Agent (MTA) more than once, which might be necessary, like when it's processed through a mailing list, since an MTA serves many addresses πŸ“

Delivering the same copy of a message more than once, to the same address, is almost certainly not an intended activity πŸ™ˆ An example of a problematic setup: send a message to mailing list List-A, where List-A contains an entry for List-B, and List-B contains an entry for List-A. The message will enter an infinite loop πŸ’€ Loop detection for email can get complicated, fr. The Delivered-To: header field gives helpful info, with a definitive indication that this copy of a message has (already) been delivered to a specific address ✨

When you're specifying new activity related to existing activity, there's a choice of design approach:

  • Seeking to change (some of) the existing behavior
  • Adding to the activity without changing what's already being done
  • Calling for separate, new activity

On average, trying to change existing activities is the least likely to get adopted. It can create operational confusion between old and new activities, which in turn creates resistance to adoption 😭 Seeking new activity can make sense when that activity is sufficiently different and deemed sufficiently beneficial. Adding to existing activity has the selling point of building on an installed base πŸ‘‘ This specification builds on an existing installed base of Delivered-To: activity. It calls for little technical enhancement. Instead, it simply provides for a wider range of application πŸŽ€

Considerations:

  • Email handling info like this provides info about the email infrastructure, as well as about the recipient. Disclosing it might bring privacy concerns πŸ™ˆ
  • A specification isn't automatically guaranteed adoption or use. So this document is being published as an Experimental RFC, looking for extended constituency and general operational utility 🌸
  • This document was produced through the Independent RFC Stream and wasn't subject to the IETF's approval process πŸ’…

2. Background πŸ•°οΈ

Ad hoc use of a Delivered-To: email header field appears to go back to the 1990s, mainly for loop detection. Documentation is spotty and system specific, though πŸ™ƒ A listing of some implementations is offered in [Prior] πŸ“š

It looks like all uses include a string in the form of an email address, although at least one example has leading text that's a comment about the address. In some cases, the string seems to be the email transport destination address, like the address used in SMTP's "RCPT TO" command. In other cases, it seems to be the result of some internal mapping at the receiving system, though it tends to be a variant of the transport address πŸ¦‹

Email loop detection tends to happen through a bunch of different methods, like counting Received: header fields. These methods are often combined for even better results 🧚

The Received: header field's 'for' clause is sometimes useful for disclosing the recipient's address. However, the clause isn't used reliably, and its semantics aren't thoroughly defined 😬 Also, it references an addressing value that was received but might be different from the value that's ultimately used (after a transformation). So the value in a 'for' clause might be a good indicator of delivery addressing, but it might not be πŸ€·β€β™€οΈ

3. Framework & Terminology πŸŽ€

Unless otherwise indicated, the basic architecture and terminology used in this document are taken from:

  • [Mail-Arch]
  • [SMTP]
  • [Mail-Fmt]

and syntax is specified with:

  • [ABNF]

Normative language is per [RFC8174]:

The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "NOT RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in BCP 14 [RFC2119] [RFC8174] when, and only when, they appear in all capitals, as shown here.

4. Delivered-To ✨

okay so this section is the heart of the whole thing πŸ’– the Delivered-To: header field is basically a little receipt that gets stamped on an email every time it gets handed off to a recipient's mailbox or agent. it says which individual address was actually used to make that handoff happen πŸ¦‹

  • when a message gets delivered (the moment responsibility moves from the MHS over to the recipient's store or agent), a Delivered-To: header field SHOULD be added, with the addr-spec value holding the address the service used to reach the recipient πŸŽ€
  • if a receiving system's delivery process maps or transforms the address used by the MHS into some local value, that new value SHOULD ALSO be recorded in a separate Delivered-To: field once transit and processing with that address successfully finish 🌸 this keeps a detailed record of the whole chain of addresses the message went through πŸ“œ
  • just like the trace fields in [SMTP] (see Section 4.1.1.4 of [SMTP]), each new Delivered-To: field MUST be placed at the current top of the message's header fields, so it becomes the first header field 🧚 the result is a sequence where the first delivery sits at the bottom and the latest one sits at the top πŸ‘‘
  • because each one gets added at the current top, a Delivered-To: field MUST NOT be reordered with respect to other Delivered-To: fields or those other fields πŸ’… the whole point is that the order keeps showing the message handling sequence πŸ”₯

the field gets added at delivery time, when responsibility moves from the Message Handling Service (MHS) to an agent of the specific recipient address. it can also be added when internal system processing does address transformations 🌈

✨ Note: seeing an existing Delivered-To: header field for the same address usually means the message is stuck in a handling loop πŸ’€

the syntax is:

"Delivered-To:" FWS addr-spec FWS CRLF ; addr-spec is from [Mail-Fmt]

the field records info about one address, for one recipient. see Section 6 for the privacy stuff about spilling addresses πŸ™ˆ

5. Multi-Delivery Example πŸ“

the Delivered-To: header field can document a whole sequence of deliveries 🧚 every time an address is fully processed, a new Delivered-To: field gets added, so the most recent one ends up near the top of the stack πŸ¦‹

this example follows a message from its original posting, through a remote group mailing list, then through an independent personal aliasing mechanism, and finally to delivery at yet another independent email provider 🌈

5.1. Origination at com.example πŸ’Œ

the message as submitted. the destination address matches the To: header field.

From: Ann Author <aauthor@com.example>
Date: Mon, 25 Jan 2021 18:29:06 -0500
To: list@org.example
Subject: [list] Sending through a list and alias
Sender: Ann Author <aauthor@com.example>

5.2. List processing at org.example πŸ“¬

delivered with one Delivered-To: header field, going to the list processing module, which then resubmits the message for transport to the list member "Recipient-alumn@edu.example" πŸ’œ

Delivered-To: list@org.example
Received: by submit.org.example with SMTP id i17so17480689ljn.1
    for <list@org.example> from mail.com.example;
    Mon, 25 Jan 2021 15:29:19 -0800 (PST)
Received: by mail.com.example; Mon, 25 Jan 2021 15:29:00 -0800 (PST)
From: Ann Author <aauthor@com.example>
Date: Mon, 25 Jan 2021 18:29:06 -0500
To: list@org.example
Subject: [list] Sending through a list and alias
Sender: Ann Author <aauthor@com.example>

5.3. Alias processing at edu.example πŸŽ€

delivered with two Delivered-To: header fields, going to the alias processing module, which sends it on to "theRecipient@example.net" 🌸

Delivered-To: Recipient-alumn@edu.example
Received: from mail.org.example
    by relay.edu.example; Mon, 25 Jan 2021 23:29:24 +0000 (UTC)
Received: by submit.org.example;
    Mon, 25 Jan 2021 23:29:21 +0000 (UTC)
Delivered-To: list@org.example
Received: by submit.org.example with SMTP id i17so17480689ljn.1
    for <list@org.example> from mail.com.example;
    Mon, 25 Jan 2021 15:29:19 -0800 (PST)
Received: by mail.com.example; Mon, 25 Jan 2021 15:29:00 -0800 (PST)
From: Ann Author <aauthor@com.example>
Date: Mon, 25 Jan 2021 18:29:06 -0500
To: list@org.example
Subject: [list] Sending through a list and alias
Sender: list-bounces@org.example

5.4. Final delivery to the recipient at example.net 🏁

finally delivered with three Delivered-To: header fields, to the recipient at "theRecipient@example.net" πŸ‘‘

Delivered-To: theRecipient@example.net
Received: from mail.edu.example (mail.edu.example [4.31.198.45])
    by relay.example.net; Mon, 25 Jan 2021 23:29:24 +0000 (UTC)
Delivered-To: Recipient-alumn@edu.example
Received: from mail.org.example
    by relay.edu.example; Mon, 25 Jan 2021 23:29:24 +0000 (UTC)
Received: by submit.org.example;
    Mon, 25 Jan 2021 23:29:21 +0000 (UTC)
Delivered-To: list@org.example
Received: by submit.org.example with SMTP id i17so17480689ljn.1
    for <list@org.example> from mail.com.example;
    Mon, 25 Jan 2021 15:29:19 -0800 (PST)
Received: by mail.com.example; Mon, 25 Jan 2021 15:29:00 -0800 (PST)
From: Ann Author <aauthor@com.example>
Date: Mon, 25 Jan 2021 18:29:06 -0500
To: list@org.example
Subject: [list] Sending through a list and alias
Sender: list-bounces@org.example

6. Security Considerations πŸ”

okay this one is serious bestie, so read it slowly 🫢

as with Received: header fields, the presence of a Delivered-To: header field discloses handling information and, possibly, personal information 😭

security and privacy are essential, if challenging, topics for email in general and for handling metadata in particular πŸ’œ the purpose of this section is to point out areas of potential concern, not to give details on mitigation πŸ™ˆ the basic mechanism described here has a long history of use with no history of being problematic 🌈 however, the expanded use described here might create new scenarios that are problematic πŸ’€

an issue specific to this mechanism is disclosure of a sequence of addresses applied to the same recipient, if a message goes through a series of recipient address replacements πŸ¦‹ this document calls for each of these addresses to be recorded in a separate Delivered-To: field πŸ“œ this does not disclose addresses of other recipients, but it does disclose an address-transformation handling path for the recipient πŸŽ€

this disclosure is most likely to be a concern when a recipient manually forwards a message and includes all of the original header fields 😬 that exposes to a later recipient any intermediate addresses used to get the original message to the original recipient πŸ’… such a disclosure is likely unintended and might be (highly) problematic 🚨 a basic version of this unintended disclosure has existed for a long time, because a later recipient can see Received: header fields, especially any with a 'for' clause 🌸 but a Delivered-To: header field sequence can disclose significantly more recipient-specific handling detail πŸ‘€

an issue that is entirely implementation specific (and therefore out of scope for this document) is that in some systems, a message meant for multiple local recipients is stored as a single, shared version 🧚 supporting Delivered-To:, while keeping recipient privacy, creates a challenge in this case, since exposing different recipient addresses to other recipients can be problematic 🫣

7. IANA Considerations πŸ“‹

IANA has registered the Delivered-To: header field as below, per [RFC3864] in the "Provisional Message Header Field Names" registry πŸ’–

Header Field Name:  Delivered-To

Protocol:  mail

Status:  Provisional

Author/Change controller:  Dave Crocker

Specification document(s):  *** This document ***

Related information:  None.

8. Experimental Goals πŸ§ͺ

specific feedback is sought concerning:

  • technical issues in recording the Delivered-To: field into a message, through its entire submission/delivery sequence ✨
  • market interest in the uses described here πŸ›οΈ
  • utility for the purposes described here, or for other uses 🌈

so the questions to answer for this Experimental RFC are:

  • is there demonstrated interest by MSA/MTA/MDA (Message Submission Agent / Message Transfer Agent / Message Delivery Agent) developers? πŸ§‘β€πŸ’»
  • if the capability is implemented and the header field generated, is it used by operators or MUAs? πŸ“¬
  • does the presence of the header field create any operational problems? πŸ€”
  • does the presence of the header field demonstrate additional security issues? πŸ”’
  • what specific changes to the document are needed? ✏️
  • what other comments will aid in use of this mechanism? πŸ’¬

please send comments to ietf-smtp@ietf.org πŸ’Œ

9. References πŸ“š

9.1. Normative References πŸŽ€

9.2. Informative References 🌷

Acknowledgements ✨

okay so even a tiny, narrow spec can start the most intense debates, and this one is a whole example of that πŸ’€ but honestly? the discussion was super useful 🫢 It happened first on the IETF's emailcore working group mailing list, and then moved over to the long-standing ietf-smtp mailing list πŸ“¬

huge thank-you to everyone who helped out, bestie πŸ’œ The helpful info and suggestions came from Anonymous, StΓ©phane Bortzmeyer, Richard Clayton, Viktor Dukhovni, Adrian Farrel, Ned Freed, John Klensin, Barry Leiba, Brandon Long, George Michaelson, Michael Peddemors, Phil Pennock, Pete Resnick, Sam Varshavchik, Alessandro Vesely, and Tim Wicinski πŸŒΈπŸ™Œ

Author's Address πŸŽ€

The editor is Dave Crocker, at Brandenburg InternetWorking.

Dave Crocker (editor)
Brandenburg InternetWorking
Email: dcrocker@bbiw.net
πŸ“¦ where this page comes from