Skip to content

Add email related content support (RFC2387). #1329

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 1 commit into
base: master
Choose a base branch
from

Conversation

MarcosLenharo
Copy link

@MarcosLenharo MarcosLenharo commented May 8, 2025

MIME multipart contents can access other email parts when using "multipart/related" Content-Type.
This allows, for example, the HTML body to embed attached image files accepted by email clients and email web clients following RFC 2387.

Additionally it is necessary to add the Content-ID header to the attachment part so the html body can link it.

This commit inserts the Content-ID to each attachment with filename as the tag value, allowing the HTML body to reference it using:

<img src="cid:FILE_NAME.EXT">

Tested with:

  • Outlook
  • Thunderbird - Windows and Linux
  • IOS Native email app
  • GMAIL - Web Interface
  • GMAIL - Android and IOS APP

Description:

Related issue (if applicable): #

Checklist

  • The code change is tested and works locally.
  • There is no commented out code in this PR.
  • No lint errors (use flake8)
  • 100% test coverage

Testing

Anyone can help test this source code as follows:

# Create a virtual environment to work in as follows:
python3 -m venv apprise

# Change into our new directory
cd apprise

# Activate our virtual environment
source bin/activate

# Install the branch
pip install git+https://github.com/caronc/apprise.git@<this.branch-name>

# Test out the changes with the following command:
bin/test.sh email

MIME multipart contents can access other parts when using "multipart/related"
Content-Type.
This allows, for example, the HTML body to embed attached image files accepted
by email clients and email web clients following RFC 2387.
Additionally it is necessary to add the Content-ID header to the attachment
part so the html body can link it.

This commit inserts the Content-ID to each attachment with filename as the tag
value, allowing the HTML body to reference it using:
<img src="cid:FILE_NAME.EXT">

Tested with:
- Outlook
- Thunderbird - Windows and Linux
- IOS Native email app
- GMAIL - Web Interface
- GMAIL - Android and IOS APP
@@ -927,7 +927,7 @@ def prepare_emails(subject, body, from_addr, to,
base = MIMEText(body, 'plain', 'utf-8')

if attach:
mixed = MIMEMultipart("mixed")
mixed = MIMEMultipart("related")
Copy link
Owner

@caronc caronc May 10, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is great to support having the attachments show inline, but this isn't ideal for say a non-graphical attachment. Say a video, pdf, etc to which "mixed" is still a better option.

I think there are 2 levels needed here... one, only switch to inline if an option on the mailto:// is provided ... perhaps a ?inline=yes option. and ONLY if that is set, an additional check needs to be made right here in the code you changed. One that just looks at attach.mimetype... something like:

if attach.mimetype.startswith('image/'):
   mixed = MIMEMultipart("mixed")

Here is an example of where this kind of check exists elsewhere.

Forcing everything to be inline though (per RFC2387) is not ideal. Thoughts?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree with your suggestion of creating a new switch.

One thing that I'm not sure is whether the new switch should follow item 4 of RFC2387 and change the Content-Disposition tag from "attachment" to "inline" to help non-RFC2387 compliant clients to handle it.

Regarding your suggestion on checking the attach.mimetype: The "mixed" type is at the top of email body, not on the attachment level, so it would be necessary to list all attachments and check if at least one of them is a "image/" and then change the multipart type.

What do you think about these two points?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants