接收邮件

import imaplib
import email
from email.header import decode_header
import argparse


if __name__ == "__main__":
    parser = argparse.ArgumentParser()
    parser.add_argument("--imapserver", type=str, help="imap服务地址")
    parser.add_argument("--imapport", type=int, help="imap端口")
    parser.add_argument("--emailaddress", type=str, help="邮箱地址")
    parser.add_argument("--emailpassword", type=str, help="邮箱IMAP授权码")
    parser.add_argument("--savepath", type=str, help="附件保存目录")
    args = parser.parse_args()
    IMAP_SERVER,IMAP_PORT,EMAIL_ADDRESS,EMAIL_PASSWORD = args.imapserver,args.imapport,args.emailaddress,args.emailpassword
    savepath = args.savepath
    print(IMAP_SERVER,IMAP_PORT,EMAIL_ADDRESS,EMAIL_PASSWORD,savepath)

    # # IMAP服务器的地址和端口
    # IMAP_SERVER = 'imap.126.com'  # 例如: 'imap.gmail.com'  
    # IMAP_PORT = 993  # 默认IMAP端口为993  
    # EMAIL_ADDRESS = 'xxx@126.com'  # 你的邮箱地址  
    # EMAIL_PASSWORD = 'xxx'  # 你的邮箱密码

    # 创建 IMAP 连接
    imap_conn = imaplib.IMAP4_SSL(IMAP_SERVER, IMAP_PORT)

    # 登录邮箱账户
    imap_conn.login(EMAIL_ADDRESS, EMAIL_PASSWORD)
    imap_id = ("name", "RPA robot", "version", "1.0.0", "vendor", "ins")
    typ, data = imap_conn.xatom('ID', '("' + '" "'.join(imap_id) + '")')
    print('conn:',imap_conn)
    # 选择邮箱文件夹(例如'INBOX')
    mailbox = "Trash"
    status,response = imap_conn.select('INBOX')
    print('status:',status)
    print('imap conn:',imap_conn)
    # 搜索最新一封邮件
    status, response = imap_conn.search(None, 'ALL')
    print('status:',status)
    latest_email_id = response[0].split()[-1]

    # 获取最新一封邮件的内容
    status, response = imap_conn.fetch(latest_email_id, '(RFC822)')
    raw_email = response[0][1]
    email_message = email.message_from_bytes(raw_email)

    # 解析邮件主题
    subject = decode_header(email_message['Subject'])[0][0]
    if isinstance(subject, bytes):
        subject = subject.decode('GBK')

    # 解析发件人
    sender = decode_header(email_message['From'])[0][0]
    if isinstance(sender, bytes):
        sender = sender.decode('GBK')

    print("主题:", subject)
    print("发件人:", sender)

    # 解析邮件正文
    for part in email_message.walk():
        content_type = part.get_content_type()
        print('type:',content_type[:40])
        print('-------------------')
        if content_type == 'text/plain' or content_type == 'text/html':
            charset = part.get_content_charset()
            email_content = part.get_payload(decode=True)
            if charset:
                email_content = email_content.decode(charset)
            print("邮件内容:", email_content)

        # 解析附件
        if content_type.startswith('application/vnd.openxmlformats-officedoc'):
            filename = part.get_filename()
            if filename:
                filename = decode_header(filename)[0][0]
                print(filename)
                if isinstance(filename, bytes):
                    filename = filename.decode('GBK')
                print("附件:", filename)
                part = part.get_payload(decode=True)  # 获取附件内容(解码为bytes)  
                with open(savepath+filename, 'wb') as file:  # 将附件内容写入文件  
                    file.write(part)  # 将附件内容写入文件

    imap_conn.logout()

问题 command SEARCH illegal in state AUTH, only allowed in states SELECTED

参考

添加身份信息

import imaplib
 
# 添加缺失的命令
imaplib.Commands['ID'] = ('AUTH')
 
conn = imaplib.IMAP4_SSL(port = '993',host = 'imap.163.com')
conn.login('XXXX@163.com','HJKHSHDFIWRNKJHI')
 
# 上传客户端身份信息
args = ("name","XXXX","contact","XXXX@163.com","version","1.0.0","vendor","myclient")
typ, dat = conn._simple_command('ID', '("' + '" "'.join(args) + '")')
print(conn._untagged_response(typ, dat, 'ID'))
 
status, msgs = conn.select()