Addresses, aliases and catch-all
Every message Stalwart accepts for local delivery is addressed to one of its domains. The server must then map the local part of the address, the part before the @, to the mailbox that receives it.
Several features shape this mapping, and they are configured in different places. Accounts, groups and mailing lists have addresses and aliases. Each domain has its sub-addressing rule and, optionally, a catch-all address. A domain can also have alias names of its own, and it can allow relaying. This page explains how these features combine.
Recipient resolution
Section titled “Recipient resolution”The server resolves each recipient of an incoming message during the SMTP RCPT TO command, so that it can reject an unknown recipient before the message is transferred. It goes through the following steps, and stops at the first that applies:
- Domain. The domain part must be the name or an alias of a Domain. Otherwise the recipient is not local. The message is then relayed only when the sender is allowed to relay, and refused otherwise.
- Sub-addressing. If the domain has sub-addressing enabled, the local part is reduced to its base form, for example
jane+newstojane, as described below. - Masked addresses. With the Enterprise edition, an address generated by masked email is delivered to the account that owns it.
- External directory. If the domain’s accounts come from an LDAP or SQL directory that can look up recipients, the directory is asked whether the address exists. An address it knows is accepted, and the account is created in Stalwart if it does not exist yet. With such a directory, the next step consults only mailing lists, because the directory is the authority for the addresses and aliases of accounts.
- Local addresses. The address may be that of an account, group or mailing list, or one of their aliases. Mail to a mailing list is expanded to the list’s recipients, including the members of nested lists.
- Catch-all. If the domain has a
catchAllAddress, the message is delivered to that address. - Relaying. If the domain has
allowRelayingset, the recipient is accepted. This serves split-delivery setups, in which some mailboxes of the domain are hosted on another server. The default routing still delivers such messages locally, however, so an outbound route must send these recipients to the other server, as described in RCPT stage. - Otherwise the recipient is rejected as unknown.
The order of the steps has consequences. Because the catch-all address is tried before relaying, a domain with a catch-all address never relays mail for unknown recipients. RCPT stage describes the SMTP responses for each outcome.
Aliases
Section titled “Aliases”An alias is a further address of an account, group or mailing list. Each of them has a primary address and any number of aliases, listed in its aliases field as EmailAlias entries. Each alias is a local part and a domain, and can be disabled without removing it. Aliases are exact addresses, not patterns.
Every address, primary or alias, belongs to exactly one account, group or mailing list, so two accounts cannot share an address. Mail for one address can still reach several people, in one of two ways. A group has a mailbox that its members share. A mailing list distributes copies to its recipients.
Aliases also determine the addresses an account can send from. With the default mustMatchSender setting, an authenticated user can use any address of the account as envelope sender, as described in SMTP authentication. JMAP clients offer these addresses through identities, which the client creates.
Sub-addressing
Section titled “Sub-addressing”Sub-addressing lets users hand out variants of their address, such as [email protected], that are delivered to [email protected]. A user can give each correspondent a different variant, and later filter mail by the variant it arrived at. Sub-addressing is configured per domain with subAddressing, which takes one of three values:
Enabled: everything from the first+is removed from the local part.Custom: the expression incustomRulecomputes the base local part. It receives the local part in thercptvariable, and its result replaces the local part, so the+rule does not apply in addition. When the expression returns no value, the local part is used unchanged. When the expression fails to compile, the error is logged, and the+rule is used instead.Disabled: the local part is used as it is.
The following rule treats both - and + as separators, so that [email protected] is delivered to jane. A rule like this changes the meaning of existing addresses that contain the separator: [email protected] would be delivered to mary. Choose a character that no address of the domain uses:
{ "subAddressing": { "@type": "Custom", "customRule": { "match": { "0": {"if": "contains(rcpt, '-')", "then": "split_once(rcpt, '-')[0]"}, "1": {"if": "contains(rcpt, '+')", "then": "split_once(rcpt, '+')[0]"} }, "else": "rcpt" } }}Sub-addressing is not limited to SMTP. The same resolution applies to JMAP and DAV lookups of an address by name. Expressions describes the expression syntax and functions.
Catch-all address
Section titled “Catch-all address”A domain can direct all mail for its unknown recipients to a single address, set in catchAllAddress. The address normally belongs to an account in the same domain.
The convenience has a cost. A catch-all address accepts every guessed or misspelled address, and with it every message that spammers send to random addresses. It therefore increases the volume of spam the domain receives. It also disables the rejection of unknown recipients, which senders rely on to detect typing errors.
Domain aliases
Section titled “Domain aliases”An organisation often owns several domain names for the same mailboxes, for example after a rebranding. A domain can list such alias names in aliases. Mail to an alias domain is resolved exactly as mail to the primary domain. [email protected] is delivered to [email protected] when example.net is an alias of example.com, without separate aliases on the account.
Alias domains share the primary domain’s settings. For receiving that is the point, but for sending it has consequences:
- Outgoing mail from an address in an alias domain is DKIM-signed with the primary domain’s keys, with
d=example.com. DMARC requires the signing domain to align with the domain in theFromheader, and this signature does not align with the alias domain. DMARC can therefore pass for that mail only through SPF. Publishing the primary domain’s key under the alias domain does not change that. - Automatic DNS management publishes records for the primary name only, so the alias domain’s MX, SPF and other records must be published by hand.
A domain whose users send mail under its own name needs DMARC-aligned DKIM signatures. It therefore needs its own Domain object, with its own keys and records, instead of being an alias.
Masked addresses
Section titled “Masked addresses”Masked addresses are generated addresses that forward to an account without revealing its real address. The user can disable each of them at any time, for example once it starts to receive spam. They are resolved before the external directory and the account addresses, as shown above. Masked email describes them in full.
Deleting a domain
Section titled “Deleting a domain”The DKIM keys of a domain must be deleted before the domain itself, and its DNS records stay at the provider afterwards. Deleting a domain lists everything that must be removed first.