如何将两个Python邮件函数重构为通用可复用的邮件模块函数?
重构通用邮件函数方案
先梳理两个函数的重复与差异
- 重复部分:SMTP服务器连接、基础参数(环境标识、发件人、收件人)、邮件发送流程
- 差异部分:邮件主题前缀、正文内容结构、所需的业务参数
方案一:通过类型参数区分业务场景(适合场景固定的情况)
这种方式通过一个email_type参数指定业务场景,内部根据类型生成对应主题和正文,同时用关键字参数接收不同场景的专属参数。
import smtplib def send_email(env, from_email, to, email_type, **kwargs): # 初始化SMTP服务器(修正原代码大小写错误:Smtp → SMTP) server = smtplib.SMTP('server') # 根据邮件类型生成主题和正文 if email_type == 'discrepancy': # 校验必要参数 if 'fcnt' not in kwargs or 'fsize' not in kwargs: raise ValueError("发送差异告警邮件需传入fcnt和fsize参数") fcnt = str(kwargs['fcnt']) fsize = str(kwargs['fsize']) subject = f'Alert on {env}' text = f'discrepancy in {fcnt} and {fsize}' # 修正原代码拼写错误:discrepency → discrepancy elif email_type == 'rfb': if 'web_url' not in kwargs or 'error_msg' not in kwargs: raise ValueError("发送RFB告警邮件需传入web_url和error_msg参数") web_url = str(kwargs['web_url']) error_msg = str(kwargs['error_msg']) subject = f'Rfb alert on {env}' text = f'URL: {web_url}\nError Message: {error_msg}' # 把原元组格式改为易读的字符串 else: raise ValueError(f"不支持的邮件类型:{email_type}") # 修正邮件格式:主题前必须加Subject: ,否则客户端无法识别 message = f'Subject: {subject}\n\n{text}' # 统一变量大小写(原代码存在Server/server、Message/message混用问题) server.sendmail(from_email, to, message) # 新增关闭连接逻辑,避免资源泄漏 server.quit()
调用示例
- 对应原
email函数的调用:
send_email('prod', 'sender@example.com', 'recipient@example.com', 'discrepancy', fcnt=100, fsize=90)
- 对应原
email_rfb函数的调用:
send_email('test', 'sender@example.com', 'recipient@example.com', 'rfb', web_url='https://example.com/rfb', error_msg='Timeout error')
方案二:传入主题/正文生成函数(扩展性更强)
如果后续可能新增更多邮件场景,这种方式更灵活——把主题和正文的生成逻辑作为参数传入,函数只负责通用的邮件发送流程。
import smtplib def send_generic_email(env, from_email, to, subject_generator, body_generator, **kwargs): server = smtplib.SMTP('server') # 调用传入的生成器函数生成主题和正文 subject = subject_generator(env, **kwargs) body = body_generator(**kwargs) message = f'Subject: {subject}\n\n{body}' server.sendmail(from_email, to, message) server.quit()
调用示例
- 对应原
email函数的调用:
def discrepancy_subject(env, **kwargs): return f'Alert on {env}' def discrepancy_body(**kwargs): fcnt = str(kwargs['fcnt']) fsize = str(kwargs['fsize']) return f'discrepancy in {fcnt} and {fsize}' send_generic_email('prod', 'sender@example.com', 'recipient@example.com', discrepancy_subject, discrepancy_body, fcnt=100, fsize=90)
- 对应原
email_rfb函数的调用:
def rfb_subject(env, **kwargs): return f'Rfb alert on {env}' def rfb_body(**kwargs): web_url = str(kwargs['web_url']) error_msg = str(kwargs['error_msg']) return f'URL: {web_url}\nError Message: {error_msg}' send_generic_email('test', 'sender@example.com', 'recipient@example.com', rfb_subject, rfb_body, web_url='https://example.com/rfb', error_msg='Timeout error')
关键修正点说明
- 统一了原代码中变量大小写混乱的问题(如
Smtp→SMTP、Server/server统一) - 修复了邮件主题格式错误(必须以
Subject:开头,否则客户端无法识别) - 修正了
discrepency的拼写错误 - 新增了SMTP连接关闭逻辑,避免资源泄漏
- 增加了参数校验,防止调用时遗漏必要参数导致报错
内容的提问来源于stack exchange,提问作者Ash_05
相关产品推荐
相关产品推荐

