90 lines
No EOL
3.5 KiB
Python
90 lines
No EOL
3.5 KiB
Python
#!/usr/bin/env python3
|
|
# -*- coding: utf-8 -*-
|
|
# Label a message (add a header) according to certain rules
|
|
# Rules are stored in a file with the format
|
|
# field:match:folder:priority
|
|
|
|
import logging
|
|
from logging.handlers import SysLogHandler
|
|
from logging.handlers import RotatingFileHandler
|
|
import sys
|
|
import pprint
|
|
import re
|
|
import os
|
|
import io
|
|
import email
|
|
from email.message import EmailMessage
|
|
from email.parser import HeaderParser
|
|
from subprocess import Popen, PIPE
|
|
|
|
messagecontent="".join(sys.stdin.readlines())
|
|
log = logging.getLogger()
|
|
log.addHandler(SysLogHandler())
|
|
handler = RotatingFileHandler('/var/spool/filter/labeler.log', maxBytes=1000000, backupCount=5)
|
|
formatter = logging.Formatter('%(asctime)s %(name)-12s %(levelname)-8s %(message)s')
|
|
handler.setFormatter(formatter)
|
|
log.addHandler(handler)
|
|
log.setLevel(logging.DEBUG)
|
|
log.info('Writing {} bytes of message in /var/spool/filter/last_message.eml...'.format(len(messagecontent)))
|
|
if not os.path.exists('/var/spool/filter'):
|
|
log.error('Path /var/spool/filter not found.')
|
|
else:
|
|
with io.open('/var/spool/filter/last_message.eml', 'w') as fp:
|
|
try:
|
|
fp.write(messagecontent)
|
|
except UnicodeEncodeError as e:
|
|
log.error('There was an Unicode encode error writting file. {}'.format(e))
|
|
|
|
parser = HeaderParser()
|
|
log.debug('Obtaining headers from message...')
|
|
msg = email.message_from_string(messagecontent)
|
|
headers = parser.parsestr(messagecontent)
|
|
|
|
log.debug('Headers: {}'.format(", ".join(headers.keys())))
|
|
log.debug('From: {}'.format(headers.get('From','')))
|
|
log.debug('To: {}'.format(headers.get('To','')))
|
|
log.debug('Subject: {}'.format(headers.get('Subject','')))
|
|
if 'Message-ID' not in headers.keys():
|
|
if 'Message-Id' not in headers.keys():
|
|
log.warning('Malformed header (no message-id).')
|
|
else:
|
|
log.debug('Processing message with ID: {}'.format(headers['Message-Id']))
|
|
else:
|
|
log.debug('Processing message with ID: {}'.format(headers['Message-ID']))
|
|
with open('/etc/postfix/filter_rules.conf','r') as fp:
|
|
strrules = fp.read()
|
|
|
|
log.debug('Reading general filter rules...')
|
|
rules = list()
|
|
for rule in strrules.split('\n'):
|
|
if rule != "":
|
|
lrule = rule.split(':')
|
|
field = lrule[0]
|
|
match = lrule[1]
|
|
folder = lrule[2]
|
|
priority = lrule[4]
|
|
rules.append(lrule)
|
|
if field in headers.keys():
|
|
m = re.search(match, headers[field])
|
|
if m is None:
|
|
a = 1
|
|
else:
|
|
msg['X-AD-Label'] = "{}:{}".format(folder, priority)
|
|
log.info('Added label "{}" due to rule "{}"'.format(folder, rule))
|
|
messagecontent=msg.as_string()
|
|
if not os.path.exists('/var/spool/filter'):
|
|
log.error('Path /var/spool/filter not found.')
|
|
else:
|
|
log.info('Writing {} bytes of message in /var/spool/filter/last_message_altered.eml...'.format(len(messagecontent)))
|
|
with open('/var/spool/filter/last_message_altered.eml', 'w', encoding='utf8') as fp:
|
|
fp.write(messagecontent)
|
|
|
|
args = list()
|
|
args = ["/usr/sbin/sendmail"] + sys.argv
|
|
args.pop(1)
|
|
log.debug('Running sendmail with command line: {}'.format(' '.join(args)))
|
|
if not os.path.exists("/usr/sbin/sendmail"):
|
|
log.error('Not found sendmail in "/usr/sbin/sendmail"')
|
|
else:
|
|
p = Popen(args, stdin=PIPE)
|
|
p.communicate(bytearray(messagecontent, 'utf-8')) |