Skip to content
Advertisement

ZipFile does not store any text inside an archived file

The following code results in the file found in the zip being empty, instead of having some text in it:

def func(path):
    with tempfile.NamedTemporaryFile() as f:
        f.write('some text')
        with zipfile.ZipFile(path + '.zip', 'w', zipfile.ZIP_DEFLATED) as zf:
            zf.write((f.name), path)

Advertisement

Answer

Add flush to the file object:

def func(path):
    with tempfile.NamedTemporaryFile() as f:
        f.write('some text')
        f.flush()  # <-- lifesaver
        with zipfile.ZipFile(path + '.zip', 'w', zipfile.ZIP_DEFLATED) as zf:
            zf.write((f.name), path)

This problem also affects normal (non-temporary) files, so they’ll also need the flush treatment:

def func(path):
    with open(path, 'w') as f:
        f.write('some text')
        f.flush()  # <-- lifesaver
        with zipfile.ZipFile(path + '.zip', 'w', zipfile.ZIP_DEFLATED) as zf:
            zf.write(path)

Alternatively, de-denting the 2nd with block would avoid having to use flush since a file gets closed automatically when that block exits, increasing the chance of it being flushed:

def func(path):
    with open(path, 'w') as f:
        f.write('some text')
    with zipfile.ZipFile(path + '.zip', 'w', zipfile.ZIP_DEFLATED) as zf:
        zf.write(path)

Note that this will only work for the 2nd example, but not the 1st; see tempfile docs for the reason why.

User contributions licensed under: CC BY-SA
3 People found this is helpful
Advertisement