Oracle SQL查询导出Excel并发送邮件时波斯文显示为问号的技术问询
波斯文显示为问号的问题排查与解决
在使用Python的pandas库执行Oracle SQL查询,将结果导出为Excel文件并通过邮件发送时,波斯文内容显示为问号。相关实现代码如下:
connection = cx_Oracle.connect(user_db,password_db,dsn_tns) df = pd.read_sql(query,con=connection) attach_file_name = filename+'_'+timestr+'.xlsx' df.to_excel(attach_file_name,sheet_name="report",encoding="utf-8",engine='xlsxwriter') msg.attach(MIMEText(body,'plain')) attach_file = open(attach_file_name,'rb') payload = MIMEBase('application','octate-stream') payload.set_payload((attach_file).read()) encoders.encode_base64(payload) payload.add_header('Content-Disposition',"attach_file; filename= "+attach_file_name) msg.attach(payload)
以下是具体的排查和解决步骤:
1. 确保Oracle连接使用正确字符集
cx_Oracle连接时未指定字符集,会导致非ASCII字符读取后编码异常。连接时需显式设置encoding和nencoding为UTF-8(匹配Oracle数据库的AL32UTF8字符集):
connection = cx_Oracle.connect( user_db, password_db, dsn_tns, encoding="UTF-8", nencoding="UTF-8" )
这一步是核心,若数据库字符集为AL32UTF8,设置后能保证读取的波斯文是正确的Unicode字符串。
2. 修正Excel导出的字体格式
xlsxwriter引擎默认使用UTF-8,但部分Excel默认字体不支持波斯文,需指定支持的字体(如Arial Unicode MS):
# 替换原有的to_excel代码 writer = pd.ExcelWriter(attach_file_name, engine='xlsxwriter') df.to_excel(writer, sheet_name="report", index=False) workbook = writer.book worksheet = writer.sheets["report"] # 创建支持波斯文的单元格格式 persian_format = workbook.add_format({'font_name': 'Arial Unicode MS'}) # 对波斯文列应用格式(示例为第2列,索引从0开始,根据实际调整) worksheet.set_column(1, 1, None, persian_format) writer.close()
注:to_excel的encoding参数对xlsxwriter无效,无需设置。
3. 修复邮件附件的文件名编码
邮件附件文件名包含非ASCII字符时,需用RFC 2047格式编码,否则客户端可能解析异常:
from email.header import Header # 替换原有的add_header行 payload.add_header( 'Content-Disposition', 'attachment', filename=(Header(attach_file_name, 'UTF-8').encode()) )
同时注意原代码中Content-Disposition的参数写错了,应该是attachment而非attach_file。
4. 验证数据框中的字符正确性
导出前先确认数据框中的波斯文是否正常:
# 替换为你的波斯文列名 print(df['persian_column'].head())
如果输出已经是问号,说明问题出在Oracle数据读取阶段,重点检查第1步的连接字符集设置。
内容的提问来源于stack exchange,提问作者MohammadReza moeini
相关产品推荐
相关产品推荐

