Server Fault is a question and answer site for system and network administrators. Join them; it only takes a minute:

Sign up
Here's how it works:
  1. Anybody can ask a question
  2. Anybody can answer
  3. The best answers are voted up and rise to the top

I'm a developer and I'm currently building a hosted ecommerce solution. One thing the software must do is email customers on behalf of the vendor. However, one of the business requirements is that we use the vendor's email server for all email communication. But since we can't have the web application waiting for response from a remote mail server, we need a local server that resends or routes that email through the vendor's mail server.

Ideally I'd like to set up a local mail server (by local I mean in the farm that hosts my web app, and by mail server I'm open to anything but this is a Windows shop so first thing to my mind is Exchange) that will do the relaying for us.

Is this possible? Ie, that the same mail server will resend mail through client's server depending on the from address -- all mail from should be resent through and all mail from should be resent through

What's the best way to accomplish this?
What about credentials on each remote mail server?

share|improve this question
up vote 1 down vote accepted

Any decent MTA (mail server) should be able to route mail according to rules, instead of simply based on DNS. My experience is mostly with Exim, but Exim is not unique here.

Certainly with Exim it's almost trivial to write a Router which looks at the sender address to determine which host to send out by and put that before the normal dnslookup or smarthost Router. Add credentials adds a little complexity, but not much. The biggest question is really how do you want to store the data? LDAP? MySQL? CDB? Flat files? It all works. I don't use Exchange myself, but there are plenty of people using Exim in front of Exchange and relying on Exim's LDAP support to query AD for the data needed to not have to duplicate information.

For instance, as a non-trivial example implementing all your wishes, with some security on top, with a CDB file mapping customer domains to key="value" data for the domain, you might have:

value: server="" user="fred" pass="s3kr3t" submission=t

and then:

# after "begin routers" and before the normal remote mail sending Router:
  driver = manualroute
  senders = *@cdb;/etc/mail/customers.cdb
  transport = customer_server_t
  address_data = ${lookup{$sender_address_domain}cdb{/etc/mail/customers.cdb}}
  route_data = ${extract{server}{${lookup{$sender_address_domain}cdb{/etc/mail/customers.cdb}}}

# after "begin transports"
  driver = smtp
  hosts_require_auth = ${extract{user}{$address_data}{*}{}}
  port = ${extract{submission}{$address_data}{587}{25}}
  # these next two will mandate TLS if tls is present, and turn on cert verification
  hosts_require_tls = ${extract{tls}{$address_data}{*}{}}
  tls_verify_certificates = ${extract{tls}{$address_data}{/etc/ssl/certs}{}}

# after "begin authenticators"
  driver = plaintext
  public_name = PLAIN
  client_condition = ${if def:tls_cipher}
  client_send = ^${extract{user}{$address_data}}^${extract{pass}{$address_data}}

As a couple of notes: address_data on the Router preserved the lookup results for easy access later, route_data did the same lookup, but in practice that will be use the cached results of the address_data, and this is a rather complete, albeit untested, example.

You can do other stuff instead of cdb, I just chose that at random. In particular, LDAP searches for multiple attributes will return data in the right format for the ${extract...} expansion operator to work with, so this should be good if you want to put the data into AD.

share|improve this answer
ended up using hMailServer, but your thorough run through helped me greatly! – hackerhasid Aug 10 '10 at 0:44

Your Answer


By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.