Как ограничить скорость загрузки в этом PHP-коде - PullRequest
0 голосов
/ 03 апреля 2019

У меня есть следующий код PHP, который касается методов загрузки для моего сайта.Я пытаюсь ограничить скорость загрузки чем-то конкретным, так как она в настоящее время злоупотребляет менеджерами загрузки.

К сожалению, у меня нет опыта в кодировании.

public function download(
    $file,
    $filename,
    $file_size,
    $content_type,
    $disposition = 'inline',
    $android = false
) {
    // Gzip enabled may set the wrong file size.
    if (function_exists('apache_setenv')) {
        @apache_setenv('no-gzip', 1);
    }
    if (ini_get('zlib.output_compression')) {
        @ini_set('zlib.output_compression', 'Off');
    }
    @set_time_limit(0);
    session_write_close();
    header("Content-Length: ".$file_size);

    if ($android) {
        header("Content-Type: application/octet-stream");
        header("Content-Disposition: attachment; filename=\"".$filename."\"");
    } else {
        header("Content-Type: $content_type");
        header("Content-Disposition: $disposition; filename=\"".$filename."\"");
        header("Content-Transfer-Encoding: binary");
        header("Expires: -1");
    }
    if (ob_get_level()) {
        ob_end_clean();
    }
    readfile($file);
    return true;
}

1 Ответ

0 голосов
/ 03 апреля 2019

Код:

<?php 
public function download(
    $file,
    $filename,
    $file_size,
    $content_type,
    $disposition = 'inline',
    $android = false
) {
    // Gzip enabled may set the wrong file size.
    if (function_exists('apache_setenv')) {
        @apache_setenv('no-gzip', 1);
    }
    if (ini_get('zlib.output_compression')) {
        @ini_set('zlib.output_compression', 'Off');
    }
    @set_time_limit(0);
    session_write_close();
    header("Content-Length: ".$file_size);

    if ($android) {
        header("Content-Type: application/octet-stream");
        header("Content-Disposition: attachment; filename=\"".$filename."\"");
    } else {
        header("Content-Type: $content_type");
        header("Content-Disposition: $disposition; filename=\"".$filename."\"");
        header("Content-Transfer-Encoding: binary");
        header("Expires: -1");
    }
    if (ob_get_level()) {
        ob_end_clean();
    }

    $this->readSlow($file, 1);

    return true;
}

private function readSlow(string $filename, int $sleepAmount = 0, int $chunkSize = 409600)
{
    $handle = fopen($filename, "r");

    while (!feof($handle)) {
        echo fread($handle, $chunkSize);
        ob_flush();
        sleep($sleepAmount);
    }
    fclose($handle);
}

Примечание:

Я предполагаю, что вы разместили часть своего класса. Если вы хотите использовать readSlow() вне класса, используйте его следующим образом:

readSlow('pathToFile', $amountOfSleep, $amountOfBytesToReadAtOneRead);

Это необязательно,

ob_flush();

Я сделал это так, как только буфер прочитан, он сразу же отправляется клиенту, который запросил данные, но в вашем случае может быть лучше удалить его - проверьте, лучше ли с ним или нет для других значений $amountSleep и $chunkSize

sleep () не потребляет время полного выполнения вашего скрипта, поэтому, если файл загружается без ожидания в течение 10 секунд, а максимальное время выполнения сценария php составляет 30 секунд, вы можете легко сделать скрипт, работающий 120 секунд на загрузку, используя sleep.
Вместо использования sleep () вы можете использовать usleep () , который должен дать вам более точный контроль над ограничением скорости, потому что это занимает время сна в микросекундах, чем в секундах, так что имейте это в виду при использовании и если вы хотите перейти в режим сна между считываниями на 1 секунду, тогда $sleepAmount следует установить равным 1000000 при использовании usleep ()

$chunkSize - это количество байтов, которые будут прочитаны, а затем ваш скрипт перейдет в спящий режим. Поиграйте с этим значением, чтобы получить оптимальную скорость.

Я не тестировал код, поэтому он может работать, может и не работать, но, по крайней мере, это идея для начала.

...