Configuring the Edges

The next big section in slimta.conf is edge, which allows you to setup as many different inbound edge listeners as you need. In the edge section, each key provides an arbitrary, free-form name for the edge, and the value is a mapping with two required keys:

  • type: String

    Defines the type of edge. A known type must be given or an error will be thrown. The other keys in this mapping depend on the value of type.

  • queue: String

    When messages are received by this edge listener, they are passed to this queue. The value of this queue is a name, which must correspond to a key in the top-level queue section.

When available, edges may also include a listener sub-section that uses consistent options. This sub-section is defined as:

  • listener: Dictionary

    This mapping defines how to open the listening socket. Available keys are as follows:

    • type: String

      Defines the type of listening socket. Valid values are tcp , udp and unix. The default type is tcp.

    • interface: String

      For tcp and udp types, this setting defines the interface IP on which to bind. Examples are '127.0.0.1' to only listen locally, or '' to listen on all interfaces. The default is '127.0.0.1'.

    • port: Integer

      For tcp and udp types, this setting defines the port on which to bind. The default port number depends on the type of edge.

    • path: String

      For unix types, this setting defines the file path where the listening UNIX socket is created. There is no default value.

    • backlog: Integer

      For tcp and unix types, this setting defines the size of the backlog of unaccepted connections. See the listen() method for more information. The default is 256.

Some options can use python-slimta-lookup to query an external source for its data. These sections must have the following option:

  • type: String, required

    Defines the type of external data source. Valid values are redis, sqlite3, and config.

Additional optional and required options depend on type. See the class definitions in slimta.lookup.drivers for more information on these options.

smtp Edges

SMTP Edges produce an SmtpEdge object from the extra keys given in the edge sub-section. These keys are:

  • listener: Dictionary

    This mapping defines how to open the listening socket. See the listener sub-section for information on its available keys. The default value for port is 25.

  • hostname: String

    This is the string presented as the machine’s hostname in the SMTP banner message. By default, this will be the machine’s FQDN.

  • max_size: Integer

    This is the maximum allowed size, in bytes, of incoming messages on this SMTP edge. Larger messages are rejected. By default, there is no size limit.

  • tls: Dictionary

    This mapping, which takes the same keys as the keyword parameters to wrap_socket(), both enables and configures TLS encryption on this SMTP edge. By default, TLS is not enabled.

  • tls_immediately: Boolean

    Defines whether or not TLS should handshake immediately on connection, or if a socket is only encrypted if the user runs STARTTLS. By default, sessions are only encrypted on STARTTLS.

  • proxy_protocol: Boolean

    Defines whether or not connections to the edge will include a PROXY protocol header defining the original connection information. Only use this option when running behind a properly configured proxy.

  • rules: Dictionary

    This sub-section gives extra configurability in the internals of the SMTP edge. It has its own set of keys, all of which are optional:

    • banner: String

      This string is presented to connecting clients as the SMTP banner message. It can contain {fqdn} or {hostname} to substitute in the respective information about the local machine. By default, a generic banner message is used.

    • dnsbl: String

      Specifies a server that will be queried as a DNS blocklist. If a connecting client “hits” on the DNS blocklist, it is rejected outright. By default, no DNS blocklists are checked.

    • reject_spf: List

      Specifies a list of SPF result types that are rejected in an SMTP session. Valid strings in the list are: pass, permerror, fail, temperror, softfail, none, and neutral. By default, no SPF results are rejected.

    • reject_spam: Dictionary

      Specifies a spam engine that will be used to reject message data that is considered spam before it is accepted for delivery. At the moment, only spamassassin is available, which takes optional host and port keys.

    • only_senders: List

      Only the email addresses in this list will be accepted when given in the MAIL FROM:<> command from a client. By default, all senders are accepted.

    • only_recipients: List

      Only the email addresses in this list will be acceped when given in the RCPT TO:<> commands from the client. By default, all recipients are accepted.

    • regex_senders: List

      Like only_senders but compiles each value into a regular expression that each sender address is matched against.

    • regex_recipients: List

      Like only_recipients but compiles each value into a regular expression that each recipient address is matched against.

    • lookup_senders: Dictionary

      This section follows the lookup section requirements. It will limit the allowed addresses to the MAIL FROM:<> command to those with records in the external data source.

    • lookup_recipients: Dictionary

      This section follows the lookup section requirements. It will limit the allowed addresses to the RCPT TO:<> command to those with records in the external data source.

    • lookup_credentials: Dictionary

      This section follows the lookup section requirements. The SMTP AUTH extension will check the external data source for the authenticating username, and look for the password attribute. That password is verified against that field using passlib.apps.ldap_context, meaning it supports the {SCHEME}HASH format.

http Edges

HTTP Edges produce an WsgiEdge object that is then configured to receive mail. It supports the following options:

  • listener: Dictionary

    This mapping defines how to open the listening socket. See the listener sub-section for information on its available keys. The default value for port is 8025.

  • hostname: String

    This is the string presented as the machine’s hostname in the SMTP banner message. By default, this will be the machine’s FQDN.

  • uri: String

    This option defines a regular expression pattern that request paths must match, or a 404 Not Found will be returned. If it is not given, all paths are accepted.

  • tls: Dictionary

    This mapping, which takes the same keys as the keyword parameters to wrap_socket(), both enables and configures TLS encryption on this HTTP edge. All inbound requests must be HTTPS. By default, TLS is not enabled.

  • rules: Dictionary

    This sub-section gives extra configurability in the internals of the HTTP edge. It has its own set of keys, all of which are optional:

    • only_senders: List

      Only the email addresses in this list will be accepted when given in the X-Envelope-Sender header from a client. By default, all senders are accepted.

    • only_recipients: List

      Only the email addresses in this list will be acceped when given in the X-Envelope-Recipient headers from the client. By default, all recipients are accepted.

    • lookup_senders: Dictionary

      This section follows the lookup section requirements. It will limit the allowed addresses in the X-Envelope-Sender header to those with records in the external data source.

    • lookup_recipients: Dictionary

      This section follows the lookup section requirements. It will limit the allowed addresses in the X-Envelope-Recipient header to those with records in the external data source.

custom Edges

Only one additional key is required by the "custom" edge type:

  • factory: String, required

    This is a string of the form package.module:symbol. The package and module portion are imported with importlib.import_module(), and then the symbol is fetched from the loaded module with getattr().

    The result of loading the symbol must be a function that takes two arguments, the options object (that contains the type, queue, and factory keys as well as any others as necessary) and the Queue object that the edge should delivery received messages to:

    def edge_factory(options, queue):
        if 'foo' in options:
            return FooEdge(options.stuff, queue)
        else:
            return BarEdge(options.baz, queue)