Custom Objects
This document describes the objects available to Starlark policy scripts in postern. These objects are passed into the policy hooks.
conn
A conn represents the incoming network connection that delivered the message.
Attributes
| Attribute | Type | Description |
|---|---|---|
remote_addr |
string |
The full remote address of the connection (e.g. 1.2.3.4:54321). |
client_ip |
string |
The remote IP address. For TCP connections this is the bare IP without port. Falls back to remote_addr for non-TCP connections. |
Example
def on_message_deliver(conn, user, msg):
if conn.client_ip.startswith("10."):
return "INBOX"
return "INBOX"
user
A user represents a Postern user account.
Attributes
| Attribute | Type | Description |
|---|---|---|
name |
string |
The username (login) of the user. |
addresses |
tuple[str] |
The list of email addresses belonging to the user, as a tuple of strings. |
gatekeeper |
UserGatekeeper or None |
The per-user gatekeeper sub-object, or None if no gatekeeper is configured. |
Example
def on_message_deliver(conn, user, msg):
if "vip@example.com" in user.addresses:
return "VIP"
return "INBOX"
msg
A msg represents the email message being processed.
Attributes
| Attribute | Type | Description |
|---|---|---|
header_from |
Address |
Parsed From header. Errors (e.g. missing From) propagate as Starlark errors. |
header_to |
Address |
Parsed To header. Returns an error if the To header is missing or invalid. |
subject |
string |
The Subject header value, or an empty string if absent. |
size |
int |
Size of the raw message in bytes. |
body |
bytes |
The full raw message body (headers + content) as bytes. |
text_body |
string |
The concatenated plain-text body parts of the message. |
html_body |
string |
The concatenated HTML body parts of the message. |
attachments |
list[Attachment] |
List of extracted attachments (see Attachment). |
Example
def on_message_deliver(conn, user, msg):
for att in msg.attachments:
if att.filename.endswith(".pdf"):
print("found PDF:", att.filename)
return "INBOX"
Address
A parsed email address, returned by msg.header_from and msg.header_to.
Attributes
| Attribute | Type | Description |
|---|---|---|
address |
string |
The bare email address (e.g. alice@example.com). |
name |
string |
The display name portion of the address, if any (e.g. Alice). Empty if not present. |
raw |
string |
The original, unparsed header value as it appeared in the message. |
Example
addr = msg.header_from
print(addr.raw) # "Alice <alice@example.com>"
print(addr.name) # "Alice"
print(addr.address) # "alice@example.com"
Attachment
Represents a single attachment (or inline binary part) extracted from the
message. Returned as elements of msg.attachments.
Attributes
| Attribute | Type | Description |
|---|---|---|
filename |
string |
The filename of the attachment, taken from Content-Disposition or the name parameter of Content-Type. May be empty. |
content_type |
string |
The MIME media type of the attachment (e.g. application/pdf, image/png). |
data |
bytes |
The decoded payload bytes of the attachment. |
Example
for att in msg.attachments:
if att.content_type == "application/pdf":
store_pdf(att.filename, att.data)
users module
The users module is a predeclared global that lets scripts look up user
accounts by name or by email address.
Functions
users.get(username)
Look up a user by username.
- Args:
username: string - Returns: a
Userobject, orNoneif no such user exists.
users.get_by_address(address)
Look up the user that owns a given email address.
- Args:
address: string - Returns: a
Userobject, orNoneif no user owns the address.
Example
def on_message_deliver(conn, user, msg):
recipient = msg.header_to.address
owner = users.get_by_address(recipient)
if owner.name is "admin":
return "Postmaster"
return "INBOX"