Skip to content

Instantly share code, notes, and snippets.

@uchida
Last active December 18, 2015 03:58
Show Gist options
  • Select an option

  • Save uchida/5721892 to your computer and use it in GitHub Desktop.

Select an option

Save uchida/5721892 to your computer and use it in GitHub Desktop.
simple mail search tool for mew-prog-grep
#!/usr/bin/env python
# -*- coding: utf-8 -*-
# by Akihiro Uchida, CC0 dedicated to the public domain
# see http://creativecommons.org/publicdomain/zero/1.0/
import sys, re
import email, email.header
import os.path
import argparse
from locale import getpreferredencoding
DEFAULT_ENCODING = 'cp932'
def contains_in_header(regex, header):
parts = email.header.decode_header(header)
try:
header = u"".join([s.decode(e or DEFAULT_ENCODING) for s, e in parts])
except UnicodeDecodeError:
print >> sys.stderr, 'Error: cannot decode header.'
header = u"".join([s.decode(e or DEFAULT_ENCODING, 'ignore')
for s, e in parts])
if regex.search(header):
return True
return False
def contains_in_body(regex, part):
payload = part.get_payload(decode=True)
try:
encoding = part.get_content_charset(DEFAULT_ENCODING)
body = payload.decode(encoding)
except UnicodeDecodeError:
print >> sys.stderr, 'Error: cannot decode body.'
body = payload.decode(encoding, 'ignore')
for line in body.splitlines():
if regex.search(line):
return True
return False
def contains(regex, msg):
for header in msg.values():
if contains_in_header(regex, header):
return True
if msg.is_multipart():
for part in msg.get_payload():
content_type = part.get_content_type()
if content_type == 'text/plain':
if contains_in_body(regex, part):
return True
elif content_type == 'message/rfc822':
if contains(regex, part):
return True
else:
if contains_in_body(regex, msg):
return True
return False
if __name__ == '__main__':
desc = 'simple mail search tool for mew-prog-grep'
parser = argparse.ArgumentParser(description=desc)
parser.add_argument('-i', '--input-encoding', metavar='encoding',
dest='enc', type=str, default=getpreferredencoding())
parser.add_argument('pattern', metavar='pattern', type=str)
parser.add_argument('files', metavar='file', nargs='*')
args = parser.parse_args()
regex = re.compile(args.pattern.decode(args.enc))
for fn in args.files:
if not os.path.isfile(fn):
print >> sys.stderr, 'Error: {} is not a regular file.'.format(fn)
continue
with open(fn, 'r') as f:
msg = email.message_from_file(f)
if contains(regex, msg):
print fn
(setq mew-prog-grep "mewgrep.py")
(setq mew-prog-grep-opts '())
;(setq mew-prog-grep-opts '("-i" "euc_jp"))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment