Skip to content

Instantly share code, notes, and snippets.

@zulzeen
Last active November 20, 2020 08:40
Show Gist options
  • Save zulzeen/05a6e6f6913a359a983fbbfaefbb925b to your computer and use it in GitHub Desktop.
Save zulzeen/05a6e6f6913a359a983fbbfaefbb925b to your computer and use it in GitHub Desktop.
Create in-memory zip file with multiple in-memory CSVs to serve with Django
from django.http import HttpResponse
import io
import csv
from zipfile import ZipFile
def get_zip(request):
# We generate rows for our different files
first_csv_rows = generate_rows_for_first_csv()
second_csv_rows = generate_rows_for_second_csv()
# We create file-like objects to be used as in-memory containers
# CSV files requires to be StringIO while Zip files are binary files
with io.BytesIO() as zip_buffer, io.StringIO() as first_csv, io.StringIO() as second_csv:
# We create a writer for each of our CSV files
first_writer = csv.writer(first_csv)
second_writer = csv.writer(second_csv)
# We write our rows in our CSV files
first_writer.writerows(first_rows)
second_writer.writerows(second_rows)
# We create our Zip file from our file-like object
with ZipFile(zip_buffer, 'w') as zip_file:
# Then write our CSV file-like
zip_file.writestr('first.csv', first_csv.getvalue())
zip_file.writestr('second.csv', second_csv.getvalue())
# Exiting the "with" statement closes the Zip file, effectivly "writing" data in our
# file-like BytesIO object
# We then pass the binary content of our binary file-like to our response
response = HttpResponse(zip_buffer.getbuffer().tobytes(), content_type="application/zip")
# Every file-like object is now closed
# We precise our response has an attachement
response['Content-disposition'] = 'attachement; filename=export.zip'
# We return our response
return response
@zulzeen
Copy link
Author

zulzeen commented Nov 20, 2020

Of course, if we've had more than two files, a "for" iteration would've been welcome, but for readability I kept it simple.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment