Repository: Mailu/Mailu

Issue:
Allow specific users to send email from any address
Before switching to Mailu I had postfix set up so that my admin user `admin@mydomain.dev` could impersonate / send email as any other user.

This was extremely useful for sending email programmatically from multiple sources, e.g. from a web app that needs to send email from `*@mydomain.dev` and several other domains like `*@admin.mydomain.dev`/`*@someotherdomain.dev`.

I suspect I can add something into `overrides/postfix.conf` to get this behavior back, but I'm not sure how to do it since I only want a specific user to be able to impersonate others, not all users.  Ideally there would be a UI page to configure the permitted sender addresses for each user, with sqlite-style wildcard support.

```ini
smtpd_client_restrictions =
  permit_mynetworks,
  check_sender_access ${podop}senderaccess,
  reject_non_fqdn_sender,
  reject_unknown_sender_domain,
  reject_unknown_recipient_domain,
  reject_unverified_recipient,
  permit

smtpd_relay_restrictions =
  permit_mynetworks,
  permit_sasl_authenticated,
  reject_unauth_destination
```

For now, given I'm the only one using the server and I need this behavior back ASAP, can I just remove the `check_sender_access ${podop}senderaccess,` line? Or is there a better long-term fix?

I also cant just use `RELAYNETS` with some whitelisted IPs becuase the servers doing the sending have dynamic IP addresses that often change, I need it to be whitelisted on a per-user basis not a per-sender-ip basis.

**Useful links:**
- https://github.com/Mailu/Mailu/blob/master/core/postfix/conf/main.cf
- http://www.postfix.org/ADDRESS_VERIFICATION_README.html
- http://www.postfix.org/postconf.5.html#check_sender_access


Discussion:
Using relaynets is probably better advised, since removing sender access will also allow illegitimate impersonation from anywhere, even external scammers.

Then, depending on your setup you could use aliases: a user can impersonate any alias that points to its address. Otherwise we will need to implement this while it is not entirely trivial: sender access verifications do not pass the authenticated user to the background.
Wait but isn't it all authenticated with the SMTP credentials?  How would a spammer be able to send from anywhere if they don't have SMTP credentials for the server?

All registered user accounts on this server are trusted, it's just me and a couple other people, so there's no chance of users that have SMTP credentials / registered accounts being spammers.  I just want to authorize a single SMTP user/pass to be able to send from `%@mydomain.com` (or even better, `%@%` without domain validation).

I tried the alias setup you suggested, the problem is that the alias for `%@mydomain.com` that allows it to send from any address conflicts with other accounts and becomes a catch-all for received mail, I just want to allow arbitrary sending without changing the received mail routing.

> I also cant just use RELAYNETS with some whitelisted IPs becuase the servers doing the sending have dynamic IP addresses that often change.
Incoming mail using is not authenticated: SMTP only supports authenticating local users, remote users aren't. And sender access is the set of rules that makes sure that remote servers cannot impersonate your local users, among other things.

Also, the catch all alias is probably the simplest way to go. It should not conflict with any other alias or local user since it should have the lowest priority. It will just act as a default catch all.
Right, I know incoming mail isn't authenticated, I meant for outgoing mail.

> makes sure that remote servers cannot impersonate your local users, among other things.

This is exactly what I'm trying to accomplish, I need my servers to be able to send from `*@allmydomains.com` using one set of SMTP credentials.  

I already tried the catchall, it didn't work, all relayed emails got rejected due to sender addresses not being owned by the SMTP user.

Resolving patch:
diff --git a/core/admin/mailu/configuration.py b/core/admin/mailu/configuration.py
--- a/core/admin/mailu/configuration.py
+++ b/core/admin/mailu/configuration.py
@@ -32,6 +32,7 @@
     'DOMAIN': 'mailu.io',
     'HOSTNAMES': 'mail.mailu.io,alternative.mailu.io,yetanother.mailu.io',
     'POSTMASTER': 'postmaster',
+    'WILDCARD_SENDERS': '',
     'TLS_FLAVOR': 'cert',
     'INBOUND_TLS_ENFORCE': False,
     'AUTH_RATELIMIT': '1000/minute;10000/hour',
diff --git a/core/admin/mailu/internal/views/postfix.py b/core/admin/mailu/internal/views/postfix.py
--- a/core/admin/mailu/internal/views/postfix.py
+++ b/core/admin/mailu/internal/views/postfix.py
@@ -133,10 +133,12 @@ def postfix_sender_map(sender):
 
 @internal.route("/postfix/sender/login/<path:sender>")
 def postfix_sender_login(sender):
+    wildcard_senders = [s for s in flask.current_app.config.get('WILDCARD_SENDERS', '').lower().replace(' ', '').split(',') if s]
     localpart, domain_name = models.Email.resolve_domain(sender)
     if localpart is None:
-        return flask.abort(404)
+        return flask.jsonify(",".join(wildcard_senders)) if wildcard_senders else flask.abort(404)
     destination = models.Email.resolve_destination(localpart, domain_name, True)
+    destination = [*destination, *wildcard_senders] if destination else [*wildcard_senders]
     return flask.jsonify(",".join(destination)) if destination else flask.abort(404)
 
 @internal.route("/postfix/sender/rate/<path:sender>")


Test patch: