使用 zipfile zlib python 和 mailgun 时,Mailgun 仅在 Python 脚本中发送部分 zip 文件
Posted
技术标签:
【中文标题】使用 zipfile zlib python 和 mailgun 时,Mailgun 仅在 Python 脚本中发送部分 zip 文件【英文标题】:Mailgun only sends partial zip file in Python script when using zipfile zlib python and mailgun 【发布时间】:2016-02-26 19:41:28 【问题描述】:编辑:我尝试实现 gzip,但无法使其与 zipfile 库一起使用。文档似乎表明 zlib 是唯一兼容的库。我还尝试重新安装 zlib。
我创建的 Python 脚本遇到了一个奇怪的问题。该脚本的重点是从 SQL 服务器中提取一些数据,将其转储为 CSV,将其压缩(压缩)并通过 Mailgun API 发送电子邮件。
如果我在没有 zlib 压缩的情况下压缩文件,mailgun 会提取整个 zip 文件(包含测试数据的 14mb)并通过电子邮件成功发送。我可以从电子邮件和我的本地文件系统下载 zip 文件,并在其中打开 csv 文件而不会出现问题。
但是一旦我添加了 zipfile.ZIP_DEFLATED 压缩方法,我就会遇到问题。生成的 zip 在我的本地文件系统上下降到 365kb,并且可以正常打开。但是当我查看生成的电子邮件时,zip 文件的大小被严重截断,约为 865 字节。如果我尝试下载并打开它,我会从 Windows 收到“这不是一个有效的 zip 文件”错误。
为什么 Mailgun 会发送完整的未压缩 zip,而不是压缩的 zip,即使它在我的文件系统上可以正常打开?即使代码显然是同步的,我也尝试过一件疯狂的事情,就是在函数调用之间添加暂停,以防压缩需要更多时间。这没有帮助。
代码如下,为简洁起见已剪辑。
import pyodbc
import unicodecsv
import time
import requests
import zipfile
import zlib
now = time.localtime(time.time())
today = time.strftime("%Y-%m-%d %H%M%p", now)
filename_sql1 = "SCORM Courses " + today
filename_sql2 = "Non-SCORM Courses " + today
print "ready...."
class ODBCtoCSV(object):
def __init__(self):
def getEncodedData (self, doubleList):
data=struct.pack(len(doubleList) * 'd', *doubleList)
return base64.b64encode(data)
def dump(self, sql, filename, include_headers=True):
f = unicodecsv.writer(file(filename + ".csv", 'wb'))
cnxn = pyodbc.connect(self.connect_string)
c = cnxn.cursor()
c.execute(sql)
if include_headers:
f.writerow([d[0] for d in c.description])
f.writerows(c.fetchall())
cnxn.close()
def generatereport(s, filename):
print "Processing %s" % (filename)
if __name__ == '__main__':
query = ODBCtoCSV()
query.dump(s, filename)
f = open(filename + ".csv", 'rb')
def zippy(filename):
zf = zipfile.ZipFile(filename + ".zip", "w", zipfile.ZIP_DEFLATED)
zf.write(filename + ".csv")
zf.close()
def send_notification_message(filename):
return requests.post(
"xxxxxxx",
auth=("api", "xxxx"),
files=[("attachment", open(filename + ".zip"))],
data="from": "xxxxxxx",
"to": ["xxxxxx"],
"subject": " Reports are Available",
"text": "This is an automated message. The reports have run successfully and are available via attachment.",
"html": "<p><b>This is an automated message.</b></p><p>The reports have run successfully and are available via attachment.</p>",
"o:tag": "xxxxxx")
generatereport(sql1, filename_sql1)
zippy(filename_sql1)
print filename_sql1 + "Succesfully generated"
generatereport(sql2, filename_sql2)
zippy(filename_sql2)
print filename_sql2 + "Succesfully generated"
send_notification_message(filename_sql1)
send_notification_message(filename_sql2)
exit
【问题讨论】:
【参考方案1】:我通过在 Mailgun 调用中将模式文件 IO 模式更改为“rb”解决了这个问题。
我不确定为什么它适用于未压缩的 zip 文件,但仍然不能用于压缩的 zip 文件。修改后的代码如下。
files=[("attachment", open(filename + ".zip", "rb"))],
【讨论】:
以上是关于使用 zipfile zlib python 和 mailgun 时,Mailgun 仅在 Python 脚本中发送部分 zip 文件的主要内容,如果未能解决你的问题,请参考以下文章
tomcat 启动异常 EOFException: Unexpected end of ZLIB input stream