Как узнать сколько раз скачали файл?

26.06.2010

Теги: MySQLPHPWeb-разработкаФайл

Допустим, у вас на сайте есть раздел Downloads, где посетитель может скачать скрипты, музыку, фотографии и т.п. Но как узнать, какие файлы пользуются успехом, а какие лежат мертвым грузом (и их можно безболезненно удалить, чтобы не занимали место)? Выход — счетчик скачиваний. Обычно этот счетчик устанавливается рядом со ссылкой на скачиваемый документ:

<a href="/downloads/download.php?id=178">NotePadPP.zip</a>, скачали 57 раз(а)

Пусть информация о файлах для скачивания у нас хранится в таблице базы данных, которая имеет следующую структуру:

CREATE TABLE `files` (
  `id` INT(10) PRIMARY KEY,
  `title` VARCHAR(255) NOT NULL DEFAULT '',
  `description` TEXT NOT NULL DEFAULT '',
  `filename` VARCHAR(64) NOT NULL DEFAULT '',
  `mimetype` VARCHAR(8) NOT NULL DEFAULT ''
) ENGINE=INNODB DEFAULT CHARSET=cp1251;

Здесь

  • id — уникальный ID файла
  • title — название файла, например, «Текстовой редактор NotePad++»
  • description — описание файла, например, «Бесплатный редактор текстовых файлов с поддержкой синтаксиса большого количества языков программирования, ориентирован для работы в операционной системе MS Windows»
  • filename — имя файла для скачивания, например, NotePadPP.zip
  • mimetype — MIME-тип файла

Файлы для скачивания расположены в директории DOCUMENT_ROOT/downloads/files/. Эта директория защищена с помощью .htaccess, чтобы посетитель не мог скачать файл напрямую, минуя наш счетчик:

Order Allow,Deny
Deny from All

Файл DOCUMENT_ROOT/downloads/index.php выводит список всех файлов, доступных для скачивания, а файл DOCUMENT_ROOT/downloads/download.php отдает файлы на скачивание и подсчитывает количество скачиваний.

Файл DOCUMENT_ROOT/downloads/index.php

<?php
$query = "SELECT `id`, `title`, `description`, `mimetype` FROM `files` WHERE 1 ORDER BY `title`";
$res = mysql_query( $query );
echo '<table border="1">'."\n";
echo '<tr><th>№</th><th>Наименование</th><th>Описание</th><th>Тип</th><th>Скачать</th></tr>'."\n";
$i = 1;
while ($file = mysql_fetch_array($res)) {
  echo '<tr>';
  echo '<td>'.$i.'</td>';
  echo '<td>'.$file['title'].'</td>';
  echo '<td>'.$file['description'].'</td>';
  echo '<td>'.$file['mimetype'].'</td>';
  echo '<td><a href="/downloads/download.php?id='.$row['id'].'" target="_blank">Скачать</a></td>';
  echo '</tr>'."\n";
  $i++;
}
echo '</table>'."\n";

Файл DOCUMENT_ROOT/downloads/download.php

<?php
if ( !isset( $_GET['id'] ) ) {
  // если не передан ID файла
  header ("HTTP/1.0 404 Not Found");
  die();
}
$id = (int)$_GET['id'];
if ( $id < 1 ) {
  header ("HTTP/1.0 404 Not Found");
  die();
}
// имя файла для скачивания
$query = "SELECT `filename`, `mimetype` FROM `files` WHERE `id`=".$id;
$res = mysql_query( $query );
if( mysql_num_rows( $res ) == 0 ) {
  header ( 'HTTP/1.1 404 Not Found' );
  die();
}
list( $filename, $mimetype ) = mysql_fetch_row( $res );
// если файла нет
if( !file_exists( './files/'.$filename ) ) {
  header ( 'HTTP/1.1 404 Not Found' );
  die();
}
// сообщаем размер файла
header( 'Content-Length: '.filesize('./files/'.$filename) );
// дата модификации файла для кеширования
header( 'Last-Modified: '.date("D, d M Y H:i:s T", filemtime('./files/'.$filename)) );
// сообщаем тип данных
switch( $mimetype ) {
  case 'pdf' : $ctype = 'application/pdf'; break;
  case 'zip' : $ctype = 'application/zip'; break;
  case 'doc' : $ctype = 'application/msword'; break;
  case 'xls' : $ctype = 'application/vnd.ms-excel'; break;
  case 'gif' : $ctype = 'image/gif'; break;
  case 'png' : $ctype = 'image/png'; break;
  case 'jpeg':
  case 'jpg' : $ctype = 'image/jpg'; break;
  case 'mp3' : $ctype = 'audio/mpeg'; break;
  case 'wav' : $ctype = 'audio/x-wav'; break;
  case 'mpeg':
  case 'mpg' :
  case 'mpe' : $ctype = 'video/mpeg'; break;
  case 'mov' : $ctype = 'video/quicktime'; break;
  case 'avi' : $ctype = 'video/x-msvideo'; break;
  default    : $ctype = 'application/octet-stream';
}
header( 'Content-Type: '.$ctype );
// файл будет получен с именем $filename
header('Content-Disposition: attachment; filename="'.$filename.'"');
// начинаем передачу содержимого файла
readfile( './files/'.$filename );

// увеличиваем счетчик количества закачек
mysql_query( "UPDATE `files` SET `count`=`count`+1 WHERE `id`=".$id );

Поиск: MySQL • PHP • Web-разработка • Файл

Каталог оборудования
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.
Производители
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.
Функциональные группы
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.