Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Stream a file to the HTTP response in Pylons

I have a Pylons controller action that needs to return a file to the client. (The file is outside the web root, so I can't just link directly to it.) The simplest way is, of course, this:

    with open(filepath, 'rb') as f:
        response.write(f.read())

That works, but it's obviously inefficient for large files. What's the best way to do this? I haven't been able to find any convenient methods in Pylons to stream the contents of the file. Do I really have to write the code to read a chunk at a time myself from scratch?

like image 276
EMP Avatar asked Mar 10 '10 00:03

EMP


1 Answers

The correct tool to use is shutil.copyfileobj, which copies from one to the other a chunk at a time.

Example usage:

import shutil
with open(filepath, 'r') as f:
    shutil.copyfileobj(f, response)

This will not result in very large memory usage, and does not require implementing the code yourself.

The usual care with exceptions should be taken - if you handle signals (such as SIGCHLD) you have to handle EINTR because the writes to response could be interrupted, and IOError/OSError can occur for various reasons when doing I/O.

like image 98
Jerub Avatar answered Sep 27 '22 15:09

Jerub