blob: 0dcfbfb4025c851266f3fa7b4524830bad5687e1 [file] [log] [blame]
Benjamin Peterson90f5ba52010-03-11 22:53:45 +00001#!/usr/bin/env python3
Georg Brandl116aa622007-08-15 14:28:22 +00002
3"""Send the contents of a directory as a MIME message."""
4
5import os
Georg Brandl116aa622007-08-15 14:28:22 +00006import smtplib
7# For guessing MIME type based on file name extension
8import mimetypes
9
Serhiy Storchaka992cf1d2013-10-06 11:45:25 +030010from argparse import ArgumentParser
Georg Brandl116aa622007-08-15 14:28:22 +000011
R David Murray29d1bc02016-09-07 21:15:59 -040012from email.message import EmailMessage
13from email.policy import SMTP
Georg Brandl116aa622007-08-15 14:28:22 +000014
15
16def main():
Serhiy Storchaka992cf1d2013-10-06 11:45:25 +030017 parser = ArgumentParser(description="""\
Georg Brandl116aa622007-08-15 14:28:22 +000018Send the contents of a directory as a MIME message.
Georg Brandl116aa622007-08-15 14:28:22 +000019Unless the -o option is given, the email is sent by forwarding to your local
20SMTP server, which then does the normal delivery process. Your local machine
21must be running an SMTP server.
22""")
Serhiy Storchaka992cf1d2013-10-06 11:45:25 +030023 parser.add_argument('-d', '--directory',
24 help="""Mail the contents of the specified directory,
25 otherwise use the current directory. Only the regular
26 files in the directory are sent, and we don't recurse to
27 subdirectories.""")
28 parser.add_argument('-o', '--output',
29 metavar='FILE',
30 help="""Print the composed message to FILE instead of
31 sending the message to the SMTP server.""")
32 parser.add_argument('-s', '--sender', required=True,
33 help='The value of the From: header (required)')
34 parser.add_argument('-r', '--recipient', required=True,
35 action='append', metavar='RECIPIENT',
36 default=[], dest='recipients',
37 help='A To: header value (at least one required)')
38 args = parser.parse_args()
39 directory = args.directory
Georg Brandl116aa622007-08-15 14:28:22 +000040 if not directory:
41 directory = '.'
R David Murray29d1bc02016-09-07 21:15:59 -040042 # Create the message
43 msg = EmailMessage()
44 msg['Subject'] = 'Contents of directory %s' % os.path.abspath(directory)
45 msg['To'] = ', '.join(args.recipients)
46 msg['From'] = args.sender
47 msg.preamble = 'You will not see this in a MIME-aware mail reader.\n'
Georg Brandl116aa622007-08-15 14:28:22 +000048
49 for filename in os.listdir(directory):
50 path = os.path.join(directory, filename)
51 if not os.path.isfile(path):
52 continue
53 # Guess the content type based on the file's extension. Encoding
54 # will be ignored, although we should check for simple things like
55 # gzip'd or compressed files.
56 ctype, encoding = mimetypes.guess_type(path)
57 if ctype is None or encoding is not None:
58 # No guess could be made, or the file is encoded (compressed), so
59 # use a generic bag-of-bits type.
60 ctype = 'application/octet-stream'
61 maintype, subtype = ctype.split('/', 1)
R David Murray29d1bc02016-09-07 21:15:59 -040062 with open(path, 'rb') as fp:
63 msg.add_attachment(fp.read(),
64 maintype=maintype,
65 subtype=subtype,
66 filename=filename)
Georg Brandl116aa622007-08-15 14:28:22 +000067 # Now send or store the message
Serhiy Storchaka992cf1d2013-10-06 11:45:25 +030068 if args.output:
R David Murray29d1bc02016-09-07 21:15:59 -040069 with open(args.output, 'wb') as fp:
70 fp.write(msg.as_bytes(policy=SMTP))
Georg Brandl116aa622007-08-15 14:28:22 +000071 else:
Serhiy Storchaka992cf1d2013-10-06 11:45:25 +030072 with smtplib.SMTP('localhost') as s:
R David Murray29d1bc02016-09-07 21:15:59 -040073 s.send_message(msg)
Georg Brandl116aa622007-08-15 14:28:22 +000074
75
76if __name__ == '__main__':
77 main()