GAE的Python:解析压缩的XML超过内存(GAE Python: Parsing compre

2019-10-29 07:39发布

我试图获取并解析XML文件转换成DATABSE。 XML是在gzip压缩。 gzip文件是8MB〜。 当我运行的代码在本地上pythonw.exe内存积聚,导致整个系统(Windows 7)停止响应级别,当我在网上运行超过在谷歌App Engine的内存限制。 不知道如果文件过大,或者如果我做错了什么。 任何帮助将非常感谢!

from google.appengine.ext import webapp
from google.appengine.api.urlfetch import fetch
from xml.dom.minidom import parseString
import gzip
import base64
import StringIO

class ParseCatalog(webapp.RequestHandler):
user = xxx
password = yyy
catalog = fetch('url',
                    headers={"Authorization": 
                             "Basic %s" % base64.b64encode(user + ':' + password)}, deadline=600)
xmlstring = StringIO.StringIO(catalog.content)
gz = gzip.GzipFile(fileobj=xmlstring)
gzcontent = gz.read()
contentxml = parseString(gzcontent)
items = contentxml.getElementsByTagName("Product")

for item in items:
    item = DatabaseEntry()
    item.name = str(coupon.getElementsByTagName("Manufacturer")[0].firstChild.data)
    item.put()

UPDATE

于是,我就跟着BasicWolf的建议切换到LXML但我有它导入问题。 我下载了LXML 2.3库,并把它放在我的应用程序的文件夹中(我知道这是不理想,但它是我知道如何将第三方库的唯一途径)。 另外,我补充下我的app.yaml:

libraries:
- name: lxml
  version: "2.3"

然后,我写了下面的代码来测试它是否解析:

import lxml

class ParseCatalog(webapp.RequestHandler):
    user = xxx
    password = yyy
    catalog = fetch('url',
                    headers={"Authorization": 
                             "Basic %s" % base64.b64encode(user + ':' + password)}, deadline=600)
    items = etree.iterparse(catalog.content)

    def get(self): 
       for elem in items:
           self.response.out.write(str(elem.tag))

然而,这是导致出现以下错误:

ImportError: cannot import name etree

我已经检查这个错误的其他问题,似乎我在Windows 7上运行的事实,可能会起到一定的作用。 我也试图从安装预编译的二进制包http://www.lfd.uci.edu/~gohlke/pythonlibs/#lxml但这并不会改变任何事情。

Answer 1:

你能指望什么? 首先,你读一个串入内存,然后 - 把它解压到内存中,然后 - 构建一个DOM树,还是在内存中。

这里有一些改进:

  1. del每个缓冲区的变量,你不需要它的那一刻。
  2. 摆脱DOM的XML解析器,使用事件驱动LXML以节省内存。


文章来源: GAE Python: Parsing compressed XML exceeds memory