Documentation ¶
Overview ¶
Package store implements storage for accounts, their mailboxes, IMAP subscriptions and messages, and broadcasts updates (e.g. mail delivery) to interested sessions (e.g. IMAP connections).
Layout of storage for accounts:
<DataDir>/accounts/<name>/index.db <DataDir>/accounts/<name>/msg/[a-zA-Z0-9_-]+/<id>
Index.db holds tables for user information, mailboxes, and messages. Messages are stored in the msg/ subdirectory, each in their own file. The on-disk message does not contain headers generated during an incoming SMTP transaction, such as Received and Authentication-Results headers. Those are in the database to prevent having to rewrite incoming messages (e.g. Authentication-Result for DKIM signatures can only be determined after having read the message). Messages must be read through MsgReader, which transparently adds the prefix from the database.
Index ¶
- Variables
- func BroadcastChanges(acc *Account, ch []Change)
- func CheckKeyword(kw string) error
- func CheckMailboxName(name string, allowInbox bool) (normalizedName string, isInbox bool, rerr error)
- func CloseRemoveTempFile(log mlog.Log, f *os.File, descr string)
- func CreateMessageTemp(log mlog.Log, pattern string) (*os.File, error)
- func ExportMessages(ctx context.Context, log mlog.Log, db *bstore.DB, accountDir string, ...) error
- func MergeKeywords(l, add []string) ([]string, bool)
- func MessagePath(messageID int64) string
- func MessageRuleset(log mlog.Log, dest config.Destination, m *Message, msgPrefix []byte, ...) *config.Ruleset
- func ParseDovecotKeywordsFlags(r io.Reader, log mlog.Log) ([]string, error)
- func RemoveKeywords(l, remove []string) ([]string, bool)
- func SessionAdd(ctx context.Context, log mlog.Log, accountName, loginAddress string) (session SessionToken, csrf CSRFToken, rerr error)
- func SessionAddToken(ctx context.Context, log mlog.Log, ls *LoginSession) error
- func SessionRemove(ctx context.Context, log mlog.Log, accountName string, ...) error
- func StartAuthCache()
- func Switchboard() (stop func())
- type Account
- func OpenAccount(log mlog.Log, name string) (*Account, error)
- func OpenAccountDB(log mlog.Log, accountDir, accountName string) (a *Account, rerr error)
- func OpenEmail(log mlog.Log, email string) (*Account, config.Destination, error)
- func OpenEmailAuth(log mlog.Log, email string, password string) (acc *Account, rerr error)
- func (a *Account) AddMessageSize(log mlog.Log, tx *bstore.Tx, size int64) error
- func (a *Account) AssignThreads(ctx context.Context, log mlog.Log, txOpt *bstore.Tx, startMessageID int64, ...) error
- func (a *Account) CanAddMessageSize(tx *bstore.Tx, size int64) (ok bool, maxSize int64, err error)
- func (a *Account) CheckClosed()
- func (a *Account) CheckConsistency() error
- func (a *Account) Close() error
- func (a *Account) Conf() (config.Account, bool)
- func (a *Account) DeliverDestination(log mlog.Log, dest config.Destination, m *Message, msgFile *os.File) error
- func (a *Account) DeliverMailbox(log mlog.Log, mailbox string, m *Message, msgFile *os.File) error
- func (a *Account) DeliverMessage(log mlog.Log, tx *bstore.Tx, m *Message, msgFile *os.File, ...) error
- func (a *Account) HighestDeletedModSeq(tx *bstore.Tx) (ModSeq, error)
- func (a *Account) MailboxCreate(tx *bstore.Tx, name string) (changes []Change, created []string, exists bool, rerr error)
- func (a *Account) MailboxDelete(ctx context.Context, log mlog.Log, tx *bstore.Tx, mailbox Mailbox) (changes []Change, removeMessageIDs []int64, hasChildren bool, rerr error)
- func (a *Account) MailboxEnsure(tx *bstore.Tx, name string, subscribe bool) (mb Mailbox, changes []Change, rerr error)
- func (a *Account) MailboxExists(tx *bstore.Tx, name string) (bool, error)
- func (a *Account) MailboxFind(tx *bstore.Tx, name string) (*Mailbox, error)
- func (a *Account) MailboxRename(tx *bstore.Tx, mbsrc Mailbox, dst string) (changes []Change, isInbox, notExists, alreadyExists bool, rerr error)
- func (a *Account) MessagePath(messageID int64) string
- func (a *Account) MessageReader(m Message) *MsgReader
- func (a *Account) NextModSeq(tx *bstore.Tx) (ModSeq, error)
- func (a *Account) NextUIDValidity(tx *bstore.Tx) (uint32, error)
- func (a *Account) OpenJunkFilter(ctx context.Context, log mlog.Log) (*junk.Filter, *config.JunkFilter, error)
- func (a *Account) QuotaMessageSize() int64
- func (a *Account) RejectsRemove(log mlog.Log, rejectsMailbox, messageID string) error
- func (a *Account) ResetThreading(ctx context.Context, log mlog.Log, batchSize int, clearIDs bool) (int, error)
- func (a *Account) RetrainMessage(ctx context.Context, log mlog.Log, tx *bstore.Tx, jf *junk.Filter, m *Message, ...) error
- func (a *Account) RetrainMessages(ctx context.Context, log mlog.Log, tx *bstore.Tx, msgs []Message, ...) (rerr error)
- func (a *Account) SendLimitReached(tx *bstore.Tx, recipients []smtp.Path) (msglimit, rcptlimit int, rerr error)
- func (a *Account) SetPassword(log mlog.Log, password string) error
- func (a *Account) Subjectpass(email string) (key string, err error)
- func (a *Account) SubscriptionEnsure(tx *bstore.Tx, name string) ([]Change, error)
- func (a *Account) ThreadingWait(log mlog.Log) error
- func (a *Account) TidyRejectsMailbox(log mlog.Log, rejectsMailbox string) (hasSpace bool, rerr error)
- func (a *Account) TrainMessage(ctx context.Context, log mlog.Log, jf *junk.Filter, m Message) (bool, error)
- func (a *Account) WithRLock(fn func())
- func (a *Account) WithWLock(fn func())
- type Archiver
- type CRAMMD5
- type CSRFToken
- type Change
- type ChangeAddMailbox
- type ChangeAddSubscription
- type ChangeAddUID
- type ChangeFlags
- type ChangeMailboxCounts
- type ChangeMailboxKeywords
- type ChangeMailboxSpecialUse
- type ChangeRemoveMailbox
- type ChangeRemoveUIDs
- type ChangeRenameMailbox
- type ChangeThread
- type Comm
- type DirArchiver
- type DiskUsage
- type Flags
- type FromAddressSettings
- type LoginSession
- type Mailbox
- func (mb *Mailbox) CalculateCounts(tx *bstore.Tx) (mc MailboxCounts, err error)
- func (mb Mailbox) ChangeCounts() ChangeMailboxCounts
- func (mb Mailbox) ChangeKeywords() ChangeMailboxKeywords
- func (mb Mailbox) ChangeSpecialUse() ChangeMailboxSpecialUse
- func (mb Mailbox) KeywordsChanged(origmb Mailbox) bool
- type MailboxCounts
- type MaildirReader
- type MboxArchiver
- type MboxReader
- type Message
- func (m Message) ChangeAddUID() ChangeAddUID
- func (m Message) ChangeFlags(orig Flags) ChangeFlags
- func (m Message) ChangeThread() ChangeThread
- func (m *Message) JunkFlagsForMailbox(mb Mailbox, conf config.Account)
- func (m Message) LoadPart(r io.ReaderAt) (message.Part, error)
- func (m Message) MailboxCounts() (mc MailboxCounts)
- func (m Message) NeedsTraining() bool
- func (m *Message) PrepareExpunge()
- func (m *Message) PrepareThreading(log mlog.Log, part *message.Part)
- type ModSeq
- type MsgReader
- type MsgSource
- type NextUIDValidity
- type Outgoing
- type Password
- type Quoting
- type Recipient
- type RecipientDomainTLS
- type RulesetNoListID
- type RulesetNoMailbox
- type RulesetNoMsgFrom
- type SCRAM
- type SessionToken
- type Settings
- type SpecialUse
- type Subjectpass
- type Subscription
- type SyncState
- type TarArchiver
- type UID
- type Upgrade
- type Validation
- type ViewMode
- type WordSearch
- type ZipArchiver
Constants ¶
This section is empty.
Variables ¶
var ( ErrUnknownMailbox = errors.New("no such mailbox") ErrUnknownCredentials = errors.New("credentials not found") ErrAccountUnknown = errors.New("no such account") ErrOverQuota = errors.New("account over quota") )
var CheckConsistencyOnClose = true
If true, each time an account is closed its database file is checked for consistency. If an inconsistency is found, panic is called. Set by default because of all the packages with tests, the mox main function sets it to false again.
var DBTypes = []any{ NextUIDValidity{}, Message{}, Recipient{}, Mailbox{}, Subscription{}, Outgoing{}, Password{}, Subjectpass{}, SyncState{}, Upgrade{}, RecipientDomainTLS{}, DiskUsage{}, LoginSession{}, Settings{}, FromAddressSettings{}, RulesetNoListID{}, RulesetNoMsgFrom{}, RulesetNoMailbox{}, }
Types stored in DB.
var DefaultInitialMailboxes = config.InitialMailboxes{ SpecialUse: config.SpecialUseMailboxes{ Sent: "Sent", Archive: "Archive", Trash: "Trash", Draft: "Drafts", Junk: "Junk", }, }
var ErrNoJunkFilter = errors.New("junkfilter: not configured")
ErrNoJunkFilter indicates user did not configure/enable a junk filter.
FlagsAll is all flags set, for use as mask.
var InitialUIDValidity = func() uint32 { return uint32(time.Now().Unix() >> 1) }
InitialUIDValidity returns a UIDValidity used for initializing an account. It can be replaced during tests with a predictable value.
Functions ¶
func BroadcastChanges ¶ added in v0.0.6
BroadcastChanges ensures changes are sent to all listeners on the accoount.
func CheckKeyword ¶ added in v0.0.6
CheckKeyword returns an error if kw is not a valid keyword. Kw should already be in lower-case.
func CheckMailboxName ¶ added in v0.0.6
func CheckMailboxName(name string, allowInbox bool) (normalizedName string, isInbox bool, rerr error)
CheckMailboxName checks if name is valid, returning an INBOX-normalized name. I.e. it changes various casings of INBOX and INBOX/* to Inbox and Inbox/*. Name is invalid if it contains leading/trailing/double slashes, or when it isn't unicode-normalized, or when empty or has special characters.
If name is the inbox, and allowInbox is false, this is indicated with the isInbox return parameter. For that case, and for other invalid names, an error is returned.
func CloseRemoveTempFile ¶ added in v0.0.8
CloseRemoveTempFile closes and removes f, a file described by descr. Often used in a defer after creating a temporary file.
func CreateMessageTemp ¶
CreateMessageTemp creates a temporary file, e.g. for delivery. The is created in subdirectory tmp of the data directory, so the file is on the same file system as the accounts directory, so renaming files can succeed. The caller is responsible for closing and possibly removing the file. The caller should ensure the contents of the file are synced to disk before attempting to deliver the message.
func ExportMessages ¶
func ExportMessages(ctx context.Context, log mlog.Log, db *bstore.DB, accountDir string, archiver Archiver, maildir bool, mailboxOpt string, recursive bool) error
ExportMessages writes messages to archiver. Either in maildir format, or otherwise in mbox. If mailboxOpt is empty, all mailboxes are exported, otherwise only the named mailbox.
Some errors are not fatal and result in skipped messages. In that happens, a file "errors.txt" is added to the archive describing the errors. The goal is to let users export (hopefully) most messages even in the face of errors.
func MergeKeywords ¶ added in v0.0.5
MergeKeywords adds keywords from add into l, returning whether it added any keyword, and the slice with keywords, a new slice if modifications were made. Keywords are only added if they aren't already present. Should only be used with keywords, not with system flags like \Seen.
func MessagePath ¶
MessagePath returns the filename of the on-disk filename, relative to the containing directory such as <account>/msg or queue. Returns names like "AB/1".
func MessageRuleset ¶
func MessageRuleset(log mlog.Log, dest config.Destination, m *Message, msgPrefix []byte, msgFile *os.File) *config.Ruleset
MessageRuleset returns the first ruleset (if any) that matches the message represented by msgPrefix and msgFile, with smtp and validation fields from m.
func ParseDovecotKeywordsFlags ¶ added in v0.0.6
ParseDovecotKeywordsFlags attempts to parse a dovecot-keywords file. It only returns valid flags/keywords, as lower-case. If an error is encountered and returned, any keywords that were found are still returned. The returned list has both system/well-known flags and custom keywords.
func RemoveKeywords ¶ added in v0.0.5
RemoveKeywords removes keywords from l, returning whether any modifications were made, and a slice, a new slice in case of modifications. Keywords must have been validated earlier, e.g. through ParseFlagKeywords or CheckKeyword. Should only be used with valid keywords, not with system flags like \Seen.
func SessionAdd ¶ added in v0.0.9
func SessionAdd(ctx context.Context, log mlog.Log, accountName, loginAddress string) (session SessionToken, csrf CSRFToken, rerr error)
SessionAdd creates a new session token, with csrf token, and adds it to the database and in-memory session cache. If there are too many sessions, the oldest is removed.
func SessionAddToken ¶ added in v0.0.9
SessionAddTokens adds a prepared or pre-existing LoginSession to the database and cache. Can be used to restore a session token that was used to reset a password.
func SessionRemove ¶ added in v0.0.9
func SessionRemove(ctx context.Context, log mlog.Log, accountName string, sessionToken SessionToken) error
SessionRemove removes a session from the database and in-memory cache. Future operations using the session token will fail.
func StartAuthCache ¶ added in v0.0.2
func StartAuthCache()
StartAuthCache starts a goroutine that regularly clears the auth cache.
func Switchboard ¶
func Switchboard() (stop func())
Switchboard distributes changes to accounts to interested listeners. See Comm and Change.
Types ¶
type Account ¶
type Account struct { Name string // Name, according to configuration. Dir string // Directory where account files, including the database, bloom filter, and mail messages, are stored for this account. DBPath string // Path to database with mailboxes, messages, etc. DB *bstore.DB // Open database connection. // Write lock must be held for account/mailbox modifications including message delivery. // Read lock for reading mailboxes/messages. // When making changes to mailboxes/messages, changes must be broadcasted before // releasing the lock to ensure proper UID ordering. sync.RWMutex // contains filtered or unexported fields }
Account holds the information about a user, includings mailboxes, messages, imap subscriptions.
func OpenAccount ¶
OpenAccount opens an account by name.
No additional data path prefix or ".db" suffix should be added to the name. A single shared account exists per name.
func OpenAccountDB ¶ added in v0.0.6
OpenAccountDB opens an account database file and returns an initialized account or error. Only exported for use by subcommands that verify the database file. Almost all account opens must go through OpenAccount/OpenEmail/OpenEmailAuth.
func OpenEmail ¶
OpenEmail opens an account given an email address.
The email address may contain a catchall separator.
func OpenEmailAuth ¶
OpenEmailAuth opens an account given an email address and password.
The email address may contain a catchall separator.
func (*Account) AddMessageSize ¶ added in v0.0.9
AddMessageSize adjusts the DiskUsage.MessageSize by size.
func (*Account) AssignThreads ¶ added in v0.0.7
func (a *Account) AssignThreads(ctx context.Context, log mlog.Log, txOpt *bstore.Tx, startMessageID int64, batchSize int, progressWriter io.Writer) error
AssignThreads assigns thread-related fields to messages with ID >= startMessageID. Changes are committed each batchSize changes if txOpt is nil (i.e. during automatic account upgrade, we don't want to block database access for a long time). If txOpt is not nil, all changes are made in that transaction.
When resetting thread assignments, the caller must first clear the existing thread fields.
Messages are processed in order of ID, so when added to the account, not necessarily by received/date. Most threaded messages can immediately be matched to their parent message. If not, we keep track of the missing message-id and resolve as soon as we encounter it. At the end, we resolve all remaining messages, they start with a cycle.
Does not set Seen flag for muted threads.
Progress is written to progressWriter, every 100k messages.
func (*Account) CanAddMessageSize ¶ added in v0.0.9
CanAddMessageSize checks if a message of size bytes can be added, depending on total message size and configured quota for account.
func (*Account) CheckClosed ¶ added in v0.0.11
func (a *Account) CheckClosed()
CheckClosed asserts that the account has a zero reference count. For use in tests.
func (*Account) CheckConsistency ¶ added in v0.0.6
CheckConsistency checks the consistency of the database and returns a non-nil error for these cases:
- Missing on-disk file for message. - Mismatch between message size and length of MsgPrefix and on-disk file. - Missing HaveCounts. - Incorrect mailbox counts. - Incorrect total message size. - Message with UID >= mailbox uid next. - Mailbox uidvalidity >= account uid validity. - ModSeq > 0, CreateSeq > 0, CreateSeq <= ModSeq. - All messages have a nonzero ThreadID, and no cycles in ThreadParentID, and parent messages the same ThreadParentIDs tail.
func (*Account) Close ¶
Close reduces the reference count, and closes the database connection when it was the last user.
func (*Account) Conf ¶
Conf returns the configuration for this account if it still exists. During an SMTP session, a configuration update may drop an account.
func (*Account) DeliverDestination ¶ added in v0.0.7
func (a *Account) DeliverDestination(log mlog.Log, dest config.Destination, m *Message, msgFile *os.File) error
DeliverDestination delivers an email to dest, based on the configured rulesets.
Returns ErrOverQuota when account would be over quota after adding message.
Caller must hold account wlock (mailbox may be created). Message delivery, possible mailbox creation, and updated mailbox counts are broadcasted.
func (*Account) DeliverMailbox ¶
DeliverMailbox delivers an email to the specified mailbox.
Returns ErrOverQuota when account would be over quota after adding message.
Caller must hold account wlock (mailbox may be created). Message delivery, possible mailbox creation, and updated mailbox counts are broadcasted.
func (*Account) DeliverMessage ¶ added in v0.0.3
func (a *Account) DeliverMessage(log mlog.Log, tx *bstore.Tx, m *Message, msgFile *os.File, sync, notrain, nothreads, updateDiskUsage bool) error
DeliverMessage delivers a mail message to the account.
The message, with msg.MsgPrefix and msgFile combined, must have a header section. The caller is responsible for adding a header separator to msg.MsgPrefix if missing from an incoming message.
If the destination mailbox has the Sent special-use flag, the message is parsed for its recipients (to/cc/bcc). Their domains are added to Recipients for use in dmarc reputation.
If sync is true, the message file and its directory are synced. Should be true for regular mail delivery, but can be false when importing many messages.
If updateDiskUsage is true, the account total message size (for quota) is updated. Callers must check if a message can be added within quota before calling DeliverMessage.
If CreateSeq/ModSeq is not set, it is assigned automatically.
Must be called with account rlock or wlock.
Caller must broadcast new message.
Caller must update mailbox counts.
func (*Account) HighestDeletedModSeq ¶ added in v0.0.6
func (*Account) MailboxCreate ¶ added in v0.0.6
func (a *Account) MailboxCreate(tx *bstore.Tx, name string) (changes []Change, created []string, exists bool, rerr error)
MailboxCreate creates a new mailbox, including any missing parent mailboxes, the total list of created mailboxes is returned in created. On success, if exists is false and rerr nil, the changes must be broadcasted by the caller.
Name must be in normalized form.
func (*Account) MailboxDelete ¶ added in v0.0.6
func (a *Account) MailboxDelete(ctx context.Context, log mlog.Log, tx *bstore.Tx, mailbox Mailbox) (changes []Change, removeMessageIDs []int64, hasChildren bool, rerr error)
MailboxDelete deletes a mailbox by ID. If it has children, the return value indicates that and an error is returned.
Caller should broadcast the changes and remove files for the removed message IDs.
func (*Account) MailboxEnsure ¶
func (a *Account) MailboxEnsure(tx *bstore.Tx, name string, subscribe bool) (mb Mailbox, changes []Change, rerr error)
Ensure mailbox is present in database, adding records for the mailbox and its parents if they aren't present.
If subscribe is true, any mailboxes that were created will also be subscribed to. Caller must hold account wlock. Caller must propagate changes if any.
func (*Account) MailboxExists ¶ added in v0.0.3
MailboxExists checks if mailbox exists. Caller must hold account rlock.
func (*Account) MailboxFind ¶ added in v0.0.3
MailboxFind finds a mailbox by name, returning a nil mailbox and nil error if mailbox does not exist.
func (*Account) MailboxRename ¶ added in v0.0.6
func (a *Account) MailboxRename(tx *bstore.Tx, mbsrc Mailbox, dst string) (changes []Change, isInbox, notExists, alreadyExists bool, rerr error)
MailboxRename renames mailbox mbsrc to dst, and any missing parents for the destination, and any children of mbsrc and the destination.
Names must be normalized and cannot be Inbox.
func (*Account) MessagePath ¶
MessagePath returns the file system path of a message.
func (*Account) MessageReader ¶
MessageReader opens a message for reading, transparently combining the message prefix with the original incoming message.
func (*Account) NextModSeq ¶ added in v0.0.6
NextModSeq returns the next modification sequence, which is global per account, over all types.
func (*Account) NextUIDValidity ¶
NextUIDValidity returns the next new/unique uidvalidity to use for this account.
func (*Account) OpenJunkFilter ¶
func (a *Account) OpenJunkFilter(ctx context.Context, log mlog.Log) (*junk.Filter, *config.JunkFilter, error)
OpenJunkFilter returns an opened junk filter for the account. If the account does not have a junk filter enabled, ErrNotConfigured is returned. Do not forget to save the filter after modifying, and to always close the filter when done. An empty filter is initialized on first access of the filter.
func (*Account) QuotaMessageSize ¶ added in v0.0.9
QuotaMessageSize returns the effective maximum total message size for an account. Returns 0 if there is no maximum.
func (*Account) RejectsRemove ¶
RejectsRemove removes a message from the rejects mailbox if present. Caller most hold account wlock. Changes are broadcasted.
func (*Account) ResetThreading ¶ added in v0.0.7
func (a *Account) ResetThreading(ctx context.Context, log mlog.Log, batchSize int, clearIDs bool) (int, error)
ResetThreading resets the MessageID and SubjectBase fields for all messages in the account. If clearIDs is true, all Thread* fields are also cleared. Changes are made in transactions of batchSize changes. The total number of updated messages is returned.
ModSeq is not changed. Calles should bump the uid validity of the mailboxes to propagate the changes to IMAP clients.
func (*Account) RetrainMessage ¶
func (a *Account) RetrainMessage(ctx context.Context, log mlog.Log, tx *bstore.Tx, jf *junk.Filter, m *Message, absentOK bool) error
RetrainMessage untrains and/or trains a message, if relevant given m.TrainedJunk and m.Junk/m.Notjunk. Updates m.TrainedJunk after retraining.
func (*Account) RetrainMessages ¶
func (a *Account) RetrainMessages(ctx context.Context, log mlog.Log, tx *bstore.Tx, msgs []Message, absentOK bool) (rerr error)
RetrainMessages (un)trains messages, if relevant given their flags. Updates m.TrainedJunk after retraining.
func (*Account) SendLimitReached ¶ added in v0.0.6
func (a *Account) SendLimitReached(tx *bstore.Tx, recipients []smtp.Path) (msglimit, rcptlimit int, rerr error)
SendLimitReached checks whether sending a message to recipients would reach the limit of outgoing messages for the account. If so, the message should not be sent. If the returned numbers are >= 0, the limit was reached and the values are the configured limits.
To limit damage to the internet and our reputation in case of account compromise, we limit the max number of messages sent in a 24 hour window, both total number of messages and number of first-time recipients.
func (*Account) SetPassword ¶
SetPassword saves a new password for this account. This password is used for IMAP, SMTP (submission) sessions and the HTTP account web page.
func (*Account) Subjectpass ¶
Subjectpass returns the signing key for use with subjectpass for the given email address with canonical localpart.
func (*Account) SubscriptionEnsure ¶ added in v0.0.3
SubscriptionEnsure ensures a subscription for name exists. The mailbox does not have to exist. Any parents are not automatically subscribed. Changes are returned and must be broadcasted by the caller.
func (*Account) ThreadingWait ¶ added in v0.0.7
ThreadingWait blocks until the one-time account threading upgrade for the account has completed, and returns an error if not successful.
To be used before starting an import of messages.
func (*Account) TidyRejectsMailbox ¶
func (a *Account) TidyRejectsMailbox(log mlog.Log, rejectsMailbox string) (hasSpace bool, rerr error)
TidyRejectsMailbox removes old reject emails, and returns whether there is space for a new delivery.
Caller most hold account wlock. Changes are broadcasted.
func (*Account) TrainMessage ¶
func (a *Account) TrainMessage(ctx context.Context, log mlog.Log, jf *junk.Filter, m Message) (bool, error)
TrainMessage trains the junk filter based on the current m.Junk/m.Notjunk flags, disregarding m.TrainedJunk and not updating that field.
type Archiver ¶
type Archiver interface { // Add file to archive. If name ends with a slash, it is created as a directory and // the returned io.WriteCloser can be ignored. Create(name string, size int64, mtime time.Time) (io.WriteCloser, error) Close() error }
Archiver can archive multiple mailboxes and their messages.
type CRAMMD5 ¶
CRAMMD5 holds HMAC ipad and opad hashes that are initialized with the first block with (a derivation of) the key/password, so we don't store the password in plain text.
func (CRAMMD5) MarshalBinary ¶
BinaryMarshal is used by bstore to store the ipad/opad hash states.
func (*CRAMMD5) UnmarshalBinary ¶
BinaryUnmarshal is used by bstore to restore the ipad/opad hash states.
type Change ¶
type Change any
Change to mailboxes/subscriptions/messages in an account. One of the Change* types in this package.
type ChangeAddMailbox ¶
ChangeAddMailbox is sent for a newly created mailbox.
type ChangeAddSubscription ¶
type ChangeAddSubscription struct { Name string Flags []string // For additional IMAP flags like \NonExistent. }
ChangeAddSubscription is sent for an added subscription to a mailbox.
type ChangeAddUID ¶
type ChangeAddUID struct { MailboxID int64 UID UID ModSeq ModSeq Flags Flags // System flags. Keywords []string // Other flags. }
ChangeAddUID is sent for a new message in a mailbox.
type ChangeFlags ¶
type ChangeFlags struct { MailboxID int64 UID UID ModSeq ModSeq Mask Flags // Which flags are actually modified. Flags Flags // New flag values. All are set, not just mask. Keywords []string // Non-system/well-known flags/keywords/labels. }
ChangeFlags is sent for an update to flags for a message, e.g. "Seen".
type ChangeMailboxCounts ¶ added in v0.0.6
type ChangeMailboxCounts struct { MailboxID int64 MailboxName string MailboxCounts }
ChangeMailboxCounts is sent when the number of total/deleted/unseen/unread messages changes.
type ChangeMailboxKeywords ¶ added in v0.0.6
ChangeMailboxKeywords is sent when keywords are changed for a mailbox. For example, when a message is added with a previously unseen keyword.
type ChangeMailboxSpecialUse ¶ added in v0.0.6
type ChangeMailboxSpecialUse struct { MailboxID int64 MailboxName string SpecialUse SpecialUse }
ChangeMailboxSpecialUse is sent when a special-use flag changes.
type ChangeRemoveMailbox ¶
ChangeRemoveMailbox is sent for a removed mailbox.
type ChangeRemoveUIDs ¶
type ChangeRemoveUIDs struct { MailboxID int64 UIDs []UID // Must be in increasing UID order, for IMAP. ModSeq ModSeq }
ChangeRemoveUIDs is sent for removal of one or more messages from a mailbox.
type ChangeRenameMailbox ¶
ChangeRenameMailbox is sent for a rename mailbox.
type ChangeThread ¶ added in v0.0.7
ChangeThread is sent when muted/collapsed changes.
type Comm ¶
type Comm struct { Pending chan struct{} // Receives block until changes come in, e.g. for IMAP IDLE. sync.Mutex // contains filtered or unexported fields }
Comm handles communication with the goroutine that maintains the account/mailbox/message state.
func RegisterComm ¶
Register starts a Comm for the account. Unregister must be called.
type DirArchiver ¶
type DirArchiver struct {
Dir string
}
DirArchiver is an Archiver that writes to a directory.
func (DirArchiver) Create ¶
func (a DirArchiver) Create(name string, size int64, mtime time.Time) (io.WriteCloser, error)
Create creates name in the file system, in dir. name must always use forwarded slashes.
type DiskUsage ¶ added in v0.0.9
type DiskUsage struct { ID int64 // Always one record with ID 1. MessageSize int64 // Sum of all messages, for quota accounting. }
DiskUsage tracks quota use.
type Flags ¶
type Flags struct { Seen bool Answered bool Flagged bool Forwarded bool Junk bool Notjunk bool Deleted bool Draft bool Phishing bool MDNSent bool }
Flags for a mail message.
func ParseFlagsKeywords ¶ added in v0.0.6
ParseFlagsKeywords parses a list of textual flags into system/known flags, and other keywords. Keywords are lower-cased and sorted and check for valid syntax.
func (Flags) Changed ¶ added in v0.0.6
Changed returns a mask of flags that have been between f and other.
type FromAddressSettings ¶ added in v0.0.11
FromAddressSettings are webmail client settings per "From" address.
type LoginSession ¶ added in v0.0.9
type LoginSession struct { ID int64 Created time.Time `bstore:"nonzero,default now"` // Of original login. Expires time.Time `bstore:"nonzero"` // Extended each time it is used. SessionTokenBinary [16]byte `bstore:"nonzero"` // Stored in cookie, like "webmailsession" or "webaccountsession". CSRFTokenBinary [16]byte // For API requests, in "x-mox-csrf" header. AccountName string `bstore:"nonzero"` LoginAddress string `bstore:"nonzero"` // contains filtered or unexported fields }
LoginSession represents a login session. We keep a limited number of sessions for a user, removing the oldest session when a new one is created.
func SessionUse ¶ added in v0.0.9
func SessionUse(ctx context.Context, log mlog.Log, accountName string, sessionToken SessionToken, csrfToken CSRFToken) (LoginSession, error)
SessionUse checks if a session is valid. If csrfToken is the empty string, no CSRF check is done. Otherwise it must be the csrf token associated with the session token.
type Mailbox ¶
type Mailbox struct { ID int64 // "Inbox" is the name for the special IMAP "INBOX". Slash separated // for hierarchy. Name string `bstore:"nonzero,unique"` // If UIDs are invalidated, e.g. when renaming a mailbox to a previously existing // name, UIDValidity must be changed. Used by IMAP for synchronization. UIDValidity uint32 // UID likely to be assigned to next message. Used by IMAP to detect messages // delivered to a mailbox. UIDNext UID SpecialUse // Keywords as used in messages. Storing a non-system keyword for a message // automatically adds it to this list. Used in the IMAP FLAGS response. Only // "atoms" are allowed (IMAP syntax), keywords are case-insensitive, only stored in // lower case (for JMAP), sorted. Keywords []string HaveCounts bool // Whether MailboxCounts have been initialized. MailboxCounts // Statistics about messages, kept up to date whenever a change happens. }
Mailbox is collection of messages, e.g. Inbox or Sent.
func (*Mailbox) CalculateCounts ¶ added in v0.0.6
func (mb *Mailbox) CalculateCounts(tx *bstore.Tx) (mc MailboxCounts, err error)
CalculateCounts calculates the full current counts for messages in the mailbox.
func (Mailbox) ChangeCounts ¶ added in v0.0.6
func (mb Mailbox) ChangeCounts() ChangeMailboxCounts
CountsChange returns a change with mailbox counts.
func (Mailbox) ChangeKeywords ¶ added in v0.0.6
func (mb Mailbox) ChangeKeywords() ChangeMailboxKeywords
ChangeKeywords returns a change with new keywords for a mailbox (e.g. after setting a new keyword on a message in the mailbox), for broadcasting to other connections.
func (Mailbox) ChangeSpecialUse ¶ added in v0.0.6
func (mb Mailbox) ChangeSpecialUse() ChangeMailboxSpecialUse
ChangeSpecialUse returns a change for special-use flags, for broadcasting to other connections.
func (Mailbox) KeywordsChanged ¶ added in v0.0.6
KeywordsChanged returns whether the keywords in a mailbox have changed.
type MailboxCounts ¶ added in v0.0.6
type MailboxCounts struct { Total int64 // Total number of messages, excluding \Deleted. For JMAP. Deleted int64 // Number of messages with \Deleted flag. Used for IMAP message count that includes messages with \Deleted. Unread int64 // Messages without \Seen, excluding those with \Deleted, for JMAP. Unseen int64 // Messages without \Seen, including those with \Deleted, for IMAP. Size int64 // Number of bytes for all messages. }
MailboxCounts tracks statistics about messages for a mailbox.
func (*MailboxCounts) Add ¶ added in v0.0.6
func (mc *MailboxCounts) Add(delta MailboxCounts)
Add increases mailbox counts mc with those of delta.
func (MailboxCounts) String ¶ added in v0.0.6
func (mc MailboxCounts) String() string
func (*MailboxCounts) Sub ¶ added in v0.0.6
func (mc *MailboxCounts) Sub(delta MailboxCounts)
Add decreases mailbox counts mc with those of delta.
type MaildirReader ¶
type MaildirReader struct {
// contains filtered or unexported fields
}
func NewMaildirReader ¶
type MboxArchiver ¶ added in v0.0.11
MboxArchive fakes being an archiver to which a single mbox file can be written. It returns an error when a second file is added. It returns its writer for the first file to be written, leaving parameters unused.
func (*MboxArchiver) Close ¶ added in v0.0.11
func (a *MboxArchiver) Close() error
Close on an mbox archiver does nothing.
func (*MboxArchiver) Create ¶ added in v0.0.11
func (a *MboxArchiver) Create(name string, size int64, mtime time.Time) (io.WriteCloser, error)
Create returns the underlying writer for the first call, and an error on later calls.
type MboxReader ¶
type MboxReader struct {
// contains filtered or unexported fields
}
MboxReader reads messages from an mbox file, implementing MsgSource.
func NewMboxReader ¶
func (*MboxReader) Next ¶
Next returns the next message read from the mbox file. The file is a temporary file and must be removed/consumed. The third return value is the position in the file.
func (*MboxReader) Position ¶
func (mr *MboxReader) Position() string
Position returns "<filename>:<lineno>" for the current position.
type Message ¶
type Message struct { // ID, unchanged over lifetime, determines path to on-disk msg file. // Set during deliver. ID int64 UID UID `bstore:"nonzero"` // UID, for IMAP. Set during deliver. MailboxID int64 `bstore:"nonzero,unique MailboxID+UID,index MailboxID+Received,index MailboxID+ModSeq,ref Mailbox"` // Modification sequence, for faster syncing with IMAP QRESYNC and JMAP. // ModSeq is the last modification. CreateSeq is the Seq the message was inserted, // always <= ModSeq. If Expunged is set, the message has been removed and should not // be returned to the user. In this case, ModSeq is the Seq where the message is // removed, and will never be changed again. // We have an index on both ModSeq (for JMAP that synchronizes per account) and // MailboxID+ModSeq (for IMAP that synchronizes per mailbox). // The index on CreateSeq helps efficiently finding created messages for JMAP. // The value of ModSeq is special for IMAP. Messages that existed before ModSeq was // added have 0 as value. But modseq 0 in IMAP is special, so we return it as 1. If // we get modseq 1 from a client, the IMAP server will translate it to 0. When we // return modseq to clients, we turn 0 into 1. ModSeq ModSeq `bstore:"index"` CreateSeq ModSeq `bstore:"index"` Expunged bool // If set, this message was delivered to a Rejects mailbox. When it is moved to a // different mailbox, its MailboxOrigID is set to the destination mailbox and this // flag cleared. IsReject bool // If set, this is a forwarded message (through a ruleset with IsForward). This // causes fields used during junk analysis to be moved to their Orig variants, and // masked IP fields cleared, so they aren't used in junk classifications for // incoming messages. This ensures the forwarded messages don't cause negative // reputation for the forwarding mail server, which may also be sending regular // messages. IsForward bool // MailboxOrigID is the mailbox the message was originally delivered to. Typically // Inbox or Rejects, but can also be a mailbox configured in a Ruleset, or // Postmaster, TLS/DMARC reporting addresses. MailboxOrigID is not changed when the // message is moved to another mailbox, e.g. Archive/Trash/Junk. Used for // per-mailbox reputation. // // MailboxDestinedID is normally 0, but when a message is delivered to the Rejects // mailbox, it is set to the intended mailbox according to delivery rules, // typically that of Inbox. When such a message is moved out of Rejects, the // MailboxOrigID is corrected by setting it to MailboxDestinedID. This ensures the // message is used for reputation calculation for future deliveries to that // mailbox. // // These are not bstore references to prevent having to update all messages in a // mailbox when the original mailbox is removed. Use of these fields requires // checking if the mailbox still exists. MailboxOrigID int64 MailboxDestinedID int64 Received time.Time `bstore:"default now,index"` // Full IP address of remote SMTP server. Empty if not delivered over SMTP. The // masked IPs are used to classify incoming messages. They are left empty for // messages matching a ruleset for forwarded messages. RemoteIP string RemoteIPMasked1 string `bstore:"index RemoteIPMasked1+Received"` // For IPv4 /32, for IPv6 /64, for reputation. RemoteIPMasked2 string `bstore:"index RemoteIPMasked2+Received"` // For IPv4 /26, for IPv6 /48. RemoteIPMasked3 string `bstore:"index RemoteIPMasked3+Received"` // For IPv4 /21, for IPv6 /32. // Only set if present and not an IP address. Unicode string. Empty for forwarded // messages. EHLODomain string `bstore:"index EHLODomain+Received"` MailFrom string // With localpart and domain. Can be empty. MailFromLocalpart smtp.Localpart // SMTP "MAIL FROM", can be empty. // Only set if it is a domain, not an IP. Unicode string. Empty for forwarded // messages, but see OrigMailFromDomain. MailFromDomain string `bstore:"index MailFromDomain+Received"` RcptToLocalpart smtp.Localpart // SMTP "RCPT TO", can be empty. RcptToDomain string // Unicode string. // Parsed "From" message header, used for reputation along with domain validation. MsgFromLocalpart smtp.Localpart MsgFromDomain string `bstore:"index MsgFromDomain+Received"` // Unicode string. MsgFromOrgDomain string `bstore:"index MsgFromOrgDomain+Received"` // Unicode string. // Simplified statements of the Validation fields below, used for incoming messages // to check reputation. EHLOValidated bool MailFromValidated bool MsgFromValidated bool EHLOValidation Validation // Validation can also take reverse IP lookup into account, not only SPF. MailFromValidation Validation // Can have SPF-specific validations like ValidationSoftfail. MsgFromValidation Validation // Desirable validations: Strict, DMARC, Relaxed. Will not be just Pass. // Domains with verified DKIM signatures. Unicode string. For forwarded messages, a // DKIM domain that matched a ruleset's verified domain is left out, but included // in OrigDKIMDomains. DKIMDomains []string `bstore:"index DKIMDomains+Received"` // For forwarded messages, OrigEHLODomain string OrigDKIMDomains []string // Canonicalized Message-Id, always lower-case and normalized quoting, without // <>'s. Empty if missing. Used for matching message threads, and to prevent // duplicate reject delivery. MessageID string `bstore:"index"` // For matching threads in case there is no References/In-Reply-To header. It is // lower-cased, white-space collapsed, mailing list tags and re/fwd tags removed. SubjectBase string `bstore:"index"` // Hash of message. For rejects delivery in case there is no Message-ID, only set // when delivered as reject. MessageHash []byte // ID of message starting this thread. ThreadID int64 `bstore:"index"` // IDs of parent messages, from closest parent to the root message. Parent messages // may be in a different mailbox, or may no longer exist. ThreadParentIDs must // never contain the message id itself (a cycle), and parent messages must // reference the same ancestors. ThreadParentIDs []int64 // ThreadMissingLink is true if there is no match with a direct parent. E.g. first // ID in ThreadParentIDs is not the direct ancestor (an intermediate message may // have been deleted), or subject-based matching was done. ThreadMissingLink bool // If set, newly delivered child messages are automatically marked as read. This // field is copied to new child messages. Changes are propagated to the webmail // client. ThreadMuted bool // If set, this (sub)thread is collapsed in the webmail client, for threading mode // "on" (mode "unread" ignores it). This field is copied to new child message. // Changes are propagated to the webmail client. ThreadCollapsed bool // If received message was known to match a mailing list rule (with modified junk // filtering). IsMailingList bool // If this message is a DSN, generated by us or received. For DSNs, we don't look // at the subject when matching threads. DSN bool ReceivedTLSVersion uint16 // 0 if unknown, 1 if plaintext/no TLS, otherwise TLS cipher suite. ReceivedTLSCipherSuite uint16 ReceivedRequireTLS bool // Whether RequireTLS was known to be used for incoming delivery. Flags // For keywords other than system flags or the basic well-known $-flags. Only in // "atom" syntax (IMAP), they are case-insensitive, always stored in lower-case // (for JMAP), sorted. Keywords []string `bstore:"index"` Size int64 TrainedJunk *bool // If nil, no training done yet. Otherwise, true is trained as junk, false trained as nonjunk. MsgPrefix []byte // Typically holds received headers and/or header separator. // ParsedBuf message structure. Currently saved as JSON of message.Part because bstore // cannot yet store recursive types. Created when first needed, and saved in the // database. // todo: once replaced with non-json storage, remove date fixup in ../message/part.go. ParsedBuf []byte }
Message stored in database and per-message file on disk.
Contents are always the combined data from MsgPrefix and the on-disk file named based on ID.
Messages always have a header section, even if empty. Incoming messages without header section must get an empty header section added before inserting.
func (Message) ChangeAddUID ¶ added in v0.0.6
func (m Message) ChangeAddUID() ChangeAddUID
func (Message) ChangeFlags ¶ added in v0.0.6
func (m Message) ChangeFlags(orig Flags) ChangeFlags
func (Message) ChangeThread ¶ added in v0.0.7
func (m Message) ChangeThread() ChangeThread
func (*Message) JunkFlagsForMailbox ¶
JunkFlagsForMailbox sets Junk and Notjunk flags based on mailbox name if configured. Often used when delivering/moving/copying messages to a mailbox. Mail clients are not very helpful with setting junk/notjunk flags. But clients can move/copy messages to other mailboxes. So we set flags when clients move a message.
func (Message) MailboxCounts ¶ added in v0.0.6
func (m Message) MailboxCounts() (mc MailboxCounts)
MailboxCounts returns the delta to counts this message means for its mailbox.
func (Message) NeedsTraining ¶
NeedsTraining returns whether message needs a training update, based on TrainedJunk (current training status) and new Junk/Notjunk flags.
func (*Message) PrepareExpunge ¶ added in v0.0.6
func (m *Message) PrepareExpunge()
PrepareExpunge clears fields that are no longer needed after an expunge, so almost all fields. Does not change ModSeq, but does set Expunged.
type ModSeq ¶ added in v0.0.6
type ModSeq int64
ModSeq represents a modseq as stored in the database. ModSeq 0 in the database is sent to the client as 1, because modseq 0 is special in IMAP. ModSeq coming from the client are of type int64.
func ModSeqFromClient ¶ added in v0.0.6
ModSeqFromClient converts a modseq from a client to a modseq for internal use, e.g. in a database query. ModSeq 1 is turned into 0 (the Go zero value for ModSeq).
type MsgReader ¶
type MsgReader struct {
// contains filtered or unexported fields
}
MsgReader provides access to a message. Reads return the "msg_prefix" in the database (typically received headers), followed by the on-disk msg file contents. MsgReader is an io.Reader, io.ReaderAt and io.Closer.
func FileMsgReader ¶
FileMsgReader makes a MsgReader for an open file. If initialization fails, reads will return the error. Only call close on the returned MsgReader if you want to close msgFile.
func (*MsgReader) Read ¶
Read reads data from the msg, taking prefix and on-disk msg file into account. The read offset is adjusted after the read.
func (*MsgReader) ReadAt ¶
ReadAt reads data from the msg, taking prefix and on-disk msg file into account. The read offset is not affected by ReadAt.
type MsgSource ¶
type MsgSource interface { // Return next message, or io.EOF when there are no more. Next() (*Message, *os.File, string, error) }
MsgSource is implemented by readers for mailbox file formats.
type NextUIDValidity ¶
NextUIDValidity is a singleton record in the database with the next UIDValidity to use for the next mailbox.
type Outgoing ¶ added in v0.0.3
type Outgoing struct { ID int64 Recipient string `bstore:"nonzero,index"` // Canonical international address with utf8 domain. Submitted time.Time `bstore:"nonzero,default now"` }
Outgoing is a message submitted for delivery from the queue. Used to enforce maximum outgoing messages.
type Password ¶
type Password struct { Hash string // bcrypt hash for IMAP LOGIN, SASL PLAIN and HTTP basic authentication. CRAMMD5 CRAMMD5 // For SASL CRAM-MD5. SCRAMSHA1 SCRAM // For SASL SCRAM-SHA-1. SCRAMSHA256 SCRAM // For SASL SCRAM-SHA-256. }
Password holds credentials in various forms, for logging in with SMTP/IMAP.
type Quoting ¶ added in v0.0.11
type Quoting string
Quoting is a setting for how to quote in replies/forwards.
type Recipient ¶
type Recipient struct { ID int64 MessageID int64 `bstore:"nonzero,ref Message"` // Ref gives it its own index, useful for fast removal as well. Localpart string `bstore:"nonzero"` // Encoded localpart. Domain string `bstore:"nonzero,index Domain+Localpart"` // Unicode string. OrgDomain string `bstore:"nonzero,index"` // Unicode string. Sent time.Time `bstore:"nonzero"` }
Recipient represents the recipient of a message. It is tracked to allow first-time incoming replies from users this account has sent messages to. When a mailbox is added to the Sent mailbox the message is parsed and recipients are inserted as recipient. Recipients are never removed other than for removing the message. On move/copy of a message, recipients aren't modified either. For IMAP, this assumes a client simply appends messages to the Sent mailbox (as opposed to copying messages from some place).
type RecipientDomainTLS ¶ added in v0.0.8
type RecipientDomainTLS struct { Domain string // Unicode. Updated time.Time `bstore:"default now"` STARTTLS bool // Supports STARTTLS. RequireTLS bool // Supports RequireTLS SMTP extension. }
RecipientDomainTLS stores TLS capabilities of a recipient domain as encountered during most recent connection (delivery attempt).
type RulesetNoListID ¶ added in v0.0.11
type RulesetNoListID struct { ID int64 RcptToAddress string `bstore:"nonzero"` ListID string `bstore:"nonzero"` ToInbox bool // Otherwise from Inbox to other mailbox. }
RulesetNoListID records a user "no" response to the question of creating/removing a ruleset after moving a message with list-id header from/to the inbox.
type RulesetNoMailbox ¶ added in v0.0.11
type RulesetNoMailbox struct { ID int64 // The mailbox from/to which the move has happened. // Not a references, if mailbox is deleted, an entry becomes ineffective. MailboxID int64 `bstore:"nonzero"` ToMailbox bool // Whether MailboxID is the destination of the move (instead of source). }
RulesetNoMailbox represents a "never from/to this mailbox" response to the question of adding/removing a ruleset after moving a message.
type RulesetNoMsgFrom ¶ added in v0.0.11
type RulesetNoMsgFrom struct { ID int64 RcptToAddress string `bstore:"nonzero"` MsgFromAddress string `bstore:"nonzero"` // Unicode. ToInbox bool // Otherwise from Inbox to other mailbox. }
RulesetNoMsgFrom records a user "no" response to the question of creating/moveing a ruleset after moving a mesage with message "from" address from/to the inbox.
type SessionToken ¶ added in v0.0.9
type SessionToken string
SessionToken and CSRFToken are types to prevent mixing them up. Base64 raw url encoded.
type Settings ¶ added in v0.0.11
type Settings struct { ID uint8 // Singleton ID 1. Signature string Quoting Quoting // Whether to show the bars underneath the address input fields indicating // starttls/dnssec/dane/mtasts/requiretls support by address. ShowAddressSecurity bool // Show HTML version of message by default, instead of plain text. ShowHTML bool }
Settings are webmail client settings.
type SpecialUse ¶ added in v0.0.6
SpecialUse identifies a specific role for a mailbox, used by clients to understand where messages should go.
type Subjectpass ¶
type Subjectpass struct { Email string // Our destination address (canonical, with catchall localpart stripped). Key string }
Subjectpass holds the secret key used to sign subjectpass tokens.
type Subscription ¶
type Subscription struct {
Name string
}
Subscriptions are separate from existence of mailboxes.
type SyncState ¶ added in v0.0.6
type SyncState struct { ID int // Just a single record with ID 1. // Last used, next assigned will be one higher. The first value we hand out is 2. // That's because 0 (the default value for old existing messages, from before the // Message.ModSeq field) is special in IMAP, so we return it as 1. LastModSeq ModSeq `bstore:"nonzero"` // Highest ModSeq of expunged record that we deleted. When a clients synchronizes // and requests changes based on a modseq before this one, we don't have the // history to provide information about deletions. We normally keep these expunged // records around, but we may periodically truly delete them to reclaim storage // space. Initially set to -1 because we don't want to match with any ModSeq in the // database, which can be zero values. HighestDeletedModSeq ModSeq }
SyncState track ModSeqs.
type TarArchiver ¶
TarArchiver is an Archiver that writes to a tar file.
func (TarArchiver) Create ¶
func (a TarArchiver) Create(name string, size int64, mtime time.Time) (io.WriteCloser, error)
Create adds a file header to the tar file.
type Validation ¶
type Validation uint8
Validation of "message From" domain.
const ( ValidationUnknown Validation = 0 ValidationStrict Validation = 1 // Like DMARC, with strict policies. ValidationDMARC Validation = 2 // Actual DMARC policy. ValidationRelaxed Validation = 3 // Like DMARC, with relaxed policies. ValidationPass Validation = 4 // For SPF. ValidationNeutral Validation = 5 // For SPF. ValidationTemperror Validation = 6 ValidationPermerror Validation = 7 ValidationFail Validation = 8 ValidationSoftfail Validation = 9 // For SPF. ValidationNone Validation = 10 // E.g. No records. )
func SPFValidation ¶
func SPFValidation(status spf.Status) Validation
SPFValidation returns a Validation for an spf.Status.
type ViewMode ¶ added in v0.0.11
type ViewMode string
ViewMode how a message should be viewed: its text parts, html parts, or html with loading external resources.
type WordSearch ¶ added in v0.0.6
type WordSearch struct {
// contains filtered or unexported fields
}
WordSearch holds context for a search, with scratch buffers to prevent allocations for each message.
func PrepareWordSearch ¶ added in v0.0.6
func PrepareWordSearch(words, notWords []string) WordSearch
PrepareWordSearch returns a search context that can be used to match multiple messages (after each other, not concurrently).
func (WordSearch) MatchPart ¶ added in v0.0.6
MatchPart returns whether the part/mail message p matches the search. The search terms are matched against content-transfer-decoded and charset-decoded bodies and optionally headers. HTML parts are currently treated as regular text, without parsing HTML.
type ZipArchiver ¶
ZipArchiver is an Archiver that writes to a zip file.
func (ZipArchiver) Create ¶
func (a ZipArchiver) Create(name string, size int64, mtime time.Time) (io.WriteCloser, error)
Create adds a file header to the zip file.