この記事では主に、PHP でファイルのダウンロードを再開するブレークポイントを実装する方法について説明します。お役に立てれば幸いです。当社の Web サイトがファイル ダウンロード サービスを提供する場合、通常はダウンロードが再開可能 (再開可能ダウンロード) であることを望みます。これは、ユーザーがダウンロードを一時停止し、再起動することなく、将来のある時点で一時停止ポイントからダウンロードを続行できることを意味します。ファイル全体をダウンロードします。
通常、Web サーバー (Apache など) は、デフォルトでダウンロードの再開のサポートを有効にします。したがって、Web サーバー経由で直接ファイルのダウンロードを提供すると、特別な構成を行わなくてもダウンロードが再開されるというメリットを享受できます。これらのファイルは Web サーバー経由で直接ダウンロードできるように提供されているため、バックエンド スクリプトはダウンロード プロセスを制御できません。これは、パブリックな静的ファイルのみを提供する Web サイトでは問題になりませんが、プライベートな動的なファイルを提供する必要がある Web サイトの場合、Web サーバー経由で直接ダウンロードを提供することはニーズを満たすことができません。現時点では、バックグラウンド スクリプト プログラムを作成するときに、ブレークポイント再開ダウンロードのサポートを追加する必要があります。
この記事ではPHPを例に、ファイルのダウンロードを再開する方法を簡単に紹介します。
原則
ダウンロードを再開する原則は比較的直感的です。
HTTP プロトコルは、リソース全体ではなく、リソースの一部を送信する方法を指定します。たとえば、ファイルのサイズが 1000 バイトの場合、ブラウザはファイルの最初の 300 バイトのみ、または 500 バイト目から 1000 バイト目までしかリクエストできません。この方法では、リソースのコンテンツ全体を 1 つのリクエストで送信する代わりに、コンテンツの一部のみをリクエストする複数のリクエストを作成できます。これらのリクエストがすべて返された後、取得したコンテンツが部分ごとに結合されて、完全なリソースが取得されます。
ダウンロードを再開できるブレークポイントを実装するには、http プロトコルの上記の特性を利用します。ユーザーがダウンロードを一時停止すると、ブラウザはダウンロードされた場所を記録します。その後、ユーザーがダウンロードを再開したときに、最初からダウンロードを開始することなく、最後に一時停止した場所からダウンロードを続行できます。
実装
部分送信は必須ではなく、サーバーがサポートしている場合とサポートしていない場合があるため、要求するリソースが部分送信をサポートしているかどうかをプログラム内でブラウザに伝える必要があります。これは、HTTP Accept-Ranges 応答ヘッダーを設定することで実現できます。 PHP コードは次のとおりです:
コードは次のとおりです:
header('Accept-Ranges: bytes');
Accept-Ranges: bytes は、リソースがバイト単位の部分転送をサポートしていることをブラウザーに伝えます。この応答ヘッダーは、部分転送をサポートするすべてのリソースに追加する必要があります。
リクエストを受信するとき、ブラウザのリクエストから、ブラウザがリクエストしているリソースの部分を抽出する必要があります。この情報は、Range リクエスト ヘッダーを通じて渡されます。 PHP では、$_SERVER['HTTP_RANGE'] に格納されます。この変数が定義されているかどうかを確認する必要があります。定義されている場合はその値を使用し、そうでない場合は範囲をリソース全体に設定します。
コードは次のとおりです:
$range = "0-". ($content_length-1); if(isset($_SERVER['HTTP_RANGE'])){ $range = $_SERVER['HTTP_RANGE']; }
次に、$range の値を分析して、リソースのどの部分を返すかを決定する必要があります。可能な値の例:
コードは次のとおりです:
100-200 // 第100到第200字节 500- // 第500字节到文件末尾 -1000 // 最后的1000个字节
ここで、Range を取得した後、以下を含む値を確認する必要があることに注意してください:
1 開始位置は負ではありません
2。終了位置は開始位置より大きい必要があります
3. 開始位置はファイルの長さから 1 を引いた値より小さい必要があります (ここでの位置インデックスは 0 から始まるため)
4. 終了位置がファイルの長さより大きい場合。マイナス 1 の場合、その値はファイルの長さから 1 を引いた値に設定する必要があります
如果Range的取值不合法,则需要终止程序并告知浏览器:
代码如下:
header('HTTP/1.1 416 Requested Range Not Satisfiable');
为了保持文章简洁,具体的校验代码这里就不提供了。下面假定你已经校验了Range的取值,并得到了 $start 和 $end 两个变量,分别表示开始位置和结束位置。
接下来要做的就是把文件的对应部分的内容发送给浏览器。不过要注意的是,这里涉及到需要发送多个HTTP响应头信息,具体如下:
代码如下:
header('HTTP/1.1 206 Partial Content'); header('Accept-Ranges: bytes'); header("Content-Range: bytes $start-$end/$filesize"); $length = $end - $start + 1; header("Content-Length: $length"); /* 输出文件的指定部分 */
这里的$length需要注意一下,它的取值是本次传输的内容的长度,而不是整个文件的长度。另外需要注意的一点是,这里的HTTP状态码是206,不是200。
总结
文件下载的断点续传实际上是利用了HTTP协议中对传输部分文件的支持。而HTTP协议的这一特性不仅可以用于实现断点续传,客户端程序也可以利用它来实现多线程下载。
在实现断点续传的过程中,需要注意正确设置各种HTTP头信息。错误的头信息将导致用户下载到的文件损坏,无法使用。
相关推荐:
以上がPHPでファイルダウンロードブレークポイント再開を実装する方法の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。