質問: EC2+Laravel(PHP)で、大容量ファイル(1G程度)をユーザーがPOSTでアップロードするプログラムを書いています。 EC2のメモリは1Gです。 メモリとアップロードの関係がよくわからないのですが、以下の解釈のどちらが正しいのでしょうか? #### (解釈1) 「1GBのファイルは一旦メモリに載せられるため、複数人が同時にアップロードすると、メモリが足りなくなり、システムが不安定になる。」 #### (解釈2) 「1GBのファイルをアップロードしても、PHP側で適切にメモリを処理するため、複数人が同時にアップロードしても、そう簡単にはメモリ不足になることはない。」 実際、700MBのファイルをアップロード中に、SSHで、free -m を使ってメモリの推移を見たのですが、 ![イメージ説明](https://teratail-v2.storage.googleapis.com/uploads/contributed_images/676ab72862ed4c75c637af1f04b35046.png) このように、【Mem:】のところは、どんどん「used」が増えて「free」が減っていくのですが、 【-/+ buffers/cache:】の「free」のところは、810MB付近であまり変化しませんでした。 これは(解釈2)が正しいということになるのでしょうか? それとも、別の解釈として、今回はアップロードのフロント側に、『Dropzonejs』というAjax型のJSを使用しているため、 #### (解釈3) 「本来、解釈1が正しいが、この実験では、Dropzonejsを使用してAjaxで非同期処理がなされているため、解釈2のように、メモリがそれほど使用されないようになっている。」 という解釈3が正しいのでしょうか? どうぞよろしくお願い致します。
回答: *下記の回答は少なくともPHPの中ではの話です。 実装によりますが、基本的に全ての解釈が間違っております。 * アップロードされたけど、何もしない場合は、メモリを使いません。 * rename関数のように、直接ファイルを移動する系(原理上、ファイルのパスだけ書き換えるため物理位置は変わらない)の操作の場合もメモリはほとんど使用しません。 * fopenし、少しずつ読み書きするストリーム系処理もメモリの使用量は少なくなります。 * 一括で、file_get_contentsをする場合のみ、メモリを大幅に使用します。 メモリ使う例 ``` file_put_contents('test', file_get_contents($_FILES['file']['tmp_name'])); ``` 使わない例 ``` rename( $_FILES['file']['tmp_name'], 'test'); ``` メモリ上の処理とストリーム処理について、一旦調べることをお勧めします。 なお、PHPのメモリ使用量は `memory_get_peak_usage()` で取得できます。 maisumakunさんの回答では > > PHPでアップロードを処理する場合 > > > というワードが重要です。(太字で書いてくれている)