def get_mail(email, password, limit=1): pop3_server = '' st = email.split('@')[1] if st and (st in pops): pop3_server = pops[st] msgAll = [] # 输入邮件地址, 口令和POP3服务器地址: email = email # input('Email: ') password = password # input('Password: '******'POP3 server: ') # pop.126.com pop.163.com try: # 连接到POP3服务器: server = poplib.POP3(pop3_server) # 可以打开或关闭调试信息: server.set_debuglevel(1) # 可选:打印POP3服务器的欢迎文字: # print(server.getwelcome().decode('utf-8')) # 身份认证: server.user(email) server.pass_(password) except: return msgAll # stat()返回邮件数量和占用空间: print('Messages: %s. Size: %s' % server.stat()) # list()返回所有邮件的编号: resp, mails, octets = server.list() # 可以查看返回的列表类似[b'1 82923', b'2 2184', ...] # print(mails) # 获取最新一封邮件, 注意索引号从1开始: index = len(mails) # 总数 page = (index - limit) if (index - limit) > 0 else 0 for x in range(index, page, -1): #循环获取所有邮件 try: resp, lines, octets = server.retr(x) # lines存储了邮件的原始文本的每一行, # 可以获得整个邮件的原始文本: msg_content = b'\r\n'.join(lines).decode('utf-8') # 稍后解析出邮件: msg = Parser().parsestr(msg_content) msgAll.append(print_info(msg)) except: pass # 可以根据邮件索引号直接从服务器删除邮件: # server.dele(index) # 关闭连接: server.quit() # except: # pass return msgAll
# stat()方法返回一个元组,为邮件数量和占用空间 msgs,counts = srv.stat() print('message:{0},size:{1}'.format(msgs,counts)) # 返回所有邮件的编号列表 rsp1,mails1,cotect1 = srv.list() print(mails1) # 获取信件 rsp,lines,octets = srv.retr(len(mails1)) # 获得邮件的整个原始文本 msg_count = b'\r\n'.join(lines).decode('utf-8') # 解析模块 from email.parser import Parser # 邮件解码模块 from email.header import decode_header # header文件解码模块 from email.utils import parseaddr msg = Parser().parsestr(msg_count) # 解码邮件整体 # str解码 def decondeStr(s): value,charset = decode_header(s)[0] if charset: value = value.decode(charset) return value # 判断编码 def guessCharset(msg): charset = msg.get_charset() if charset is None: content_tpye = msg.get('Content-Type','').lower() # 找到内容,转换为小写 pos = content_tpye.find('charset')
def main(argv): parser = argparse.ArgumentParser(description='Mail using XOAUTH2') parser.add_argument('toaddrs', metavar='address', type=str, nargs='*', help='Mail address to be sent to') parser.add_argument('-f', dest='fromaddr', type=str, help='Mail address to be sent from') parser.add_argument( '--readfrommsg', action='store_true', help='Read the mail to determine the sender and recievers') parser.add_argument('--debug', action='store_true', help='Debug mode') args = parser.parse_args() if args.debug: print(argv) # TODO: set defaults config = ConfigParser() config.read(expanduser(CONFIG_PATH)) request_url = config.get('oauth2', 'request_url') client_id = config.get('oauth2', 'client_id') client_secret = config.get('oauth2', 'client_secret') accounts = build_accounts(config) fromaddr = None toaddrs = list() body = sys.stdin.read() email_parser = Parser() msg = email_parser.parsestr(body) tos = list() ccs = list() bccs = list() if args.readfrommsg: fromaddr = parseaddr(msg['from'])[1] # email! tos = getaddresses(msg.get_all('to', [])) ccs = getaddresses(msg.get_all('cc', [])) bccs = getaddresses(msg.get_all('bcc', [])) resent_tos = getaddresses(msg.get_all('resent-to', [])) resent_ccs = getaddresses(msg.get_all('resent-cc', [])) resent_bccs = getaddresses(msg.get_all('resent-bcc', [])) tos = [x[1] for x in tos + resent_tos] ccs = [x[1] for x in ccs + resent_ccs] bccs = [x[1] for x in bccs + resent_bccs] else: fromaddr = args.fromaddr tos = args.toaddrs msg.replace_header('from', fromaddr) msg.replace_header('to', ', '.join(tos)) if msg.get_all('bcc', False): msg.replace_header('bcc', None) # wipe out from message if fromaddr in accounts: acct = accounts[fromaddr] oauth = Oauth(request_url, client_id, client_secret, acct.username, acct.refresh_token) if args.debug: print("Sending from:", fromaddr) print("Sending to:", toaddrs) sender(fromaddr, tos + ccs + bccs, msg, oauth, acct, args.debug) else: raise KeyError('Configuration file has no section for: ', fromaddr)
def install(self, version): # Most of the work will be delegated to pip with temporary_directory(prefix="poetry-installer-") as dir: dist = os.path.join(dir, "dist") print(" - Getting dependencies") try: self.call( self.CURRENT_PYTHON, "-m", "pip", "install", "poetry=={}".format(version), "--target", dist, ) except subprocess.CalledProcessError as e: if "must supply either home or prefix/exec-prefix" in e.output.decode( ): # Homebrew Python and possible other installations # We workaround this issue by temporarily changing # the --user directory original_user = os.getenv("PYTHONUSERBASE") os.environ["PYTHONUSERBASE"] = dir self.call( self.CURRENT_PYTHON, "-m", "pip", "install", "poetry=={}".format(version), "--user", "--ignore-installed", ) if original_user is not None: os.environ["PYTHONUSERBASE"] = original_user else: del os.environ["PYTHONUSERBASE"] # Finding site-package directory lib = os.path.join(dir, "lib") lib_python = list(glob(os.path.join(lib, "python*")))[0] site_packages = os.path.join(lib_python, "site-packages") shutil.copytree(site_packages, dist) else: raise print(" - Vendorizing dependencies") poetry_dir = os.path.join(dist, "poetry") vendor_dir = os.path.join(poetry_dir, "_vendor") # Everything, except poetry itself, should # be put in the _vendor directory for file in glob(os.path.join(dist, "*")): if (os.path.basename(file).startswith("poetry") or os.path.basename(file) == "__pycache__"): continue dest = os.path.join(vendor_dir, os.path.basename(file)) if os.path.isdir(file): shutil.copytree(file, dest) shutil.rmtree(file) else: shutil.copy(file, dest) os.unlink(file) wheel_data = os.path.join(dist, "poetry-{}.dist-info".format(version), "WHEEL") with open(wheel_data) as f: wheel_data = Parser().parsestr(f.read()) tag = wheel_data["Tag"] # Repack everything and install print(" - Installing {}".format(colorize("info", "poetry"))) shutil.make_archive( os.path.join(dir, "poetry-{}-{}".format(version, tag)), format="zip", root_dir=str(dist), ) os.rename( os.path.join(dir, "poetry-{}-{}.zip".format(version, tag)), os.path.join(dir, "poetry-{}-{}.whl".format(version, tag)), ) self.call( self.CURRENT_PYTHON, "-m", "pip", "install", "--upgrade", "--no-deps", os.path.join(dir, "poetry-{}-{}.whl".format(version, tag)), ) print("") print("{} ({}) successfully installed!".format( colorize("info", "poetry"), colorize("comment", version)))
def _parse_and_decode(self, text): parsed_body = Parser().parsestr(text) decoded_body = self._unwrap_content_transfer_encoding(parsed_body) return decoded_body
def get_response(cmd, conn): """Return a response""" resp = conn.socket().makefile('rb', -1) resp_dict = dict( code=0, message='', isspam=False, score=0.0, basescore=0.0, report=[], symbols=[], headers={}, ) if cmd == 'TELL': resp_dict['didset'] = False resp_dict['didremove'] = False data = resp.read() lines = data.split('\r\n') for index, line in enumerate(lines): if index == 0: match = RESPONSE_RE.match(line) if not match: raise SpamCResponseError('spamd unrecognized response: %s' % data) resp_dict.update(match.groupdict()) resp_dict['code'] = int(resp_dict['code']) else: if not line.strip(): continue match = SPAM_RE.match(line) if match: tmp = match.groupdict() resp_dict['score'] = float(tmp['score']) resp_dict['basescore'] = float(tmp['basescore']) resp_dict['isspam'] = tmp['isspam'] in ['True', 'Yes'] if not match: if cmd == 'SYMBOLS': match = PART_RE.findall(line) for part in match: resp_dict['symbols'].append(part) if not match and cmd != 'PROCESS': match = RULE_RE.findall(line) if match: resp_dict['report'] = [] for part in match: score = part[0] + part[1] score = score.strip() resp_dict['report'].append( dict(score=score, name=part[2], description=SPACE_RE.sub(" ", part[3]))) if line.startswith('DidSet:'): resp_dict['didset'] = True if line.startswith('DidRemove:'): resp_dict['didremove'] = True if cmd == 'PROCESS': resp_dict['message'] = ''.join(lines[4:]) + '\r\n' if cmd == 'HEADERS': parser = Parser() headers = parser.parsestr('\r\n'.join(lines[4:]), headersonly=True) for key in headers.keys(): resp_dict['headers'][key] = headers[key] return resp_dict
def StringToHeaders(s): return Parser().parsestr(s)
output_file = "output.csv" core_data_path = "trec06p/data/" # Different combinations to be tried for smoothing parameter alpha_iterations = 2 # Identified additional features for SPAM detection features = [ "MUST READ - ALERT", "Huge Promo", "REAL company with real products", "BEFORE WE CONTINUE - VERY IMPORTANT", "Impress your girl", "Party Zone", "Best s0ftware prices", "Best software prices", "@solocom.com", "@sunero.com", "@about.com", "@accesspro.net", "@eximeno.com", "only $", "Limited stock", "all sold out", "@szu.anet.cz", "@dreamwiz.com", "@fotofutura.com", "special price", "half the price", "half price", "@emb_tunis.intl.tn", "Unbelievable Price", "@wurldlink.net", "@msa.hinet.net" ] email_parser = Parser() # Read the given file line by line and return the content as a list def read_file(file_name): output = [] with open(file_name) as file_obj: for line in file_obj: # add each line to the list output.append(line.split(" ")) return output # Learn the feature distribution - train the model def train_model(train_data, feature_flag=False): global total_doc
import glob import sys from email.parser import Parser import smtplib if __name__ == '__main__': port = int(sys.argv[1]) if len(sys.argv) > 1 else 2025 smtp = smtplib.SMTP("localhost", port) for file in glob.glob('spam/*.txt'): msg = Parser().parse(open(file, 'rb')) smtp.sendmail('*****@*****.**', ['*****@*****.**'], msg.as_string())
def parse(self, filename): parser = Parser() with open(filename, 'rt') as eml: message = parser.parse(eml) self._parse_email(message)
def prepare_message(email, recipient, recipients_list): message = email.message if not message: return "" # Parse "Email Account" from "Email Sender" email_account = get_outgoing_email_account(raise_exception_not_set=False, sender=email.sender) if frappe.conf.use_ssl and email_account.track_email_status: # Using SSL => Publically available domain => Email Read Reciept Possible message = message.replace( "<!--email open check-->", quopri.encodestring( '<img src="https://{}/api/method/frappe.core.doctype.communication.email.mark_email_as_seen?name={}"/>' .format(frappe.local.site, email.communication).encode()).decode()) else: # No SSL => No Email Read Reciept message = message.replace("<!--email open check-->", quopri.encodestring("".encode()).decode()) if email.add_unsubscribe_link and email.reference_doctype: # is missing the check for unsubscribe message but will not add as there will be no unsubscribe url unsubscribe_url = get_unsubcribed_url(email.reference_doctype, email.reference_name, recipient, email.unsubscribe_method, email.unsubscribe_params) message = message.replace( "<!--unsubscribe url-->", quopri.encodestring(unsubscribe_url.encode()).decode()) if email.expose_recipients == "header": pass else: if email.expose_recipients == "footer": if isinstance(email.show_as_cc, string_types): email.show_as_cc = email.show_as_cc.split(",") email_sent_to = [r.recipient for r in recipients_list] email_sent_cc = ", ".join( [e for e in email_sent_to if e in email.show_as_cc]) email_sent_to = ", ".join( [e for e in email_sent_to if e not in email.show_as_cc]) if email_sent_cc: email_sent_message = _( "This email was sent to {0} and copied to {1}").format( email_sent_to, email_sent_cc) else: email_sent_message = _("This email was sent to {0}").format( email_sent_to) message = message.replace( "<!--cc message-->", quopri.encodestring(email_sent_message.encode()).decode()) message = message.replace("<!--recipient-->", recipient) message = (message and message.encode('utf8')) or '' message = safe_decode(message) if not email.attachments: return message # On-demand attachments from email.parser import Parser msg_obj = Parser().parsestr(message) attachments = json.loads(email.attachments) for attachment in attachments: if attachment.get('fcontent'): continue fid = attachment.get("fid") if fid: fname, fcontent = get_file(fid) attachment.update({ 'fname': fname, 'fcontent': fcontent, 'parent': msg_obj }) attachment.pop("fid", None) add_attachment(**attachment) elif attachment.get("print_format_attachment") == 1: attachment.pop("print_format_attachment", None) print_format_file = frappe.attach_print(**attachment) print_format_file.update({"parent": msg_obj}) add_attachment(**print_format_file) return msg_obj.as_string()
def __init__(self): self._parser = Parser()
#!/usr/bin/python import sys import subprocess from email.parser import Parser import requests URLS = [ 'https://www.mail-archive.com/search?l=mid&q={}', 'http://marc.info/?i={}', 'http://mid.gmane.org/{}' ] if __name__ == "__main__": headers = Parser().parse(sys.stdin) if 'message-id' in headers: for base_url in URLS: message_id = headers['message-id'].replace('<', '').replace('>', '') url = base_url.format(message_id) r = requests.get(url) if r.status_code == 200 and b'NOT FOUND' not in r.content: subprocess.call(['qutebrowser', url], stdout=subprocess.DEVNULL) break
def parse_cli(cli_opts_args): """ main application """ if len(cli_opts_args) == 0: usage() opts_args = cli_opts_args[1:] try: opts = getopt.getopt(opts_args, "c:d:ehlo:p:s:")[0] except getopt.GetoptError: AIGM_LOG.post(AILog.AI_DBGLVL_ERR, "Invalid options or arguments provided") usage() criteria_list = list() service_list = None manifest_file = None profile_dir = None list_criteria_only = False no_default = False for option, argument in opts: if option == "-c": criteria_list.append(argument) elif option == "-s": service_list = argument elif option == "-o": manifest_file = argument elif option == "-d": AIGM_LOG.set_debug_level(int(argument)) elif option == "-l": list_criteria_only = True elif option == "-p": profile_dir = argument elif option == "-e": no_default = True elif option == "-h": usage() if service_list is None or manifest_file is None or profile_dir is None: AIGM_LOG.post(AILog.AI_DBGLVL_ERR, "Invalid options or arguments provided") usage() AIGM_LOG.post(AILog.AI_DBGLVL_INFO, "Service list: %s", service_list) AIGM_LOG.post(AILog.AI_DBGLVL_INFO, "Manifest file: " + manifest_file) AIGM_LOG.post(AILog.AI_DBGLVL_INFO, "Profile directory: " + profile_dir) if len(criteria_list) > 0: AIGM_LOG.post(AILog.AI_DBGLVL_INFO, "Criteria list: " + str(criteria_list)) ai_criteria_known = {} # If criteria specified on the command line, use that as # our known criteria, otherwise get criteria from system. if len(criteria_list) > 0: for entry in criteria_list: entries = entry.partition("=") if entries[1]: if not entries[0]: raise ValueError( _("Missing criteria name in '%s'\n") % entry) elif entries[0].lower() in ai_criteria_known: raise ValueError( _("Duplicate criteria: '%s'\n") % entries[0]) elif not entries[2]: raise ValueError( _("Missing value for criteria '%s'\n") % entries[0]) if entries[0] not in AI_CRITERIA_SUPPORTED: raise ValueError( _("Unsupported criteria: '%s'\n") % entries[0]) ai_criteria_known[entries[0].lower()] = entries[2] else: raise ValueError( _("Criteria must be of the form " "<criteria>=<value>\n")) else: # Obtain all available information about client for key in AI_CRITERIA_SUPPORTED.keys(): if AI_CRITERIA_SUPPORTED[key][0] is not None: ai_crit = AI_CRITERIA_SUPPORTED[key][0]() if ai_crit.is_known(): ai_criteria_known[key] = ai_crit.get() # List all criteria which client can understand and provide AIGM_LOG.post(AILog.AI_DBGLVL_INFO, "Client can supply following criteria") for key in ai_criteria_known.keys(): AIGM_LOG.post(AILog.AI_DBGLVL_INFO, " %s=%s, '%s'", key, ai_criteria_known[key], AI_CRITERIA_SUPPORTED[key][1]) # if "-l" option was provided, list known criteria and exit if list_criteria_only: print "Client can supply the following criteria" print "----------------------------------------" index = 0 for key in ai_criteria_known.keys(): index += 1 print " [%d] %s=%s (%s)" % (index, key, ai_criteria_known[key], AI_CRITERIA_SUPPORTED[key][1]) return 0 # # Go through the list of services. # Contact each of them and try to obtain valid manifest. # AIGM_LOG.post(AILog.AI_DBGLVL_INFO, "Starting to contact AI services provided by %s", service_list) ai_manifest_obtained = False try: service_list_fh = open(service_list, 'r') except IOError: AIGM_LOG.post(AILog.AI_DBGLVL_ERR, "Could not open %s file", service_list) return 2 for ai_service in service_list_fh.readlines(): service = ai_service.strip() (ai_service, ai_port, ai_name) = service.split(':') ai_service += ':' + str(ai_port) AIGM_LOG.post(AILog.AI_DBGLVL_INFO, "AI service: %s", ai_service) AIGM_LOG.post(AILog.AI_DBGLVL_INFO, "AI service name: %s", ai_name) AIGM_LOG.post(AILog.AI_DBGLVL_INFO, " HTTP POST cgi-bin/cgi_get_manifest.py?service=%s", ai_service) # invoke CGI script to get manifest, profiles http_resp, ret, content_type = \ ai_get_http_file(ai_service, ai_name, "/cgi-bin/cgi_get_manifest.py", 'POST', ai_criteria_known, no_default=no_default) # # If valid manifest was provided, it is not necessary # to connect next AI service, # if ret == httplib.OK: if content_type == 'text/xml': # old format ai_manifest = http_resp ai_manifest_obtained = True AIGM_LOG.post( AILog.AI_DBGLVL_INFO, "%s AI service provided single XML file - " "assumed to be AI manifest." % ai_service) break AIGM_LOG.post(AILog.AI_DBGLVL_INFO, "%s AI service provided valid manifest", ai_service) # prepend content type header for MIME boundary # Content-Type: multipart/mixed; boundary= ... mime_response = "Content-Type: %s\n%s" % (content_type, http_resp) # by design, response is MIME-encoded, multipart if mime_response is not None: # delete any profiles from previous runs cleanup_earlier_run(profile_dir) # parse the MIME response parse = Parser() msg = parse.parsestr(mime_response) # handle each self-identifying part for imsg in msg.walk(): # write out manifest, any profiles, console messages if handle_mime_payload(imsg, manifest_file, profile_dir): ai_manifest_obtained = True if ai_manifest_obtained: # manifest written by MIME handler service_list_fh.close() return 0 else: AIGM_LOG.post(AILog.AI_DBGLVL_WARN, "%s AI service did not provide a valid manifest, " \ "ret=%d", ai_service, ret) AIGM_LOG.post(AILog.AI_DBGLVL_WARN, "Checking compatibility mechanism.") ai_manifest, ret = ai_do_compatibility(ai_service, ai_criteria_known) if ret == httplib.OK: AIGM_LOG.post(AILog.AI_DBGLVL_WARN, "Compatibility mechanism provided a valid " \ "manifest.") ai_manifest_obtained = True break else: AIGM_LOG.post(AILog.AI_DBGLVL_WARN, "Compatibility mechanism did not provide valid" \ " manifest, ret=%d", ret) service_list_fh.close() if not ai_manifest_obtained: AIGM_LOG.post(AILog.AI_DBGLVL_ERR, "None of contacted AI services provided valid manifest") if no_default: # If a default manifest is not requested, its OK if we didn't # obtain a manifest, return 0. return 0 else: return 2 # Save the manifest AIGM_LOG.post(AILog.AI_DBGLVL_INFO, "Saving manifest to %s", manifest_file) try: with open(manifest_file, 'w') as fh_manifest: fh_manifest.write(ai_manifest) except IOError: AIGM_LOG.post(AILog.AI_DBGLVL_ERR, "Could not open %s for saving obtained manifest", manifest_file) return 2 return 0
sys.exit(0) # Exit gracefully emails = [] for direct, sub_direct, filenames in os.walk(rootdir): for s in sub_direct: # only look at SENT emails from the Enron directory (to reduce quantity of emails) if s == 'sent': path = direct + "/" + s for file in os.listdir(path): os.chdir(path) f = open(file, "r") try: f = f.read() email = Parser().parsestr(f) # Look for this string indicating the email is a reply if "-----Original Message-----" in str(email): emails.append(email) except UnicodeDecodeError: continue print( "Number of emails containting '-----Original Message-----' indicating a reply: ", len(emails)) # Get the email body content from enron emails def get_content(full_email): content = []
def gen_item(mail): with open(mail.get_filename(), 'r') as fp: mailfile = Parser().parse(fp) fp.close() url = find_url_in_mail(mailfile) counter = 1 types = [part.get_content_type() for part in mailfile.walk()] for part in mailfile.walk(): # multipart/* are just containers if part.get_content_maintype() == 'multipart': continue if part.get_content_type() == 'text/plain' and 'text/html' in types: print "Warning: skipping text/plain part, since text/html part was found for mail %s." % mail.get_filename( ) continue filename = part.get_filename() if not filename: if part.get_content_type() == 'text/plain': ext = '.txt' else: ext = mimetypes.guess_extension(part.get_content_type()) if not ext: # Use a generic bag-of-bits extension ext = '.bin' filename = '%s-part-%03d%s' % (mail.get_header("Subject"), counter, ext) if os.path.splitext(filename)[1] == '': # didn't get a proper file name. Try decoding it. #filename = email.utils.decode_rfc2231(filename) # doesn't work. Don't know why. print >> sys.stderr, "Error: ignoring part with invalid file name \"%s\"." % filename filename = sanitize_filename(filename) counter += 1 with open(os.path.join(tempfolder, filename), 'wb') as fp: payload = part.get_payload(decode=True) if not payload == None: fp.write(part.get_payload(decode=True)) fp.close() else: print >> sys.stderr, "Error: Unable to extract payload from filename %s, part dump following:" % filename print >> sys.stderr, part print >> sys.stderr, "End of part dump for file named %s." % filename basename, ext = os.path.splitext(filename) if ext == '.doc': # process with abiword! try: p = subprocess.Popen([ 'abiword', '--to=%s.html' % os.path.join(tempfolder, basename), os.path.join(tempfolder, filename) ], stdout=subprocess.PIPE, stderr=subprocess.PIPE) stdout, stderr = p.communicate() except OSError, e: print >> sys.stderr, "Failed to convert to html using abiword. Possibly missing abiword? Got error: ", e calibre_to_mobi(tempfolder, basename + '.html') if part.get_content_type() in types_to_convert: # html files needs conversion. calibre_to_mobi(tempfolder, filename, mail.get_header("From"), mail.get_date(), mail.get_header("Subject"), url)
from mail import * import email from email.parser import Parser parser = Parser() acctID = '' def mailTest(): mail.list() #Gets all emails mail.select("inbox") # Gets inbox (instead of like "sent") result, data = mail.search(None, "ALL") #Gets "all" emails, I think maybe ids = data[0] # data is a list. id_list = ids.split() # ids is a space separated string latest_email_id = id_list[-1] # get the latest result, data = mail.fetch(latest_email_id, "(RFC822)") # fetch the email body (RFC822) for the given ID raw_email = data[0][1] #print raw_email with open('data.txt', 'w') as outfile: json.dump(raw_email, outfile)
def test_repoze_sendmail_send_to_queue_functional(self): # functest that emulates the interaction between pyramid_mailer and # repoze.maildir.add and queuedelivery.send. import tempfile from email.generator import Generator from email.parser import Parser from pyramid_mailer.message import Message from pyramid_mailer.message import Attachment from repoze.sendmail.encoding import cleanup_message from repoze.sendmail.delivery import copy_message def checkit(msg): self.assertEqual( msg['Content-Type'], 'text/plain; charset="iso-8859-1"' ) self.assertEqual( msg['Content-Transfer-Encoding'], transfer_encoding) payload = msg.get_payload() self.assertEqual(payload, expected) charset = 'iso-8859-1' text_encoded = b'LaPe\xf1a' text = text_encoded.decode(charset) expected = _qencode(text_encoded).decode('ascii') transfer_encoding = 'quoted-printable' body = Attachment( data=text, transfer_encoding=transfer_encoding ) msg = Message( subject="testing", sender="*****@*****.**", recipients=["*****@*****.**"], body=body ) # done in pyramid_mailer via mailer/send_to_queue msg = msg.to_message() msg.as_string() checkit(msg) # done in repoze.sendmail via delivery/AbstractMailDelivery/send cleanup_message(msg) checkit(msg) # done in repoze.sendmail via # delivery/AbstractMailDelivery/createDataManager msg_copy = copy_message(msg) checkit(msg_copy) try: # emulate what repoze.sendmail maildir.py/add does fn = tempfile.mktemp() fd = os.open(fn, os.O_CREAT|os.O_EXCL|os.O_WRONLY, 0o600 ) with os.fdopen(fd, 'w') as f: writer = Generator(f) writer.flatten(msg_copy) # emulate what repoze.sendmail.queue _parseMessage does with open(fn) as foo: parser = Parser() reconstituted = parser.parse(foo) checkit(reconstituted) finally: # pragma: no cover try: os.remove(fn) except: pass
def parse_message(message_body): parser = Parser(policy=email.policy.default) return parser.parsestr(message_body)
# Import the email modules we'll need #from email.parser import BytesParser from email.parser import Parser from email.policy import default # If the e-mail headers are in a file, uncomment these two lines: # with open(messagefile, 'rb') as fp: # headers = BytesParser(policy=default).parse(fp) # Or for parsing headers in a string (this is an uncommon operation), use: headers = Parser(policy=default).parsestr( 'From: Foo Bar <*****@*****.**>\n' 'To: <*****@*****.**>\n' 'Subject: Test message\n' '\n' 'Body would go here\n') # Now the header items can be accessed as a dictionary: print('To: {}'.format(headers['to'])) print('From: {}'.format(headers['from'])) print('Subject: {}'.format(headers['subject'])) # You can also access the parts of the addresses: print('Recipient username: {}'.format(headers['to'].addresses[0].username)) print('Sender name: {}'.format(headers['from'].addresses[0].display_name))
def prepare_message(email, recipient, recipients_list): message = email.message if not message: return "" if email.add_unsubscribe_link and email.reference_doctype: # is missing the check for unsubscribe message but will not add as there will be no unsubscribe url unsubscribe_url = get_unsubcribed_url(email.reference_doctype, email.reference_name, recipient, email.unsubscribe_method, email.unsubscribe_params) message = message.replace("<!--unsubscribe url-->", quopri.encodestring(unsubscribe_url)) if email.expose_recipients == "header": pass else: if email.expose_recipients == "footer": if isinstance(email.show_as_cc, basestring): email.show_as_cc = email.show_as_cc.split(",") email_sent_to = [r.recipient for r in recipients_list] email_sent_cc = ", ".join( [e for e in email_sent_to if e in email.show_as_cc]) email_sent_to = ", ".join( [e for e in email_sent_to if e not in email.show_as_cc]) if email_sent_cc: email_sent_message = _( "This email was sent to {0} and copied to {1}").format( email_sent_to, email_sent_cc) else: email_sent_message = _("This email was sent to {0}").format( email_sent_to) message = message.replace("<!--cc message-->", quopri.encodestring(email_sent_message)) message = message.replace("<!--recipient-->", recipient) message = (message and message.encode('utf8')) or '' if not email.attachments: return message # On-demand attachments from email.parser import Parser msg_obj = Parser().parsestr(message) attachments = json.loads(email.attachments) for attachment in attachments: if attachment.get('fcontent'): continue fid = attachment.get('fid') if not fid: continue fname, fcontent = get_file(fid) attachment.update({ 'fname': fname, 'fcontent': fcontent, 'parent': msg_obj }) attachment.pop("fid", None) add_attachment(**attachment) return msg_obj.as_string()
def get_msg(start='19900101', end='20181013'): ''' 搜索起始日期到终止日期内的邮件,返回其msg对象数组 :param start: 搜索的起始日期 :param end: 搜索的终止日期 :return: 返回Msg对象列表 ''' # 输入邮件地址, 口令和POP3服务器地址: # email = input('Email_username: '******'Password: '******'POP3 server: ') email, password, pop3_server, msg_inf = '', '', '', '' msg_list = [] # 邮箱账户读取位置 with open(r'C:\Users\123456\Documents\MttQ\1.txt', 'rt', encoding='utf-8') as file: msg_inf = file.read().split('\n') file.close() if email == '': email = msg_inf[0] if pop3_server == '': pop3_server = 'pop.qq.com' print(email, password, pop3_server) # 连接到POP3服务器: server = poplib.POP3_SSL(pop3_server, 995) # 可以打开或关闭调试信息: # server.set_debuglevel(1) # 可选:打印POP3服务器的欢迎文字: print(server.getwelcome()) # 身份认证: server.set_debuglevel(1) server.user(email) server.pass_(msg_inf[1]) # 口令,QQ邮箱是输入授权码,在qq邮箱设置 里用验证过的手机发送短信获得,不含空格 # stat()返回邮件数量和占用空间: print('Messages: %s. Size: %s' % server.stat()) # list()返回所有邮件的编号: resp, mails, octets = server.list() # 可以查看返回的列表类似['1 82923', '2 2184', ...] print(mails) # 获取最新一封邮件, 注意索引号从1开始: index = len(mails) for mail_item in range(index, 0, -1): resp, lines, octets = server.retr(mail_item) # # lines存储了邮件的原始文本的每一行, # # 可以获得整个邮件的原始文本: msg_content = b'\r\n'.join(lines).decode('gb18030', errors='ignore') # # 稍后解析出邮件: msg = Parser().parsestr(msg_content) # 获取邮件时间 tmp = msg.get("Date") tmp = tmp.split(" ") date1 = "" if len(tmp) == 5: if "" in tmp: tmp.remove("") tmp = " ".join(tmp[:4]) date1 = time.strptime(tmp, "%a, %d %b %Y") break tmp = " ".join(tmp[:4]) date1 = time.strptime(tmp, "%d %b %Y %H:%M:%S") elif len(tmp) == 8: if "" in tmp: tmp.remove("") tmp = " ".join(tmp[:5]) date1 = time.strptime(tmp, '%a, %d %b %Y %H:%M:%S') else: tmp = " ".join(tmp[:5]) date1 = time.strptime(tmp, '%a, %d %b %Y %H:%M:%S') if date1 == "": print(tmp) # date1 = time.strptime(msg.get("Date")[0:24],'%a, %d %b %Y %H:%M:%S') #格式化收件时间 date2 = time.strftime("%Y%m%d", date1) # 邮件时间格式转换 # ------------------可能有问题-------------------------- if (date2 < start): break # -------------------------------------------------------- if (date2 > end or date2 < start): continue msg_list.append(msg) return msg_list
def update(self, release): from poetry.utils._compat import Path from poetry.utils.helpers import temporary_directory version = release.version self.line('Updating to <info>{}</info>'.format(version)) prefix = sys.prefix base_prefix = getattr(sys, 'base_prefix', None) real_prefix = getattr(sys, 'real_prefix', None) prefix_poetry = Path(prefix) / 'bin' / 'poetry' if prefix_poetry.exists(): pip = (prefix_poetry.parent / 'pip').resolve() elif (base_prefix and base_prefix != prefix and (Path(base_prefix) / 'bin' / 'poetry').exists()): pip = Path(base_prefix) / 'bin' / 'pip' elif real_prefix: pip = Path(real_prefix) / 'bin' / 'pip' else: pip = Path(prefix) / 'bin' / 'pip' if not pip.exists(): raise RuntimeError('Unable to determine poetry\'s path') with temporary_directory(prefix='poetry-update-') as temp_dir: temp_dir = Path(temp_dir) dist = temp_dir / 'dist' self.line(' - Getting dependencies') self.process(str(pip), 'install', '-U', 'poetry=={}'.format(release.version), '--target', str(dist)) self.line(' - Vendorizing dependencies') poetry_dir = dist / 'poetry' vendor_dir = poetry_dir / '_vendor' # Everything, except poetry itself, should # be put in the _vendor directory for file in dist.glob('*'): if file.name.startswith('poetry'): continue dest = vendor_dir / file.name if file.is_dir(): shutil.copytree(str(file), str(dest)) shutil.rmtree(str(file)) else: shutil.copy(str(file), str(dest)) os.unlink(str(file)) wheel_data = dist / 'poetry-{}.dist-info'.format(version) / 'WHEEL' with wheel_data.open() as f: wheel_data = Parser().parsestr(f.read()) tag = wheel_data['Tag'] # Repack everything and install self.line(' - Updating <info>poetry</info>') shutil.make_archive(str(temp_dir / 'poetry-{}-{}'.format(version, tag)), format='zip', root_dir=str(dist)) os.rename( str(temp_dir / 'poetry-{}-{}.zip'.format(version, tag)), str(temp_dir / 'poetry-{}-{}.whl'.format(version, tag)), ) self.process( str(pip), 'install', '--upgrade', '--no-deps', str(temp_dir / 'poetry-{}-{}.whl'.format(version, tag))) self.line('') self.line('<info>poetry</> (<comment>{}</>) ' 'successfully installed!'.format(version))
def get_baoxiao_info(str="19900101", end="20181013", filepath="."): # 需要获取的滴滴邮件附件的时间段 """ 获取滴滴和地铁截图的附件,筛选条件为标题为滴滴出行或者地铁 :param str: 起始日期 :param end: 结束日期 :param FilePath: 附件保持路径 :return: 如果有,在路径内保存附件或者铁路文本信息,并且返回true,如果无则返回false """ # 输入邮件地址, 口令和POP3服务器地址: # email = input('Email_username: '******'Password: '******'POP3 server: ') email, password, pop3_server, msg_inf = '', '', '', '' rst = False #邮箱账户读取位置 with open(r'C:\Users\123456\Documents\MttQ\1.txt', 'rt', encoding='utf-8') as file: msg_inf = file.read().split('\n') file.close() if email == '': email = msg_inf[0] if pop3_server == '': pop3_server = 'pop.qq.com' print(email, password, pop3_server) # 连接到POP3服务器: server = poplib.POP3_SSL(pop3_server, 995) # 可以打开或关闭调试信息: # server.set_debuglevel(1) # 可选:打印POP3服务器的欢迎文字: print(server.getwelcome()) # 身份认证: server.set_debuglevel(1) server.user(email) server.pass_(msg_inf[1]) # 口令,QQ邮箱是输入授权码,在qq邮箱设置 里用验证过的手机发送短信获得,不含空格 # stat()返回邮件数量和占用空间: print('Messages: %s. Size: %s' % server.stat()) # list()返回所有邮件的编号: resp, mails, octets = server.list() # 可以查看返回的列表类似['1 82923', '2 2184', ...] print(mails) # 获取最新一封邮件, 注意索引号从1开始: index = len(mails) for mail_item in range(index, 0, -1): resp, lines, octets = server.retr(mail_item) # # lines存储了邮件的原始文本的每一行, # # 可以获得整个邮件的原始文本: msg_content = b'\r\n'.join(lines).decode('gb18030', errors='ignore') # # 稍后解析出邮件: msg = Parser().parsestr(msg_content) # 获取邮件时间 tmp = msg.get("Date") tmp = tmp.split(" ") date1 = "" if len(tmp) == 5: if "" in tmp: tmp.remove("") tmp = " ".join(tmp[:4]) date1 = time.strptime(tmp, "%a, %d %b %Y") break tmp = " ".join(tmp[:4]) date1 = time.strptime(tmp, "%d %b %Y %H:%M:%S") elif len(tmp) == 8: if "" in tmp: tmp.remove("") tmp = " ".join(tmp[:5]) date1 = time.strptime(tmp, '%a, %d %b %Y %H:%M:%S') else: tmp = " ".join(tmp[:5]) date1 = time.strptime(tmp, '%a, %d %b %Y %H:%M:%S') if date1 == "": print(tmp) # date1 = time.strptime(msg.get("Date")[0:24],'%a, %d %b %Y %H:%M:%S') #格式化收件时间 date2 = time.strftime("%Y-%m-%d", date1) # 邮件时间格式转换 # ------------------可能有问题-------------------------- if (date2 < str): break # -------------------------------------------------------- if (date2 > end or date2 < str): continue txt = print_info(msg) i = txt.find('Subject:滴滴出行电子发票') ditie = False if i < 0: i = txt.find('Subject:地铁') ditie = True c = txt.find('Subject:网上购票系统--用户支付通知') print(f"c:{c}") if c > 0: if os.path.exists('tmp.txt'): print("tmp文件存在") txt = '' with open("tmp.txt", 'rt', encoding='gb18030') as f: tmp = f.read() soup = BeautifulSoup(tmp, features="html.parser") for tag in soup.find_all('div'): if tag.string is None: continue txt += tag.string f.close() index = txt.find('张史龙') txt = txt[index:] index = txt.find("。") txt = txt[:index] # data = txt.split(',') with open( os.path.join( filepath, f"railway_{datetime.datetime.now().strftime('%Y-%m-%d')}.txt" ), 'wt') as f: f.write(txt) f.close() os.remove("tmp.txt") rst = True if i >= 0: print(date2) print(f"mail_item:{mail_item} {i}:{True}") __get_attr(msg, filepath) if ditie else __get_attr( msg, filepath, "滴滴出行行程报销单") rst = True # get_attr(msg) # # 可以根据邮件索引号直接从服务器删除邮件: # # server.dele(index) # 关闭连接 server.quit() return rst
def parse_raw_mail_data(raw_lines, charset='utf8'): msg_content = b'\r\n'.join(raw_lines) return Parser().parsestr(text=msg_content)
def send_custom_email(users: List[UserProfile], options: Dict[str, Any]) -> None: """ Can be used directly with from a management shell with send_custom_email(user_profile_list, dict( markdown_template_path="/path/to/markdown/file.md", subject="Email subject", from_name="Sender Name") ) """ with open(options["markdown_template_path"]) as f: text = f.read() parsed_email_template = Parser(policy=default).parsestr(text) email_template_hash = hashlib.sha256( text.encode("utf-8")).hexdigest()[0:32] email_filename = f"custom/custom_email_{email_template_hash}.source.html" email_id = f"zerver/emails/custom/custom_email_{email_template_hash}" markdown_email_base_template_path = "templates/zerver/emails/custom_email_base.pre.html" html_source_template_path = f"templates/{email_id}.source.html" plain_text_template_path = f"templates/{email_id}.txt" subject_path = f"templates/{email_id}.subject.txt" os.makedirs(os.path.dirname(html_source_template_path), exist_ok=True) # First, we render the Markdown input file just like our # user-facing docs with render_markdown_path. with open(plain_text_template_path, "w") as f: f.write(parsed_email_template.get_payload()) from zerver.lib.templates import render_markdown_path rendered_input = render_markdown_path( plain_text_template_path.replace("templates/", "")) # And then extend it with our standard email headers. with open(html_source_template_path, "w") as f: with open(markdown_email_base_template_path) as base_template: # Note that we're doing a hacky non-Jinja2 substitution here; # we do this because the normal render_markdown_path ordering # doesn't commute properly with inline_email_css. f.write(base_template.read().replace("{{ rendered_input }}", rendered_input)) with open(subject_path, "w") as f: f.write( get_header(options.get("subject"), parsed_email_template.get("subject"), "subject")) inline_template(email_filename) # Finally, we send the actual emails. for user_profile in users: if options.get("admins_only") and not user_profile.is_realm_admin: continue context = { "realm_uri": user_profile.realm.uri, "realm_name": user_profile.realm.name, "unsubscribe_link": one_click_unsubscribe_link(user_profile, "marketing"), } send_email( email_id, to_user_ids=[user_profile.id], from_address=FromAddress.SUPPORT, reply_to_email=options.get("reply_to"), from_name=get_header(options.get("from_name"), parsed_email_template.get("from"), "from_name"), context=context, dry_run=options["dry_run"], ) if options["dry_run"]: break
print('%sText: %s' % (' ' * indent, content + '...')) else: print('%sAttachment: %s' % (' ' * indent, content_type)) email = raw_input('Email: ') password = raw_input('Password: '******'POP3 server: ') server = poplib.POP3(pop3_server) #server.set_debuglevel(1) print(server.getwelcome()) # 认证: server.user(email) server.pass_(password) print('Messages: %s. Size: %s' % server.stat()) resp, mails, octets = server.list() # 获取最新一封邮件, 注意索引号从1开始: resp, lines, octets = server.retr(len(mails)) print '\r\n'.join(lines) # 解析邮件: msg = Parser().parsestr('\r\n'.join(lines)) # 打印邮件内容: print_info(msg) # 慎重:将直接从服务器删除邮件: # server.dele(len(mails)) # 关闭连接: server.quit()
def test_egg_version(): info = Parser().parsestr(egg_info.read()) assert info['version'] == cffi.__version__
server = poplib.POP3(pop3_server) server.set_debuglevel(1) print(server.getwelcome().decode("utf-8")) server.user(email) server.pass_(password) print("Messages: %s. Size: %s" % server.stat()) resp, mails, octets = server.list() print(mails) index = len(mails) resp, lines, octets = server.retr(index) msg_content = b"\r\n".join(lines).decode("utf-8") msg = Parser().parsestr(msg_content) def decode_str(s): value, charset = decode_header(s)[0] if charset: value = value.decode(charset) return value def guess_charset(msg): charset = msg.get_charset() if charset is None: content_type = msg.get("Content-Type", "").lower() pos = content_type.find("charset=") if pos > 0:
def main(): parser = argparse.ArgumentParser(description='Input parameters', epilog='''EXAMPLE: mutt2getontracks.py -t tracks.example.com''', add_help=False, formatter_class=argparse.RawDescriptionHelpFormatter) parser.add_argument('--help', dest='printhelp', action='store_true', help='Print help.') try: printhelp = parser.parse_known_args()[0].printhelp except AttributeError: printhelp = False parser.add_argument('-u', '--username', dest='username', action='store', default=os.environ['USER'], help='username to connect\ to server.') parser.add_argument('-p', '--password', dest='password', action='store', help='user\'s password.') parser.add_argument('-t', '--target', dest='target', action='store', help='getontracks server URL') parser.add_argument('-c', '--config', dest='configfile', action='store', required=False, help='Configuration file to read.') parser.add_argument('--no-certverify', dest='verifyCert', action='store_false', help='Do not verify certificate if https is used') if printhelp: parser.print_help() sys.exit(0) parser.set_defaults(verifyCert=True) args = parser.parse_args() if not args.target: sys.stdout.write('getontracks server not set. Aborting!\n') sys.exit(1) if not args.password: args.password = getpass.getpass(args.username + '\'s Password:'******'server': args.target, 'username': args.username, 'password': args.password, 'verifyCert': args.verifyCert } if not sys.stdin.isatty(): input_stream = sys.stdin.read() if input_stream: headers = Parser().parsestr(input_stream) description = decode_header(headers['Subject'])[0][0].decode('utf-8') else: sys.stderr.write("No data available from stdin.\n") sys.exit(1) sys.stdin = open('/dev/tty') contexts = findel('contexts', **params) projects = findel('projects', **params) print(colored("-------------------------------------------------------------\n", 'magenta')) print(colored("Available contexts:", "cyan")) for c in contexts: print(colored (('%s, %s' % (c[0], c[1])), 'yellow')) print(colored("-------------------------------------------------------------\n", 'magenta')) context = int() while context not in [item[0] for item in contexts]: context = input('Select context: ') print(colored("-------------------------------------------------------------\n", 'magenta')) print(colored("Available projects:", "cyan")) for p in projects: print(colored (('%s, %s' % (p[0], p[1])), 'yellow')) print(colored("-------------------------------------------------------------\n", 'magenta')) project = int() while project not in [item[0] for item in projects]: project = input('Select project: ') writeel(description, int(context), int(project), **params) sys.exit(0)