Introduction
Aspose.Email FOSS for Python (aspose-email-foss) is a MIT-licensed Python library for
working with Outlook MSG files, RFC-5322 EML messages, and Compound File Binary (CFB)
storage structures. The library requires no native extensions and installs directly from PyPI
with pip install aspose-email-foss.
The package targets Python 3.10 and later. It implements the MSG message format and the underlying CFB container format from scratch, giving deterministic control over how messages are serialized and read across Windows, macOS, Linux, and containerized environments.
This page covers the key feature areas: MSG creation and reading, EML interoperability, MAPI property access, attachment and recipient management, and low-level CFB storage operations.
Key Features
Creating MSG Files
MapiMessage.create() constructs a new MAPI message from a subject string and a plain-text
body string. After construction, set typed MAPI properties through set_property() using the
PropertyId enum, add recipients with add_recipient(), and attach binary data with
add_attachment(). Call save() to write the result to disk or to_bytes() to get the
raw bytes.
from aspose.email_foss import msg
message = msg.MapiMessage.create(
"Quarterly status update",
"Please review the attached summary.",
)
message.set_property(msg.PropertyId.SENDER_NAME, "Build Agent")
message.set_property(msg.PropertyId.SENDER_EMAIL_ADDRESS, "build.agent@example.com")
message.set_property(msg.PropertyId.INTERNET_MESSAGE_ID, "<report-001@example.com>")
message.add_recipient("alice@example.com", display_name="Alice")
message.add_attachment("summary.txt", b"Q2 metrics attached.", mime_type="text/plain")
message.save("quarterly.msg")
Reading MSG Files
Load an existing .msg file with MapiMessage.from_file(). The returned object exposes
subject, body, and other typed attributes. Use iter_attachments_info() to iterate
over attachment metadata and iter_properties() to walk all MAPI properties on the message.
from aspose.email_foss import msg
loaded = msg.MapiMessage.from_file("quarterly.msg")
print(loaded.subject)
print(loaded.body)
for attachment in loaded.iter_attachments_info():
print(attachment.filename)
loaded.close()
Converting MSG to EML and Back
to_email_message() converts a MapiMessage into a standard Python email.message.EmailMessage
object, preserving subject, sender, recipients, body, and attachments. Serialize the result with
as_bytes() to obtain EML-format bytes suitable for SMTP delivery or archival.
The reverse direction — building a MapiMessage from an EmailMessage — uses
MapiMessage.from_email_message().
from aspose.email_foss import msg
# MSG → EML
loaded = msg.MapiMessage.from_file("quarterly.msg")
eml = loaded.to_email_message()
with open("quarterly.eml", "wb") as f:
f.write(eml.as_bytes())
loaded.close()
# EML → MSG
from email.message import EmailMessage
source = EmailMessage()
source["Subject"] = "Meeting notes"
source["From"] = "alice@example.com"
source["To"] = "bob@example.com"
source.set_content("Notes from today's standup.")
mapi = msg.MapiMessage.from_email_message(source)
mapi.save("meeting-notes.msg")
MAPI Property Access
set_property() and get_property_value() provide typed access to MAPI properties using the
PropertyId enum. iter_properties() returns all properties as MapiProperty objects, each
exposing a property_id, property_type, and value.
from aspose.email_foss import msg
message = msg.MapiMessage.from_file("quarterly.msg")
for prop in message.iter_properties():
print(hex(prop.property_id), prop.property_type, repr(prop.value)[:60])
message.close()
Common PropertyId values include SUBJECT, SENDER_NAME, SENDER_EMAIL_ADDRESS,
INTERNET_MESSAGE_ID, MESSAGE_DELIVERY_TIME, BODY, and BODY_HTML.
Attachment and Recipient Management
add_attachment() accepts a filename string, raw bytes, and an optional MIME type. For
embedding an existing MapiMessage as an attachment, use add_embedded_message_attachment().
add_recipient() accepts an email address and an optional display name and recipient type
(RECIPIENT_TYPE_TO, RECIPIENT_TYPE_CC, RECIPIENT_TYPE_BCC).
from aspose.email_foss import msg
message = msg.MapiMessage.create("Project handoff", "Files are attached.")
message.set_property(msg.PropertyId.SENDER_EMAIL_ADDRESS, "sender@example.com")
message.add_recipient("lead@example.com", display_name="Tech Lead")
message.add_recipient(
"backup@example.com",
display_name="Backup",
recipient_type=msg.RECIPIENT_TYPE_CC,
)
message.add_attachment("spec.pdf", b"%PDF-1.4 ...", mime_type="application/pdf")
message.save("handoff.msg")
Low-Level CFB Container Access
The library includes a standalone CFB layer for reading and writing Compound File Binary
containers independently of MAPI. CFBReader.from_file() loads any .msg or .cfb file
and exposes its directory entries. iter_storages() and iter_streams() enumerate the
container tree; get_stream_data() extracts raw stream bytes.
from aspose.email_foss import msg
reader = msg.CFBReader.from_file("quarterly.msg")
print(f"CFB version={reader.major_version} sector_size={reader.sector_size}")
print(f"Directory entries: {reader.directory_entry_count}")
for entry in reader.iter_streams():
data = reader.get_stream_data(entry.stream_id)
print(f"Stream: {entry.name!r} size={len(data)}")
reader.close()
Quick Start
pip install aspose-email-fossfrom aspose.email_foss import msg
# Create a message
message = msg.MapiMessage.create("Hello from Python", "This is the message body.")
message.set_property(msg.PropertyId.SENDER_EMAIL_ADDRESS, "sender@example.com")
message.add_recipient("recipient@example.com", display_name="Recipient")
message.save("hello.msg")
# Read it back and convert to EML
with msg.MapiMessage.from_file("hello.msg") as loaded:
eml = loaded.to_email_message()
print("Subject:", eml["Subject"])
print("From:", eml["From"])
Supported Formats
| Format | Extension | Read | Write |
|---|---|---|---|
| MSG | .msg | ✓ | ✓ |
| CFB | .cfb | ✓ | ✓ |
| EML | .eml | ✓ | ✓ |
MSG files are read via MapiMessage.from_file(). EML is accessed through the
from_email_message() / to_email_message() bridge. CFB containers are handled
directly by CFBReader.
Open Source & Licensing
Aspose.Email FOSS for Python is released under the MIT License. The source is available
on GitHub and the package is distributed via PyPI under the name aspose-email-foss.
MIT licensing permits use in commercial applications without royalty or attribution
requirements beyond license text inclusion.