ETL过程跑完后,使用python发送邮件
Posted 勤为径,苦作舟
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了ETL过程跑完后,使用python发送邮件相关的知识,希望对你有一定的参考价值。
目标库中,如果有行数为0的表,使用python发送邮件
# -*- coding:utf-8 -*- # Author: zjc # Description:send monitor info to someone. # Date: 20170718 import contextlib import pymysql import smtplib from email.mime.text import MIMEText # 监控信息变量 TABLE_SCHEMA_LIST = (‘db-name1‘, ‘db-name2‘) COLUMN_LIST = "table_schema,table_name,table_type,table_rows,table_comment" # 邮箱信息变量 MAIL_HOST = "smtp.xxxxx.com" # set you mail host #定义成列表,实现全局变量功能 MAIL_SUBJECT = ["XX - MONITOR "] MAIL_SENDER_NAME = "[email protected]" MAIL_SENDER_PASSWORD = "******" MAIL_RECEIVERS = ["[email protected]","[email protected]"] MAIL_MESSAGE_BEGIN = """ <p>ETL结果信息</p> <table border="1"> <tr> <th>table_schema</th> <th>table_name</th> <th>table_rows</th> <th>table_comment</th> </tr> """ MAIL_MESSAGE_END = """ </table> """ # 邮局发送函数 def sendMailTo(message): msg = MIMEText(message, ‘html‘, ‘utf-8‘) msg[‘Subject‘] = MAIL_SUBJECT[0] try: server = smtplib.SMTP() server.connect(MAIL_HOST) server.login(MAIL_SENDER_NAME, MAIL_SENDER_PASSWORD) server.sendmail(MAIL_SENDER_NAME, MAIL_RECEIVERS, msg.as_string()) server.close() #print("邮件发送成功") return True except smtplib.SMTPException: #print("Error: 无法发送邮件") raise # 定义数据库连接,上下文管理器,连接后自动关闭连接 @contextlib.contextmanager def mysql(host=‘10.0.8.*‘, user=‘‘, password=‘*****‘, db=‘‘, port=3306, charset=‘utf8mb4‘): conn = pymysql.connect(host=host, port=port, user=user, passwd=password, db=db, charset=charset) cursor = conn.cursor(cursor=pymysql.cursors.DictCursor) try: yield cursor finally: conn.commit() cursor.close() conn.close() # 查询 MySql 元数据信息 def query_schema_table_info(): resultlist = [] # Connect to the database with mysql() as cursor: # Read a single record sql = "select "+ COLUMN_LIST + " FROM information_schema.TABLES " "WHERE TABLE_SCHEMA IN "+str(TABLE_SCHEMA_LIST) #print(sql) cursor.execute(sql) for row in cursor.fetchall(): resultlist.append(row) return resultlist # 根据查询结果,判断数据抽取是否正常 def deal(): mess = "" zero_table_count = 0 result_list = query_schema_table_info() for r in result_list: # 总体情况 if r["table_rows"] == 0: mess += "<tr bgcolor=‘red‘‘>" + " <td>" + r["table_schema"] + "</td>" + " <td>" + r["table_name"] + "</td>" + " <td>" + str(r["table_rows"]) + "</td>" + " <td>" + r["table_comment"] + "</td>" + " </tr>" else: mess += "<tr>" + " <td>" + r["table_schema"] + "</td>" + " <td>" + r["table_name"] + "</td>" + " <td>" + str(r["table_rows"]) + "</td>" + " <td>" + r["table_comment"] + "</td>" + " </tr>" if r["table_rows"] == 0: zero_table_count += 1 # 如果多于0个表是空的,则表示数据出问题了 if zero_table_count > 0: MAIL_SUBJECT[0] = " - MONITOR 发生错误" #print(mess) #print(MAIL_SUBJECT[0]) return mess # print(query_schema_table_info()) if __name__ == ‘__main__‘: message = MAIL_MESSAGE_BEGIN + deal() + MAIL_MESSAGE_END sendMailTo(message)
===================
放到到服务器运行可能错误:
报错一:
UnicodeDecodeError: ‘ascii‘ codec can‘t decode byte 0xe9 in position 0: ordinal not in range(128)
1、原因
因为默认情况下,Python采用的是ascii编码方式,如下所示:
python -c "import sys; print sys.getdefaultencoding()" ascii
而Python在进行编码方式之间的转换时,会将 unicode 作为“中间编码”,但 unicode 最大只有 128 那么长,所以这里当尝试将 ascii 编码字符串转换成"中间编码" unicode 时由于超出了其范围,就报出了如上错误。
2、解决办法
1)第一种:这里我们将Python的默认编码方式修改为utf-8,就可以规避上述问题的发生,具体方式,我们在Python文件的前面加上如下代码:
import sys defaultencoding = ‘utf-8‘ if sys.getdefaultencoding() != defaultencoding: reload(sys) sys.setdefaultencoding(defaultencoding)
2)第二种:我们在/usr/lib/python2.7/site-packages/目录下添加一个sitecustomize.py文件,内容如下:
import sys sys.setdefaultencoding(‘utf-8‘)
以上是关于ETL过程跑完后,使用python发送邮件的主要内容,如果未能解决你的问题,请参考以下文章