| FazBrowse GitHub Viewer | Trending | | Home |
| Tools: [Download Repo ZIP] [Original HTTPS Page] |
| Name | Name | Last commit date | ||
|---|---|---|---|---|
mail-parser is a production-grade, RFC-compliant email parsing library that goes far beyond a simple wrapper for Python's email module. It transforms raw email messages into richly structured Python objects with unparalleled precision, making complex email processing accessible and reliable.
As the battle-tested foundation of SpamScope—a powerful email security and threat analysis platform—mail-parser has proven itself in demanding production environments where accuracy and security matter most.
🔒 Security-First Design: Built specifically for email security analysis and digital forensics, mail-parser excels at detecting malformed structures, hidden content, and RFC non-compliance that could indicate malicious intent.
🎯 Comprehensive Parsing: Extracts every component of an email—headers, bodies (plain text and HTML), attachments, metadata, routing information, and even subtle defects that other parsers miss.
🔍 Multi-Format Access: Every parsed element is accessible in three formats (Python object, raw string, and JSON), enabling seamless integration with any workflow or downstream system.
🛡️ Defect Detection: Identifies and categorizes RFC violations, malformed MIME boundaries, and structural anomalies that could hide malicious payloads or bypass security filters.
📧 Outlook Support: Native handling of Microsoft Outlook .msg files alongside standard email formats, making it versatile for diverse email ecosystems.
⚡ Production-Ready: Trusted by security professionals and developers worldwide, with extensive test coverage and proven reliability in high-stakes environments.
mail-parser is fully compatible with Python 3, ensuring modern performance and reliability.
mail-parser converts Outlook .msg files to standard .eml before parsing. Two conversion backends are supported:
extract-msg (recommended, pure Python). No external tools required. Install the optional extra:
pip install mail-parser[outlook]msgconvert (deprecated, external Perl tool). Requires the libemail-outlook-message-perl system package:
apt-get install libemail-outlook-message-perl # Debian-based systems
apt-cache show libemail-outlook-message-perl # package detailsBackend precedence: when extract-msg is installed it is used first. Only when it is not available does mail-parser fall back to the msgconvert external tool, logging a deprecation warning. If neither backend is available, parse_from_file_msg() raises MailParserOSError telling you to install either path.
⚠️ Deprecated: the msgconvert external-tool backend is deprecated and will be removed in a future release. Migrate to the pure-Python backend with pip install mail-parser[outlook].
💥 BREAKING CHANGE: the default .msg conversion backend changed. When extract-msg is installed it is now preferred over msgconvert. The two converters produce different intermediate .eml output, so some parsed fields (header ordering, encoding edge cases, attachment naming) can differ from the previous msgconvert-only behavior. Downstream code asserting on exact .msg-derived output may need updating.
mail-parser can be downloaded, used, and modified free of charge. It is available under the Apache 2 license.
mail-parser is a labor of love and commitment to the open-source community. Thousands of developers and security professionals worldwide rely on this library for critical email processing and threat analysis. Your support directly fuels continued innovation and excellence.
Your contribution—no matter the size—makes a real difference. By supporting mail-parser, you enable us to:
Every donation, whether $5 or $500, directly funds development time and infrastructure costs. Join the community of supporters who believe in accessible, reliable, and secure email parsing for everyone.
Or contribute with Bitcoin:
Bitcoin Address: bc1qxhz3tghztpjqdt7atey68s344wvmugtl55tm32
Thank you for supporting the evolution of mail-parser!
Explore mail-parser on these platforms:
mail-parser transforms raw email messages into comprehensive, RFC-compliant Python objects that faithfully mirror the structure defined by IETF email protocol standards. Each property of the parsed object directly corresponds to standard RFC headers—"From", "To", "Cc", "Bcc", "Subject", and many more—providing intuitive, Pythonic access to every email component.
The library extracts and structures every aspect of an email message:
Every parsed element offers three distinct access patterns for maximum flexibility:
This versatile architecture makes mail-parser exceptionally powerful for diverse use cases—from security analysis and forensics to email migration, compliance auditing, and automated processing pipelines.
Standard RFC Headers (directly accessible as properties):
Additional Parsed Components:
The attachments property returns a list of dictionaries, each containing comprehensive metadata:
To access custom or vendor-specific headers, replace hyphens with underscores. For example, to access the X-MSMail-Priority header:
mail.X_MSMail_PriorityThis underscore-for-hyphen convenience, and the _json / _raw suffixes, apply only to attribute access written by you. Names read out of a message — the keys of mail and headers — are looked up literally, so a header genuinely named X_Spam_Flag or Subject_json keeps its own name and its own value. Attribute names beginning with an underscore are not headers and raise AttributeError.
The received header is intelligently parsed into individual hops, revealing the complete email routing path. Each hop contains structured fields:
Critical Security Feature: mail-parser detects and reports structural defects in email messages.
The defects property identifies RFC non-compliance issues that may indicate malformed or malicious emails—a crucial capability for security analysis and threat detection.
Multi-Format Property Access Pattern:
All parsed properties provide three access variants using intuitive suffixes:
Example usage:
mail.to # Python list of recipient objects
mail.to_json # JSON string representation
mail.to_raw # Original "To:" header string as it appears in the emailThe command-line tool outputs parsed emails in JSON format by default for easy integration with other tools and pipelines.
Email structural defects are not merely technical curiosities—they represent potential security vulnerabilities that sophisticated attackers actively exploit to bypass spam filters, antivirus scanners, and email security gateways.
Malformed MIME boundaries, for example, can conceal illegitimate epilogue sections containing:
mail-parser was specifically engineered for security analysis and digital forensics, with defect detection as a core feature rather than an afterthought. The library captures and categorizes even subtle structural anomalies that other parsers silently ignore or mishandle.
By leveraging mail-parser's defect detection, security teams can:
This robust defect detection mechanism has made mail-parser the trusted choice for security platforms like SpamScope, where identifying malicious intent hidden in structural anomalies can mean the difference between a blocked threat and a successful attack.
Fedele Mantuano: LinkedIn
mail-parser requires Python 3 and can be installed in seconds using pip. Follow these steps:
pip install mail-parserpip show mail-parserFor contributors and developers who want to work with the source code, we recommend using uv for dependency management:
git clone https://github.com/SpamScope/mail-parser.git
cd mail-parser
uv syncThis setup installs all development and testing dependencies in an isolated virtual environment, ensuring a clean and reproducible development workflow.
For comprehensive documentation about uv, visit the official uv documentation.
Import the mailparser module and use the convenient factory functions:
import mailparser
mail = mailparser.parse_from_bytes(byte_mail) # Parse from bytes object
mail = mailparser.parse_from_file(f) # Parse from file path
mail = mailparser.parse_from_file_msg(outlook_mail) # Parse Outlook .msg file
mail = mailparser.parse_from_file_obj(fp) # Parse from file object
mail = mailparser.parse_from_string(raw_mail) # Parse from stringOnce parsed, access all email components through intuitive properties:
mail.attachments # List of all attachments with metadata
mail.body # Complete message body
mail.date # Parsed datetime object (UTC)
mail.defects # List of RFC compliance defects
mail.defects_categories # Categorized defect types
mail.delivered_to # Delivery address
mail.from_ # Sender information
mail.get_server_ipaddress(trust="my_server_mail_trust") # Reliable sender IP
mail.headers # All headers as structured object
mail.mail # Fully tokenized mail object
mail.message # Underlying email.message.Message object
mail.message_as_string # Reconstructed message as string
mail.message_id # Unique message identifier
mail.received # Parsed routing information (hop-by-hop)
mail.subject # Email subject
mail.text_plain # Plain text body parts (list)
mail.text_html # HTML body parts (list)
mail.text_not_managed # Unprocessed text parts (check logs for subtypes)
mail.to # Recipient information
mail.to_domains # Extracted recipient domains
mail.timezone # Timezone information (offset from UTC)
mail.mail_partial # Partial mail object (main parts only)Write all attachments to a specified directory:
mail.write_attachments(base_path)Attachment filenames are supplied by the email sender. The filename value in mail.attachments intentionally preserves that untrusted metadata for analysis and display. Do not pass it directly to open() or join it to a directory. The safe_filename field provides a sanitized basename when one exists, but applications saving files should prefer write_attachments(), which also validates containment, rejects symlink destinations, and deduplicates names within the attachment batch. Deduplication is case-insensitive, because APFS, exFAT and SMB collapse Invoice.pdf and invoice.pdf onto a single file.
A single unusable attachment never costs the rest of the batch: write_attachments() logs a warning and moves on when a filename cannot be sanitized, a payload cannot be decoded, or the write itself fails, so the remaining attachments are still saved. A containment failure is not treated this way: it raises MailParserPathError and stops the batch.
After installing mail-parser with pip, you can use the mailparser command-line tool for quick email analysis, batch processing, or integration with shell scripts and pipelines.
usage: mailparser [-h] (-f FILE | -s STRING | -k)
[-l {CRITICAL,ERROR,WARNING,INFO,DEBUG,NOTSET}] [-j] [-b]
[-a] [-r] [-t] [-dt] [-m] [-u] [-c] [-d] [-o]
[-i Trust mail server string] [-p] [-z] [-v]
Wrapper for email Python Standard Library
optional arguments:
-h, --help show this help message and exit
-f FILE, --file FILE Raw email file (default: None)
-s STRING, --string STRING
Raw email string (default: None)
-k, --stdin Enable parsing from stdin (default: False)
-l {CRITICAL,ERROR,WARNING,INFO,DEBUG,NOTSET}, --log-level {CRITICAL,ERROR,WARNING,INFO,DEBUG,NOTSET}
Set log level (default: WARNING)
-j, --json Show the JSON of parsed mail (default: False)
-b, --body Print the body of mail (default: False)
-a, --attachments Print the attachments of mail (default: False)
-r, --headers Print the headers of mail (default: False)
-t, --to Print the to of mail (default: False)
-dt, --delivered-to Print the delivered-to of mail (default: False)
-m, --from Print the from of mail (default: False)
-u, --subject Print the subject of mail (default: False)
-c, --receiveds Print all receiveds of mail (default: False)
-d, --defects Print the defects of mail (default: False)
-o, --outlook Analyze Outlook msg (default: False)
-i Trust mail server string, --senderip Trust mail server string
Extract a reliable sender IP address heuristically
(default: None)
-p, --mail-hash Print mail fingerprints without headers (default:
False)
-z, --attachments-hash
Print attachments with fingerprints (default: False)
-sa, --store-attachments
Store attachments on disk (default: False)
-ap ATTACHMENTS_PATH, --attachments-path ATTACHMENTS_PATH
Path where store attachments (default: /tmp)
-v, --version show program's version number and exit
It takes as input a raw mail and generates a parsed object.
Parse an email file and output as formatted JSON:
mailparser -f example_mail -jExtract only the subject and sender:
mailparser -f example_mail -u -mAnalyze an Outlook .msg file with defect detection:
mailparser -f email.msg -o -d -jParse from stdin (useful for pipelines):
cat raw_email.eml | mailparser -k -jSee the transformation from raw email to beautifully parsed JSON output.
mail-parser uses a well-structured exception hierarchy for precise error handling:
MailParserError: Base MailParser Exception
|
\── MailParserOutlookError: Raised with Outlook integration errors
|
\── MailParserEnvironmentError: Raised when the environment is not correct
|
\── MailParserOSError: Raised when there is an OS error
|
\── MailParserPathError: Raised when an attachment escapes the output directory
|
\── MailParserReceivedParsingError: Raised when a received header cannot be parsed
|
\── MailParserRecursionError: Raised when a message is nested too deeply to parse
A pre-built Docker image is available for easy deployment and containerized workflows. Find the official image on Docker Hub.
After installing Docker, run the containerized mail-parser:
sudo docker run -it --rm -v ~/mails:/mails fmantuano/spamscope-mail-parserThis command mounts your local ~/mails directory into the container at /mails, allowing mail-parser to access your email files. You can pass any command-line options supported by mail-parser.
For more complex setups, a docker-compose.yml file is included in the repository. Run it with:
sudo docker-compose upThe default configuration includes:
Customize the docker-compose.yml file to adjust mount points, command-line options, or environment variables for your specific use case.
| Back | FazBrowse Home | New Git URL |