"""API details"""

# AUTOGENERATED! DO NOT EDIT! File to edit: ../nbs/00_core.ipynb.

# %% auto 0
__all__ = ['get_addr', 'attach_file', 'create_multipart_msg', 'md2email', 'smtp_connection', 'MarkdownMerge']

# %% ../nbs/00_core.ipynb
import os,mimetypes,smtplib

from fastcore.utils import *
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
from email.mime.base import MIMEBase
from email.policy import EmailPolicy
from email import encoders

from contextlib import contextmanager
from markdown import markdown
from email.headerregistry import Address
from email.header import Header
from time import sleep

# %% ../nbs/00_core.ipynb
def get_addr(email, name=None):
    "Convert `email` and optional `name` into an email `Address` object"
    return Address(email if name is None else name, addr_spec=email)

# %% ../nbs/00_core.ipynb
def attach_file(msg, f):
    "Attach file `f` to message `msg`"
    mtype,_ = mimetypes.guess_type(f)
    main,sub = (mtype or 'application/octet-stream').split('/', 1)
    part = MIMEBase(main, sub)
    with open(f, 'rb') as fp: part.set_payload(fp.read())
    encoders.encode_base64(part)
    part['Content-Disposition'] = f'attachment; filename={Path(f).name}'
    msg.attach(part)

# %% ../nbs/00_core.ipynb
def create_multipart_msg(subj, from_addr, to_addrs, md=None, html=None, attach=None):
    "Create a multipart email with markdown text and HTML"
    msg = MIMEMultipart('alternative', policy=EmailPolicy())
    msg['Subject'],msg['From'] = subj,str(from_addr)
    msg['To'] = ', '.join([str(a) for a in listify(to_addrs)])
    if md: msg.attach(MIMEText(md, 'plain'))
    if html: msg.attach(MIMEText(html, 'html'))
    for f in listify(attach): attach_file(msg, f)
    return msg

# %% ../nbs/00_core.ipynb
def md2email(subj, from_addr, to_addrs, md, attach=None):
    "Create a multipart email from markdown"
    html = markdown(md)
    return create_multipart_msg(subj, from_addr, to_addrs, md=md, html=html, attach=attach)

# %% ../nbs/00_core.ipynb
def smtp_connection(host, port, user=None, password=None, use_ssl=True, use_tls=False):
    "Create and return an SMTP connection"
    conn = smtplib.SMTP_SSL(host, port) if use_ssl else smtplib.SMTP(host, port)
    if use_tls and not use_ssl: conn.starttls()
    if user and password: conn.login(user, password)
    return conn

# %% ../nbs/00_core.ipynb
class MarkdownMerge:
    "Send templated email merge messages formatted with Markdown"
    def __init__(self, addrs, from_addr, subj, msg, smtp_cfg=None, inserts=None, test=False):
        self.addrs,self.from_addr,self.subj,self.msg,self.i = addrs,from_addr,subj,msg,0
        self.inserts = [{}]*len(addrs) if inserts is None else inserts
        self.smtp_cfg,self.test = smtp_cfg,test

    def send_msgs(self, pause=0.2):
        "Send all unsent messages to `addrs` with `pause` secs between each send"
        conn = smtp_connection(**self.smtp_cfg)
        while self.i < len(self.addrs):
            addr,insert = self.addrs[self.i],self.inserts[self.i]
            msg = self.msg.format(**insert)
            eml = md2email(self.subj, self.from_addr, addr, md=msg)
            if self.test: print(f"To: {addr}\n{'-'*40}\n{msg}\n{'='*40}\n")
            else:
                conn.send_message(eml)
                sleep(pause)
            self.i += 1
            if self.i%100==0:
                print(self.i)
                conn.quit()
                conn = smtp_connection(**self.smtp_cfg)
        conn.quit()

    def reset(self): self.i=0
