> This has been discussed many times, and I know patches have been
> published.  I think the general feeling has been that for the general
> population of users making things more complicated pushes many users
> over the edge.

+1 to the original report.  We run a Mailman 3 deployment (Postorius
1.3.13, django-allauth 65.4.1) and see roughly 200 registration attempts
per day against addresses we have no relationship with, essentially
every day -- on the order of 6,000 confirmation messages a month sent to
people who never asked for them.

Two framing points, then something more concrete.

First, the cost is not only ours.  With ACCOUNT_EMAIL_VERIFICATION =
"mandatory", which is what the recommended configuration gives you, every
one of those POSTs makes our server originate mail to an innocent third
party before anything has been verified.  From the recipient's point of
view, and from their provider's, we are the spammer.  That is a
delivery-reputation problem for the same host that carries real list
traffic, and it worries me considerably more than the junk rows.

Second, the usability objection is real but narrow: it applies to account
creation, which a given user does once.  It does not touch subscribing by
mail, posting, or reading archives.

Now the concrete part.  I want to push back on the reflex -- which was my
own first reflex -- that this is a rate-limiting problem.  It is not, and
the reason is structural rather than a matter of tuning.

django-allauth's default is:

    "signup": "20/m/ip"

Three separate problems with that as a defence here:

1. Twenty per minute is 28,800 per day from a single address.  Our
   observed abuse volume is 1/144th of that.  The limit cannot fire.

2. The key is the client IP, and the abuse is not concentrated in one.



The one limit allauth keys on an email address rather than an IP is
confirm_email (1/180s/key by default), but its key is the target address,
which in this attack is different every time.  So that does not fire
either.

The pattern is general: every key allauth offers is derived from
something the attacker varies for free -- source IP, target address.
None is derived from the resource that is actually scarce, which is this
installation's standing to originate mail to strangers.  There is no
knob to turn, because there is no usable key to turn it on.

We hit exactly this shape once before, in the anonymous unsubscribe
flow, and ended up carrying a local patch: before sending an unsubscribe
confirmation we take a cache key derived from (list_id, target address)
and refuse to originate a second message while one is pending, with a
short TTL.  It is perhaps fifteen lines.  It is keyed on the thing we
control rather than the thing the attacker controls, it is invisible to
legitimate users, and it works.

That same shape is missing from registration, and I think it is half the
answer for everyone:

 - refuse to originate a confirmation to an address that already has an
   unconfirmed registration pending;
 - a per-installation ceiling on confirmation mails per hour, so the
   blast radius is bounded even when the front door is defeated.

Neither costs an honest user anything, neither changes the UI, and
neither depends on identifying the requester.

The other half is a per-request cost, and that is where I would support a
captcha -- not because it is unbeatable, but because it is the one lever
that works without needing a key at all.  Two caveats that I think answer
the concern about the general population of users:

 - off by default and switchable by the site admin, so installations
   without this problem pay nothing;
 - pluggable rather than wired to one vendor, so a site can pick
   reCAPTCHA / hCaptcha / Altcha / a proof-of-work challenge according to
   its own constraints.  Handing every visitor's IP to Google is not
   something every installation is able to do; a proof-of-work challenge
   costs the honest user an invisible second and costs a bulk attacker
   linearly.

> It's also known that while not all spammers use ML techniques, so
> captcha can be effective, ML defeats most captchas more easily than
> humans do.

Agreed, and I would not argue for it if the goal were to stop a
determined attacker.  What we see is an unauthenticated loop over one
endpoint, run because it is free.  It does not need to become impossible,
only more expensive than it is worth.

> Another possibility would be to push the responsibility on to the big
> providers by requiring a social auth login.

I would like that available, but not required.  Worth noting that
django-mailman3 already ships DisableSignupAdapter and
EnableSocialSignupAdapter for precisely this -- closing web signup while
leaving social signup open is two settings, not a patch.  So the
machinery exists; what is missing is that it is an all-or-nothing switch.

But making social login the only door would exclude precisely the users
who are on mailing lists in order not to depend on those providers.  Long
term I would like all three available and independently switchable:
pending-address suppression and an outbound ceiling on by default,
captcha optional, social login optional.


Happy to run patches against an installation that is receiving this
traffic daily.

Stephen J. Turnbull <[email protected]> 于2026年8月1日周六 17:22写道:

> Дилян Палаузов writes:
>
>  > The problem is that this simplicity allows misuse: somebody can
>  > trigger via HTTP requests many account registrations for random
>  > email addresses.
>
> This is a known problem.
>
>  > To mitigate this misuse pattern, the procedure to create new
>  > accounts over web interface should be made more complex, e.g. by
>  > utilizing captcha.
>
> This has been discussed many times, and I know patches have been
> published.  I think the general feeling has been that for the general
> population of users making things more complicated pushes many users
> over the edge.  It's also known that while not all spammers use ML
> techniques, so captcha can be effective, ML defeats most captchas more
> easily than humans do.  So that has not been a high priority for the
> core team.
>
>  > Does somebody already have some patches, doing such things, which
>  > patches can be shared?
>
> You should be able to find both captcha and recaptcha patches in the
> GitLab tracker (check for "closed" issues as well!), and more
> references in both the Mailman 2 and Mailman 3 Users archives as well
> as in the archives of this list.
>
> Another possibility would be to push the responsibility on to the big
> providers by requiring a social auth login.
>
> --
> GNU Mailman consultant (installation, migration, customization)
> Sirius Open Source    https://www.siriusopensource.com/
> Software systems consulting in Europe, North America, and Japan
> _______________________________________________
> Mailman-Developers mailing list -- [email protected]
> To unsubscribe send an email to [email protected]
> https://mail.python.org/mailman3/lists/mailman-developers.python.org/
> Mailman FAQ: https://wiki.list.org/x/AgA3
>
> Security Policy: https://wiki.list.org/x/QIA9
>
_______________________________________________
Mailman-Developers mailing list -- [email protected]
To unsubscribe send an email to [email protected]
https://mail.python.org/mailman3/lists/mailman-developers.python.org/
Mailman FAQ: https://wiki.list.org/x/AgA3

Security Policy: https://wiki.list.org/x/QIA9

Reply via email to