アップロードファイルとアップロードハンドラ¶
アップロードファイル¶
ファイルアップロード中、実際のファイルデータは request.FILES
に保存されます。この辞書の各エントリーは UploadedFile
オブジェクト(またはそのサブクラス)です。これはアップロードされたファイルのラッパーです。アップロードされたコンテンツにアクセスするために、通常、以下のメソッドのいずれかを使用します:
- UploadedFile.read()¶
アップロードされたデータ全体をファイルから読み込む。このメソッドには注意が必要です。アップロードされたファイルが巨大な場合、それをメモリに読み込もうとするとシステムを圧迫する可能性があります。おそらく代わりに
chunks()
を使うことになるでしょう。
- UploadedFile.multiple_chunks(chunk_size=None)¶
アップロードされたファイルが、複数のチャンクに分けて読み込む必要があるほど大きい場合に
True
を返します。デフォルトでは2.5MB以上のファイルですが、設定可能です。
- UploadedFile.chunks(chunk_size=None)¶
ファイルのチャンクを返すジェネレータです。
multiple_chunks()
がTrue
の場合、read()
の代わりにこのメソッドをループで使用すべきです。実際には、常に
chunks()
を使用するのが最も簡単です。read()
を使用する代わりにchunks()
をループ処理することで、大きなファイルがシステムのメモリを圧迫しないようにできます。
UploadedFile
の有用な属性は次の通りです:
- UploadedFile.name¶
アップロードされたファイルの名前 (例:
my_file.txt
)。
- UploadedFile.size¶
アップロードされたファイルのサイズ(バイト単位)。
- UploadedFile.content_type¶
ファイルと共にアップロードされるコンテンツタイプのヘッダ (例: text/plain や application/pdf)。ユーザーから提供されるデータのように、アップロードされたファイルが実際にこのタイプであると信頼すべきではありません。依然として、ファイルがコンテンツタイプヘッダが示すコンテンツを含んでいることを検証する必要があります。"信頼するが検証せよ" です。
- UploadedFile.content_type_extra¶
content-type
ヘッダーに渡される追加のパラメータを含む辞書です。通常、Google App Engine などのサービスがファイルのアップロードを取り扱っている場合に提供されます。その結果、ハンドラはアップロードされたファイル内容を受信しないかもしれず、代わりにファイルへの URL や他のポインターを受け取ります (RFC 2388 を参照)。
- UploadedFile.charset¶
text/* コンテンツタイプについては、ブラウザが提供する文字セット(例えば
utf8
)です。ここでも、"信頼するが検証せよ" が最良の方針です。
注釈
通常の Python ファイルのように、アップロードされたファイルをイテレートすることで、ファイルを一行ずつ読むことができます:
for line in uploadedfile:
do_something_with(line)
行は ユニバーサル改行 によって分割されます。以下のものが行の終わりとして認識されます: Unix の改行規則 '\n'
、Windowsの改行規則 '\r\n'
、古い Macintosh の改行規則 '\r'
。
UploadedFile
のサブクラスには以下が含まれます:
- class TemporaryUploadedFile[ソース]¶
一時的な場所にアップロードされたファイル (つまり、stream-to-disk)。このクラスは、
TemporaryFileUploadHandler
によって使用されます。UploadedFile
のメソッドに加えて、1つの追加メソッドを持っています:
- class InMemoryUploadedFile[ソース]¶
メモリへのアップロードされたファイル(つまり、stream-to-memory)。このクラスは
MemoryFileUploadHandler
によって使用されます。
ビルトインのアップロードハンドラ¶
MemoryFileUploadHandler
と TemporaryFileUploadHandler
は、小さなファイルをメモリに読み込み、大きなファイルをディスクに保存するDjangoのデフォルトのファイルアップロードの動作を提供します。これらは django.core.files.uploadhandler
に位置しています。
小さいファイル用にアップロードをメモリにストリームするためのファイルアップロードハンドラ。
TemporaryUploadedFile
を使ってデータを一時ファイルにストリームするアップロードハンドラ。
アップロードハンドラをカスタマイズする¶
全てのファイルアップロードハンドラは、django.core.files.uploadhandler.FileUploadHandler
のサブクラスとなります。アップロードハンドラはいつでも好きなときに定義できます。
必要なメソッド¶
カスタマイズされたファイルアップロードハンドラでは、以下のメソッドを定義する 必要があります。
- FileUploadHandler.receive_data_chunk(raw_data, start)[ソース]¶
ファイルアップロードから、データの "chunk" を受け取ります。
raw_data
はアップロードされたデータを含むバイト文字列です。start
はこのraw_data
チャンクが始まる、ファイル内での位置です。あなたが返すデータは、その後のアップロードハンドラの
receive_data_chunk
メソッドに渡されます。 この方法で、1 つのハンドラは他のハンドラの「フィルタ」になることができます。receive_data_chunk
からNone
を返し、残りのアップロードハンドラがこのチャンクを取得するのを短絡します。 これは、アップロードしたデータを自分で保存しておき、将来のハンドラでデータのコピーを保存したくない場合に便利です。StopUpload
またはSkipFile
例外を発生させると、アップロードが中止されるか、ファイルが完全にスキップされます。
省略可能なメソッド¶
独自のアップロードハンドラは、以下の省略可能なメソッドや属性を定義できます:
- FileUploadHandler.chunk_size¶
Django がメモリに格納してハンドラに送り込む "chunks" のサイズです (byte で表されます)。 つまり、この属性は
FileUploadHandler.receive_data_chunk
に渡されるチャンクのサイズをコントロールします。パフォーマンスを最大限にするために、チャンクサイズは
4
で割り切れる必要があり、2 GB (231 bytes) を超えてはいけません。 複数のハンドラによってチャンクサイズが複数ある場合、Django はハンドラで定義された最小のチャンクサイズを使用します。デフォルトは 64*210 bytes、つまり 64 KB です。
- FileUploadHandler.new_file(field_name, file_name, content_type, content_length, charset, content_type_extra)[ソース]¶
新しいファイルのアップロード開始を通知するコールバックです。 アップロードハンドラにデータが送られる前に呼び出されます。
field_name
は、ファイル<input>
フィールドの文字列名です。file_name
はブラウザによって提供されるファイル名です。content_type
は、ブラウザによって提供される MIME タイプです -- 例:'image/jpeg'
。content_length
は、ブラウザによって与えられる画像の長さです。提供されずにNone
となることがあります。charset
は、ブラウザによって与えられる文字セットです (例:utf8
)。content_length
のように、提供されないことがあります。content_type_extra
は、content-type
からの、ファイルについての追加情報です。UploadedFile.content_type_extra
を参照してください。このメソッドは、将来のハンドラがこのファイルをハンドリングするのを防ぐため、
StopFutureHandlers
例外を投げます。
- FileUploadHandler.upload_interrupted()[ソース]¶
アップロードが中断されたことを通知するコールバック。例えば、ユーザーがファイルアップロード中にブラウザを閉じたときなど。
- FileUploadHandler.handle_raw_input(input_data, META, content_length, boundary, encoding)[ソース]¶
ハンドラに対して、生の HTTP インプットのパースを完全にオーバーライドできるようにします。
input_data
は、read()
をサポートするファイルのようなオブジェクトです。META
は、request.META
と同じオブジェクトです。content_length
は、input_data
内のデータの長さです。input_data
からcontent_length
バイト以上を読み出さないでください。boundary
は、このリクエストの MIME boundary です。encoding
は、リクエストのエンコーディングです。アップロードハンドリングを継続したいとき、
None
を返します。もしくはリクエストに適した新しいデータ構造を直接返したいとき、(POST, FILES)
のタプルを返します。