За последние 24 часа нас посетили 8445 программистов и 464 робота. Сейчас ищут 222 программиста ...

Как отдать файл на загрузку

Тема в разделе "PHP для новичков", создана пользователем 440Hz, 13 дек 2007.

  1. amen

    amen Активный пользователь

    С нами с:
    18 сен 2009
    Сообщения:
    298
    Симпатии:
    0
    Адрес:
    Узбекистан
    header('Content-Disposition: attachment; filename='.IRB_ROOT .'skins/files/25.jpg');

    Подскажите пожалуйста, как сделать, чтобы пользователь получал файл с именем 25.jpg, а не O__home_sp.uz_www_skins_files_25.jpg
     
  2. shurastik

    shurastik Активный пользователь

    С нами с:
    22 фев 2008
    Сообщения:
    285
    Симпатии:
    0
    Адрес:
    Латвия
    да вы прикалываетесь
     
  3. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.439
    Симпатии:
    1.744
    header('Content-Disposition: attachment; filename='25.jpg');

    :D
     
  4. amen

    amen Активный пользователь

    С нами с:
    18 сен 2009
    Сообщения:
    298
    Симпатии:
    0
    Адрес:
    Узбекистан
    Оу...
    а путь к файлу тогда где прописывать?
     
  5. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.439
    Симпатии:
    1.744
    приехали

    а ты вобще с какой целью и в каком коде такой хидер мутишь?
     
  6. amen

    amen Активный пользователь

    С нами с:
    18 сен 2009
    Сообщения:
    298
    Симпатии:
    0
    Адрес:
    Узбекистан
    Мне нужно отдать файл на загрузку. Юзер жмёт ссылку - начинается скачивание.
     
  7. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.439
    Симпатии:
    1.744
    ну дык дай ссылку на файл, зачем тебе хидеры всякие?
     
  8. amen

    amen Активный пользователь

    С нами с:
    18 сен 2009
    Сообщения:
    298
    Симпатии:
    0
    Адрес:
    Узбекистан
    Ну потом счётчик буду прикручивать...какая разница.
    Так где путь прописывать?))
     
  9. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.439
    Симпатии:
    1.744
    в караганде. =) Ты КАК собираешься отдавать файл? Телепатически?
    КУДА ты хочешь прописать хидер? Ответь на эти вопросы, и вопрос про "куда" отпадет автоматом.
     
  10. amen

    amen Активный пользователь

    С нами с:
    18 сен 2009
    Сообщения:
    298
    Симпатии:
    0
    Адрес:
    Узбекистан
    Ну вобщем так
    я где-то прописываю ссылку, по нажатии идёт перенаправление в определённый скрипт. В этом скрипте - "если ссылка нажата, то..." и тут этот самый хэдэр. Файл скачивается, меня не устраивает только имя...
     
  11. amen

    amen Активный пользователь

    С нами с:
    18 сен 2009
    Сообщения:
    298
    Симпатии:
    0
    Адрес:
    Узбекистан
    + проблемка
    оказалось, что скачиваемое изображение недоступно для просмотра.
     
  12. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.439
    Симпатии:
    1.744
    ну дык скрипт-то этот файл отдает. какое отношение отдаваемое имя имеет к имени файла который читается и отдается скриптом? (КО считает нужным указать, что никакого!)

    ты понимаешь?
     
  13. amen

    amen Активный пользователь

    С нами с:
    18 сен 2009
    Сообщения:
    298
    Симпатии:
    0
    Адрес:
    Узбекистан
    Чувак, у меня инета на 15 минут осталось, будь другом, подскажи выход.

    Имя нужно отдавать отдельно? Ещё один хедер?
     
  14. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.439
    Симпатии:
    1.744
    Нет. в этом хедере =) Иди спать!

    тут пишешь че как будет называтся для пользователя в хидерах, а читаешь и отдаешь тот файл, который сам хочешь.
    Ты понимаешь это, нет? Скрипту посрать как называется файл у тебя на сервере, как ты хочешь чтобы он назывался у юзера - пропиши в хедер.
    http://www.php.ru/forum/viewtopic.php?t=13296
     
  15. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.439
    Симпатии:
    1.744
    22 строка - прописывается имя. ЛЮБОЕ

    10 строка - указывается путь к файлу который отдавать.
     
  16. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.439
    Симпатии:
    1.744
    вот че я намутил когда-то на его основе
    Код (PHP):
    1. <?php
    2. class download {
    3.  
    4.   var $properties = array(
    5.           'old_name' => '',
    6.           'new_name' => '',
    7.           'type' => '',
    8.           'size' => '',
    9.           'resume' => '',
    10.           'max_speed' => ''
    11.   );
    12.  
    13.   var $range = 0;
    14.  
    15.   function download($path, $name='', $type='application/force-download', $resume=0, $max_speed=0) {
    16.  
    17.     $name = ($name == '') ? substr(strrchr("/".$path,"/"),1) : $name;
    18.  
    19.     $file_size = @filesize($path);
    20.  
    21.     $this->properties =  array(
    22.             'old_name' => $path,
    23.             'new_name' => $name,
    24.             'type'=> $type,
    25.             'size' => $file_size,
    26.             'resume' => $resume,
    27.             'max_speed' => $max_speed
    28.     );
    29.  
    30.     if ($this->properties['resume']) {
    31.  
    32.       if(isset($_SERVER['HTTP_RANGE'])) {
    33.  
    34.         $this->range = $_SERVER['HTTP_RANGE'];
    35.         $this->range = str_replace('bytes=', '', $this->range);
    36.         $this->range = str_replace('-', '', $this->range);
    37.  
    38.       } else {
    39.  
    40.         $this->range = 0;
    41.  
    42.       }
    43.  
    44.       if ($this->range > $this->properties['size']) $this->range = 0;
    45.  
    46.     } else {
    47.  
    48.       $this->range = 0;
    49.  
    50.     }
    51.  
    52.   }
    53.  
    54.  
    55.   function download_file() {
    56.  
    57.     if ($this->range) {
    58.       header($_SERVER['SERVER_PROTOCOL'].' 206 Partial Content');
    59.     } else {
    60.       header($_SERVER['SERVER_PROTOCOL'].' 200 OK');
    61.     }
    62.     header('Pragma: public');
    63.     header('Expires: 0');
    64.     header('Cache-Control:');
    65.     header('Cache-Control: public');
    66.     header('Content-Description: File Transfer');
    67.     header('Content-Type: '.$this->properties["type"]);
    68.     header('Content-Disposition: attachment; filename="'.$this->properties['new_name'].'";');
    69.     header('Content-Transfer-Encoding: binary');
    70.  
    71.     if ($this->properties['resume']) header('Accept-Ranges: bytes');
    72.  
    73.     if ($this->range) {
    74.  
    75.       header("Content-Range: bytes {$this->range}-".($this->properties['size']-1)."/".$this->properties['size']);
    76.       header("Content-Length: ".($this->properties['size']-$this->range));
    77.  
    78.  
    79.     } else {
    80.  
    81.       header("Content-Length: ".$this->properties['size']);
    82.  
    83.     }
    84.  
    85.     @ini_set('max_execution_time', 0);
    86.     @set_time_limit();
    87.     return $this->_download($this->properties['old_name'], $this->range);
    88.   }
    89.  
    90.   function _download ($filename, $range=0) {
    91.     @ob_end_clean();
    92.  
    93.     if (($speed = $this->properties['max_speed']) > 0)
    94.       $sleep_time = (8 / $speed) * 1e6;
    95.     else
    96.       $sleep_time = 0;
    97.  
    98.     $handle = fopen($filename, 'rb');
    99.     fseek($handle,$range);
    100.  
    101.     if ($handle === false) {
    102.       return false;
    103.     }
    104.     //ob_flush();
    105.     while (!feof($handle)) {
    106.       print (fread($handle, 1024*8));
    107.       flush();
    108.       usleep($sleep_time);
    109.     }
    110.     fclose($handle);
    111.     return true;
    112.   }
    113. }
    114.  
    115.  
    116.  
    вызывается так:
    Код (PHP):
    1. <?php
    2. $a = new download('ПУТЬ К ФАЙЛУ КОТОРЫЙ ХОЧЕШЬ ОТДАТЬ', 'ИМЯ ПОД КОТОРЫМ ЕГО УВИДИТ ПОЛЬЗОВАТЕЛЬ', 'это тебе пока рано. Оставь как везде application/force-download', true);
    3. if ($a->download_file()) {
    4.         if ($result = $db_filer->query("UPDATE `files` SET `downloads`=`downloads`+1, `date`=`date` WHERE ляляля пупупу ну ты понял это счетчик скачиваний'")) {
    5.           //updated
    6.         }
    7.       } 
     
  17. amen

    amen Активный пользователь

    С нами с:
    18 сен 2009
    Сообщения:
    298
    Симпатии:
    0
    Адрес:
    Узбекистан
    igordata, спасибо, буду разбираться.
     
  18. Mr. T

    Mr. T Активный пользователь

    С нами с:
    10 ноя 2010
    Сообщения:
    733
    Симпатии:
    0
    Адрес:
    Украина, г. Киев
    А если пользователь уже качает файл, как его поругать?
     
  19. WildZero

    WildZero Активный пользователь

    С нами с:
    24 фев 2010
    Сообщения:
    242
    Симпатии:
    0
    Адрес:
    Пермь
    Возник такой вопрос. Хотел бы ограничить количество одновременных скачиваний файла. Вроде всё просто: перед отдачей поле download_now обновляю на +1, после завершения на -1. Но если пользователь прекращает скачивание последнего update не происходит. и соответствено поле download_now не уменьшается. Как можно бороться с этим?
     
  20. Apple

    Apple Активный пользователь

    С нами с:
    13 янв 2007
    Сообщения:
    4.984
    Симпатии:
    2
    WildZero
    register_shutdown_function
     
  21. Slovoblydie

    Slovoblydie Активный пользователь

    С нами с:
    18 авг 2010
    Сообщения:
    8
    Симпатии:
    0
    Адрес:
    Москва
    люди.. сориенттируйте чайника...

    по этому посту : http://www.php.ru/forum/viewtopic.php?p=101398#101398 создал страничку .. туда же положил нужный файл.. страничка называтся index.php .. директория /test/ .. соответственно .. когда в браузер втыкаем линк : http://www.site.co/test/ .. открывается окошко загрузки указанного файла.. как бы всё так и должно быть...

    не могу въехать ..как к этому коду прикрутить шифрованный путь ..к примеру имя папки test шифровать с помощью md5 .. чтобы линк на файл получился такой: http://www.site.co/d54f5fg4erg4/
    как-то так..
     
  22. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.439
    Симпатии:
    1.744
    без БД никак. Дешифровка md5 займет месяцы, результат может не соответствовать действительности :D

    надо в бд писать это дело. я тут на днях изобрел забавный алгоритм для именования файлов при загрузке на сервер. вот он. Даю как есть, соответственно потерев лишнее можете приспособить под свои нужды.
    Код (PHP):
    1. <?php
    2.  
    3. class Files {
    4.  
    5.   private static
    6.   $unifid_counter = -1,
    7.   $unifid_rand = false;
    8.  
    9.   public static function unifid() {
    10.     /*
    11.      * функция использует 26 символов алфавита + 10 цифр чтобы создать уникальное имя файла в хранилище.
    12.      *
    13.      * За основу берется текущее время. Уникальность содержимого файлов не имеет значения.
    14.      * Пример: li76ww-onjw-0h
    15.      * $part1 = base_convert(time(), 10, 36); //Перевод текущего времени в 36-ти ричный формат: 6 символов. должно хватить на ближайшую четверть века.
    16.      * $part3 = substr('00' . base_convert(self::$unifid_counter, 10, 36), -2); //счетчик файлов в текущем экземпляре скрипта
    17.      *
    18.      */
    19.     if (self::$unifid_rand === false) {
    20.       self::$unifid_rand = substr('0000' . base_convert(rand(0, 1679615), 10, 36), -4); //один рандом на все вызовы функции в этом экземпляре скрипта.
    21.     }
    22.     ++self::$unifid_counter;
    23.     return base_convert(time(), 10, 36) . '-' . self::$unifid_rand . '-' . substr('00' . base_convert(self::$unifid_counter, 10, 36), -2);
    24.   }
    25.  
    26.   static public function AddNew($order, $work, $filename, $source, $mime) {
    27.     /*
    28.      *  id    int
    29.      *  unifid    varchar(16)
    30.      *  date    datetime
    31.      *  order    int
    32.      *  name    varchar(255)
    33.      *  mime    varchar(255)
    34.      */
    35.     $unifid = self::unifid();
    36.     $copyto = $_SERVER['DOCUMENT_ROOT'] . '/files/'.$unifid;
    37.     if (move_uploaded_file($source, $copyto) === true) {
    38.       //удачно скопирован файл, можно заносить запись в БД
    39.       $query = "
    40.         INSERT INTO `files` (`id`, `unifid`, `date`, `deleted`, `order`, `work`, `name`, `mime` )
    41.         VALUES ( NULL, '$unifid', NOW(), NULL, '$order', '$work', '".DB::escape($filename)."', '".DB::escape($mime)."');";
    42.       if ($id = DB::id($query)) {
    43.         //удачно скопирован, и запись помещена в БД
    44.         return $id;
    45.       }
    46.     }
    47.     //запись о файле не был помещена в БД. Файл необходимо удалить. Извесить администратора.
    48.     @unlink($copyto);
    49.     Engine::logit("ERROR: не удалось поместить запись о новом файле в БД. Файл будет удален.(Заказ: $order, файл: $filename, загружен в: $source).");
    50.     return false;
    51.   }
    52.  
    53. }
    54.  
    55. ?>
     
  23. Slovoblydie

    Slovoblydie Активный пользователь

    С нами с:
    18 авг 2010
    Сообщения:
    8
    Симпатии:
    0
    Адрес:
    Москва
    так у тебя для загрузки ..а не уже хранящегося файла...
     
  24. tommyangelo

    tommyangelo Старожил

    С нами с:
    6 дек 2009
    Сообщения:
    2.549
    Симпатии:
    0
    Адрес:
    Мариуполь
    чувак, у тебя в БД хранится таблица с соответствием

    Придуманный GUID <=> Реальный путь

    Задача сводится к
    0) Создать такую таблицу

    1) Принять из запроса GUID
    2) Найти соответствующий ему файл
    3) Отдать файл

    Вперде :)
     
  25. Slovoblydie

    Slovoblydie Активный пользователь

    С нами с:
    18 авг 2010
    Сообщения:
    8
    Симпатии:
    0
    Адрес:
    Москва
    да чувак я тебя понял -)))

    вопрос в следующем.. положим есть таблица.. где айди.. айпи.. время сервера.. к примеру я шифрую по айпи адресу...

    правильная реализация пункта 1 и 3 с учетом того что человеку придет на почту письмо с ссылкой на файл.. ????