6

I was trying to get a python program send an attachment via Gmail. I used the sample code found: Sending email via gmail & python

The problem is when I sent Excel files like .xls, .xlsx, .xlsm to myself, I cannot open the attachments as they were corrupted, even though the original files are fine. But sending .csv works fine. The entire process does not pop up any warnings or error.

Question is: did oauth2.0 or Gmail or MIME mess up the attachment for some formats? And how can I tell the program upload and send attachment without modifying it?

cxwf
  • 329
  • 1
  • 3
  • 12

1 Answers1

9

Had similar issue.

The error is probably in encoding file into bytes.

My gmail still sends corrupted file, when I do want to send xlsx, but I managed to get correct email with xls format.

This is my code:

def create_message_with_excel_attachment(sender, to, subject, message_text, file):

    message = MIMEMultipart()
    message['to'] = to
    message['from'] = sender
    message['subject'] = subject

    msg = MIMEText(message_text)
    message.attach(msg)

    part = MIMEBase('application', "vnd.ms-excel")
    part.set_payload(open(file, "rb").read())
    encoders.encode_base64(part)
    part.add_header('Content-Disposition', 'attachment', filename=file)
    message.attach(part)

    raw = base64.urlsafe_b64encode(message.as_bytes())
    raw = raw.decode()
    return {'raw': raw}


def send_message(service, user_id, message):
    message = (service.users().messages().send(userId=user_id, body=message).execute())
    try:

        print ('Message Id: %s' % message['id'])
        return message
    except:
        print ('An error occurred:')
franiis
  • 1,378
  • 1
  • 18
  • 33
  • 1
    Works also with xlsx files. FYI xls files and xlsx have different underlying format: xls is binary format and xlsx is text (Open XML) format. Cheers – Wojtek Adamczyk Aug 20 '18 at 08:37
  • 1
    encoders.encode_base64(part) fixed it for me. You can import encoders from email. <--- from email import encoders – PdevG Nov 08 '18 at 15:15
  • Yepp, encoders.encode_base64 to the rescue! Nice one! – Dennis Jan 18 '19 at 07:17