pythonemailmailguninline-images

Mailgun sends inline images but no text. [Python+Mailgun-Api]


I'm using the python mailgun-api to send an email with an image, the email and the image arrive to the recipient with no problems, but the text i send in the "text": "Testing some Mailgun awesomness!" it doesn't, it outputs as body text the "html": '<html>HTML version of the body</html>' part.

data={"from": "Excited User <example@mailgun.com>",
      "to": "test@example.com",
      "subject": "Hello",
      "text": "Testing some Mailgun awesomness!",
      "html": '<html>Inline image here: <img src="cid:test.jpg"></html>'})

How I can fix this?, of course if I add in the html line the text I want, it looks OK but I don't know if it is the correct way to do it. Should I use as body text the "html" part and remove the "text" part?

Thank you


Solution

  • First, note that the User's Manual has a bug. The correct code snippet should look like this:

    def send_simple_message():
        return requests.post(
            "https://api.mailgun.net/v2/YOUR-DOMAIN/messages",
            auth=("api", "YOUR-KEY"),
            files={"inline":("image", open("/tmp/image.jpg"))},
            data={"from": "rob@example.com",
                  "to": ["rob@example.com"],
                  "subject": "Hello",
                  "text": "Testing some Mailgun awesomness!",
                  "html": '<html>Inline image here: <img src="cid:image"></html>'})
    

    The files parameter must be a dict, not a list, and the value in the dict must be a tuple that includes the filename. You then use that filename as the cid: value in your HTML.

    As to your question, you need to understand that Mailgun sends the email messages as a MIME "multipart/alternative" message. Quoting from the relevant standard:

    ... each of the body parts is an "alternative" version of the same information.

    Systems should recognize that the content of the various parts are interchangeable. Systems should choose the "best" type based on the local environment and preferences ...

    So you see, your email reader is behaving correctly when it only shows you one of either 'text' or 'html'. To prove to yourself that both forms are being sent, try to view the source of the email message. In Gmail, look for the "Show Original" menu item. In Firefox, try "View | Message Source" or "View | Message Body As ...".

    As a mail sender, you should, if at all possible, include your messages as both 'text' and 'html', with equivalent meaning. Like this:

    text='''Our sale prices are VERY LOW this weekend.
            Visit http://sales.example.com.''',
    html='''<html>
            <img src="cid:logo.jpg"/>
            Our sale prices are <b>very low</b> this weekend.
            Visit <a href="http://sales.example.com">our website!</a>
            </html>'''
    

    Do you see how, no matter which version the user sees, he'll get the same meaning, limited only by the medium in which he views the message?

    In the alternative, if you choose not to send the same message in both 'text' and 'html', you can send it in only one or the other. If you send it in only 'html', then it will be rendered correctly on most modern email readers, but will be gibberish on traditional email readers. If you send it in 'text' only, it will be readable on all email readers, but won't have any rich-text features: bold, italic, inline images, etc.