nutools/pyulib/src/uapps/umail.py
Jephte CLAIN 677750f50b maj doc
ne faire un multipart que si c'est nécessaire
2013-11-16 17:31:42 +04:00

134 lines
4.5 KiB
Python
Executable File

#!/usr/bin/env python
# -*- coding: utf-8 mode: python -*- vim:sw=4:sts=4:et:ai:si:sta:fenc=utf-8
u"""%(scriptname)s: Afficher un mail correctement encodé pour son envoi
USAGE
%(scriptname)s [options] <SUBJECT> RECIPIENTS... <<<"BODY" | /usr/sbin/sendmail -i
%(scriptname)s [options] <SUBJECT> RECIPIENTS... <<<"BODY" | /usr/sbin/sendmail RECIPIENTS...
La deuxième forme est pour les implémentations compatible de sendmail qui
ignorent l'argument -i. Il faut alors spécifier tous les destinataires en
argument.
OPTIONS
-f FROM
Spécifier l'adresse de l'expéditeur. Par défaut, utiliser no-reply@univ-reunion.fr
-a FILE
Attacher un fichier au mail. Cette option peut être spécifiée autant de
fois que nécessaire pour attacher plusieurs fichiers.
SUBJECT
Sujet du mail. Cette valeur est requise.
RECIPIENTS
Destinataires du mail. Il faut au moins un destinataire.
BODY
Corps du mail"""
DEFAULT_FROM = 'no-reploy@univ-reunion.fr'
import i_need_py25 # nécessite module email version 4.0
import os, sys, mimetypes
from os import path
from email import encoders
from email.header import Header
from email.mime.base import MIMEBase
from email.mime.text import MIMEText
from email.mime.image import MIMEImage
from email.mime.audio import MIMEAudio
from email.mime.multipart import MIMEMultipart
from email.generator import Generator
from ulib.all import *
def display_help():
uprint(__doc__ % globals())
def run_umail():
options, longoptions = build_options([
('h', 'help', "Afficher l'aide"),
('f:', 'from=', "Spécifier l'expéditeur"),
('a:', 'attach=', "Attacher un fichier"),
])
options, args = get_args(None, options, longoptions)
mfrom = DEFAULT_FROM
subject = None
mtos = []
body = None
afiles = []
for option, value in options:
if option in ('-h', '--help'):
display_help()
sys.exit(0)
elif option in ('-f', '--from'):
mfrom = value
elif option in ('-a', '--attach'):
afiles.append(value)
if not args[0:1]: die("Vous devez spécifier le sujet")
subject = args[0]
if not args[1:]: die("Vous devez spécifier les destinataires")
mtos = args[1:]
lines = BLines()
lines.readlines(sys.stdin)
if not afiles:
# Sans attachement, faire un message simple
msg = MIMEText('\n'.join(lines), 'plain')
msg.set_charset('utf-8')
else:
# Il y a des attachement, faire un multipart
msg = MIMEMultipart()
#msg.set_charset('utf-8')
if lines:
body = MIMEText('\n'.join(lines), 'plain')
body.set_charset('utf-8')
msg.attach(body)
for afile in afiles:
if not path.isfile(afile): die("%s: Fichier introuvable" % afile)
mimetype, encoding = mimetypes.guess_type(afile)
if mimetype is None or encoding is not None:
mimetype = 'application/octet-stream'
maintype, subtype = mimetype.split('/', 1)
if maintype == 'text':
inf = open(afile, 'rb')
try:
#XXX on considère que tous les fichiers texte sont encodés en
# utf-8. Ce n'est pas forcément vrai, mais cette approximation
# devrait être suffisante pour le moment
part = MIMEText(inf.read(), _subtype=subtype, _charset='utf-8')
finally:
inf.close()
elif maintype == 'image':
inf = open(afile, 'rb')
try:
part = MIMEImage(inf.read(), _subtype=subtype)
finally:
inf.close()
elif maintype == 'audio':
inf = open(afile, 'rb')
try:
part = MIMEAudio(inf.read(), _subtype=subtype)
finally:
inf.close()
else:
part = MIMEBase(maintype, subtype)
inf = open(afile, 'rb')
try:
part.set_payload(inf.read())
finally:
inf.close()
encoders.encode_base64(part)
part.add_header('Content-Disposition', 'attachment', filename=path.basename(afile))
msg.attach(part)
msg['From'] = mfrom
msg['To'] = ', '.join(mtos)
msg['Subject'] = Header(subject, 'utf-8')
Generator(sys.stdout).flatten(msg)
if __name__ == '__main__':
run_umail()