Message – A single message

class Message(msg_p, parent=None)

Represents a single Email message

Technically, this wraps the underlying notmuch_message_t structure. A user will usually not create these objects themselves but get them as search results.

As it implements __cmp__(), it is possible to compare two Messages using if msg1 == msg2: ….

Parameters:
  • msg_p – A pointer to an internal notmuch_message_t Structure. If it is None, we will raise an NullPointerError.
  • parent – A ‘parent’ object is passed which this message is derived from. We save a reference to it, so we can automatically delete the parent object once all derived objects are dead.
get_message_id()

Returns the message ID

Returns:String with a message ID
Raises:NotInitializedError if the message is not initialized.
get_thread_id()

Returns the thread ID

The returned string belongs to ‘message’ will only be valid for as long as the message is valid.

This function will not return None since Notmuch ensures that every message belongs to a single thread.

Returns:String with a thread ID
Raises:NotInitializedError if the message is not initialized.
get_replies()

Gets all direct replies to this message as Messages iterator

Note

This call only makes sense if ‘message’ was ultimately obtained from a Thread object, (such as by coming directly from the result of calling Thread.get_toplevel_messages() or by any number of subsequent calls to get_replies()). If this message was obtained through some non-thread means, (such as by a call to Query.search_messages()), then this function will return an empty Messages iterator.

Returns:Messages.
Raises:NotInitializedError if the message is not initialized.
get_filename()

Returns the file path of the message file

Returns:Absolute file path & name of the message file
Raises:NotInitializedError if the message is not initialized.
get_filenames()

Get all filenames for the email corresponding to ‘message’

Returns a Filenames() generator with all absolute filepaths for messages recorded to have the same Message-ID. These files must not necessarily have identical content.

FLAG
FLAG.MATCH
This flag is automatically set by a Query.search_threads on those messages that match the query. This allows us to distinguish matches from the rest of the messages in that thread.
get_flag(flag)

Checks whether a specific flag is set for this message

The method Query.search_threads() sets Message.FLAG.MATCH for those messages that match the query. This method allows us to get the value of this flag.

Parameters:flag – One of the Message.FLAG values (currently only Message.FLAG.MATCH
Returns:An unsigned int (0/1), indicating whether the flag is set.
Raises:NotInitializedError if the message is not initialized.
set_flag(flag, value)

Sets/Unsets a specific flag for this message

Parameters:
  • flag – One of the Message.FLAG values (currently only Message.FLAG.MATCH
  • value – A bool indicating whether to set or unset the flag.
Raises:

NotInitializedError if the message is not initialized.

get_date()

Returns time_t of the message date

For the original textual representation of the Date header from the message call notmuch_message_get_header() with a header value of “date”.

Returns:A time_t timestamp.
Return type:c_unit64
Raises:NotInitializedError if the message is not initialized.
get_header(header)

Get the value of the specified header.

The value will be read from the actual message file, not from the notmuch database. The header name is case insensitive.

Returns an empty string (“”) if the message does not contain a header line matching ‘header’.

Parameters:header (str) – The name of the header to be retrieved. It is not case-sensitive.
Returns:The header value as string
Raises:NotInitializedError if the message is not initialized
Raises:NullPointerError if any error occurred
get_tags()

Returns the message tags

Returns:A Tags iterator.
Raises:NotInitializedError if the message is not initialized
Raises:NullPointerError if any error occurred
get_property(prop)

Retrieve the value for a single property key

Parameters:prop – The name of the property to get.
Returns:String with the property value or None if there is no such key. In the case of multiple values for the given key, the first one is retrieved.
Raises:NotInitializedError if message has not been initialized
get_properties(prop='', exact=False)

Get the properties of the message, returning a generator of name, value pairs.

The generator will yield once per value. There might be more than one value on each name, so the generator might yield the same name several times.

Parameters:
  • prop – The name of the property to get. Otherwise it will return the full list of properties of the message.
  • exact – if True, require exact match with key. Otherwise treat as prefix.
Yields:

Each property values as a pair of name, value

Ytype:

pairs of str

Raises:

NotInitializedError if message has not been initialized

maildir_flags_to_tags()

Synchronize file Maildir flags to notmuch tags

Flag Action if present —- —————– ‘D’ Adds the “draft” tag to the message ‘F’ Adds the “flagged” tag to the message ‘P’ Adds the “passed” tag to the message ‘R’ Adds the “replied” tag to the message ‘S’ Removes the “unread” tag from the message

For each flag that is not present, the opposite action (add/remove) is performed for the corresponding tags. If there are multiple filenames associated with this message, the flag is considered present if it appears in one or more filenames. (That is, the flags from the multiple filenames are combined with the logical OR operator.)

As a convenience, you can set the sync_maildir_flags parameter in Database.index_file() to implicitly call this.

Returns:a STATUS. In short, you want to see notmuch.STATUS.SUCCESS here. See there for details.
tags_to_maildir_flags()

Synchronize notmuch tags to file Maildir flags

‘D’ if the message has the “draft” tag ‘F’ if the message has the “flagged” tag ‘P’ if the message has the “passed” tag ‘R’ if the message has the “replied” tag ‘S’ if the message does not have the “unread” tag

Any existing flags unmentioned in the list above will be preserved in the renaming.

Also, if this filename is in a directory named “new”, rename it to be within the neighboring directory named “cur”.

Do note that calling this method while a message is frozen might not work yet, as the modified tags have not been committed yet to the database.

Returns:a STATUS value. In short, you want to see notmuch.STATUS.SUCCESS here. See there for details.
remove_tag(tag, sync_maildir_flags=False)

Removes a tag from the given message

If the message has no such tag, this is a non-operation and will report success anyway.

Parameters:
  • tag – String with a ‘tag’ to be removed.
  • sync_maildir_flags – If notmuch configuration is set to do this, add maildir flags corresponding to notmuch tags. See underlying method tags_to_maildir_flags(). Use False if you want to add/remove many tags on a message without having to physically rename the file every time. Do note, that this will do nothing when a message is frozen, as tag changes will not be committed to the database yet.
Returns:

STATUS.SUCCESS if the tag was successfully removed or if the message had no such tag. Raises an exception otherwise.

Raises:

NullPointerError if the tag argument is NULL

Raises:

TagTooLongError if the length of tag exceeds Message.NOTMUCH_TAG_MAX)

Raises:

ReadOnlyDatabaseError if the database was opened in read-only mode so message cannot be modified

Raises:

NotInitializedError if message has not been initialized

add_tag(tag, sync_maildir_flags=False)

Adds a tag to the given message

Adds a tag to the current message. The maximal tag length is defined in the notmuch library and is currently 200 bytes.

Parameters:
  • tag – String with a ‘tag’ to be added.
  • sync_maildir_flags – If notmuch configuration is set to do this, add maildir flags corresponding to notmuch tags. See underlying method tags_to_maildir_flags(). Use False if you want to add/remove many tags on a message without having to physically rename the file every time. Do note, that this will do nothing when a message is frozen, as tag changes will not be committed to the database yet.
Returns:

STATUS.SUCCESS if the tag was successfully added. Raises an exception otherwise.

Raises:

NullPointerError if the tag argument is NULL

Raises:

TagTooLongError if the length of tag exceeds Message.NOTMUCH_TAG_MAX)

Raises:

ReadOnlyDatabaseError if the database was opened in read-only mode so message cannot be modified

Raises:

NotInitializedError if message has not been initialized

remove_all_tags(sync_maildir_flags=False)

Removes all tags from the given message.

See freeze() for an example showing how to safely replace tag values.

Parameters:sync_maildir_flags – If notmuch configuration is set to do this, add maildir flags corresponding to notmuch tags. See tags_to_maildir_flags(). Use False if you want to add/remove many tags on a message without having to physically rename the file every time. Do note, that this will do nothing when a message is frozen, as tag changes will not be committed to the database yet.
Returns:STATUS.SUCCESS if the tags were successfully removed. Raises an exception otherwise.
Raises:ReadOnlyDatabaseError if the database was opened in read-only mode so message cannot be modified
Raises:NotInitializedError if message has not been initialized
freeze()

Freezes the current state of ‘message’ within the database

This means that changes to the message state, (via add_tag(), remove_tag(), and remove_all_tags()), will not be committed to the database until the message is thaw() ed.

Multiple calls to freeze/thaw are valid and these calls will “stack”. That is there must be as many calls to thaw as to freeze before a message is actually thawed.

The ability to do freeze/thaw allows for safe transactions to change tag values. For example, explicitly setting a message to have a given set of tags might look like this:

msg.freeze()
msg.remove_all_tags(False)
for tag in new_tags:
    msg.add_tag(tag, False)
msg.thaw()
msg.tags_to_maildir_flags()

With freeze/thaw used like this, the message in the database is guaranteed to have either the full set of original tag values, or the full set of new tag values, but nothing in between.

Imagine the example above without freeze/thaw and the operation somehow getting interrupted. This could result in the message being left with no tags if the interruption happened after remove_all_tags() but before add_tag().

Returns:STATUS.SUCCESS if the message was successfully frozen. Raises an exception otherwise.
Raises:ReadOnlyDatabaseError if the database was opened in read-only mode so message cannot be modified
Raises:NotInitializedError if message has not been initialized
thaw()

Thaws the current ‘message’

Thaw the current ‘message’, synchronizing any changes that may have occurred while ‘message’ was frozen into the notmuch database.

See freeze() for an example of how to use this function to safely provide tag changes.

Multiple calls to freeze/thaw are valid and these calls with “stack”. That is there must be as many calls to thaw as to freeze before a message is actually thawed.

Returns:STATUS.SUCCESS if the message was successfully frozen. Raises an exception otherwise.
Raises:UnbalancedFreezeThawError if an attempt was made to thaw an unfrozen message. That is, there have been an unbalanced number of calls to freeze() and thaw().
Raises:NotInitializedError if message has not been initialized
__str__()

Return str(self).