Pomoc - Szukaj - Użytkownicy - Kalendarz
Pełna wersja: Licznik downloadu
Forum PHP.pl > Forum > Przedszkole
php programmer
Mam coś takiego.

<A href="plik.zip">Plik do ściągnięcia</A>

Poniważ elementem docelowym nie jest strona tylko plik,
więc nie moge sobie tak po prostu zrobić licznika,
A chciałbym wiedzieć ile osób zapisało (zrobiło download na swój dysk)
dany plik z mojego serwera. Jak to zrobić questionmark.gifquestionmark.gif
bregovic
  1. <a href="download.php?file=plik.zip">plik</a>


  1. <?php
  2.  
  3. //wpisz informacje:
  4. mysql_query(&#092;"update downloads set downloaded=downloaded+1 where file='\".$_GET['file'].\"';\");
  5.  
  6. header('Content-type: '.mime_content_type($_GET['file']));
  7. header('Content-Disposition: attachment; filename=\"'.$_GET['file'].'\"');
  8. readfile($_GET['file']);
  9.  
  10. ?>
zYm3N
/etc/passwd ?

/cfg/config.inc

?

czy to jest aby bezpieczne ?
bregovic
zYm3N: Ja mu nie podałem stuprocentowego rozwiazania, tylko szkic. Zreszta dosc latwo jest zabezpieczyc ten skrypt. Wystarczy np tak:
  1. <?php
  2. $_GET['file'] = 'download/'.$_GET['file'];
  3. if(is_file($_GET['file']) && strpos($_GET['file'], '..') != false)
  4. {
  5. //wpisz informacje:
  6. mysql_query(&#092;"update downloads set downloaded=downloaded+1 where file='\".$_GET['file'].\"';\");
  7.  
  8. header('Content-type: '.mime_content_type($_GET['file']));
  9. header('Content-Disposition: attachment; filename=\"'.$_GET['file'].'\"');
  10. readfile($_GET['file']);
  11. }
  12. else
  13. {
  14. print 'Prawdopodobna próba ataku!';
  15. }
  16. ?>
zYm3N
tak, ale dział to "początkujący" i należy zakładać, że kolega raczej nie interesował się zabezpieczaniem swoich skryptów :-)

if(is_file($_GET['file']) && strpos($_GET['file'], '..') != false)

A jeśli nazwa wygląda:

to_jest_nazwa_pliku..jpg

bo uzytkownikowi się pomyliło ? :-)

To nie jest najlepszy pomysł. Lepiej dać regularne.

strpos($_GET['file'], '..') != false

strpos
strpos -- Find position of first occurrence of a string

Czyli, że jeżeli w ciągu jest '..' to wynikiem będzie true, a true!=false jest prawdą, czyli że wejdzie ? hm ;-)

Albo ja coś mylę, albo Ty się pomyliłeś :-)
bregovic
Masz rację, pomyliło mi się winksmiley.jpg
Powinno oczywiście być:
  1. <?php
  2. $_GET['file'] = 'download/'.$_GET['file'];
  3. if(is_file($_GET['file']) && strpos($_GET['file'], '..') != true)
  4. {
  5. //wpisz informacje:
  6. mysql_query(&#092;"update downloads set downloaded=downloaded+1 where file='\".$_GET['file'].\"';\");
  7.  
  8. header('Content-type: '.mime_content_type($_GET['file']));
  9. header('Content-Disposition: attachment; filename=\"'.$_GET['file'].'\"');
  10. readfile($_GET['file']);
  11. }
  12. else
  13. {
  14. print 'Prawdopodobna próba ataku!';
  15. }
  16. ?>


Imo zdecydowanie nie ma żadnego sensu dawać regularnych. Tylko kretyn używa w nazwie swojego pliku dwóch kropek '..' - a zastartowanie silnika wyrażeń regularnych żeby pomóc kretynom, to imo zły pomysł...
zYm3N
a jeśli to jest część skryptu za pomocą którego można ściągać pliki dostępne na serwerze po uprzednim wysłaniu ich ? :-)

Wiesz, laski czesto mają pliki w stylu:

"pamiętnik...txt"

Jakoś połowicznie sprawne rozwiązania nie przekonywują mnie :-)

Na miejscu autora wątku założyłbym sobie tabele w bazie danych. Nawet dwie :-)

Jedna, to pliki: id -> nazwa
Druga to: id_pliku -> id pierwszej + wszystkie ciekawe informacje wyświetlane przy okazji phpinfo(); Dzięki temu zrobienie w przyszłości statystyk to rzecz prosta i przyjemna :-)

A to, że teraz tego nie wykorzysta.. no dobra, ale statsy pójdą :-))

pzodr.
bregovic
Zaraz, php programmer zapytał się, cytuje:
Cytat
chciałbym wiedzieć ile osób zapisało (zrobiło download na swój dysk)
dany plik z mojego serwera

Nikt nie ma szansy wiedzieć czy on używa tego systemu jako coś większego, czy tylko jako standalone... Oczywiscie, jeśli to ma być część CMSa lub Frameworka, to jasne, dla każdego pliku powinien być rekord w bazie danych, i wtedy wystarczy zamiast nazwy pliku dać identyfikator...
Np tak:
  1. <?php
  2. //wpisz informacje:
  3.  
  4. //ładujemy odpowiedni rekord
  5. $arrFileData = mysql_fetch_array(mysql_query(&#092;"select * from files where file_id='\".$_GET['file'].\"'\"));
  6.  
  7. //sprawdzamy czy plik istnieje
  8. if(is_file($arrFileData['file_fullpath']))
  9. {
  10. //updatujemy statystyki
  11. mysql_query(&#092;"update downloads set downloaded=downloaded+1 where file_id='\".$_GET['file'].\"';\");
  12.  
  13. //wysyłamy mime
  14. header('Content-type: '.mime_content_type($arrFileData['file_fullpath']));
  15.  
  16. //wysyłamy prośbę o zapisanie pliku na dysku
  17. header('Content-Disposition: attachment; filename=\"'.$arrFileData['file_name'].'\"');
  18.  
  19. //wysyłamy zawartość pliku
  20. readfile($arrFileData['file_fullpath']);
  21. }
  22. else
  23. {
  24. print 'Plik nie istnieje!';
  25. }
  26. ?>
To jest wersja lo-fi głównej zawartości. Aby zobaczyć pełną wersję z większą zawartością, obrazkami i formatowaniem proszę kliknij tutaj.
Invision Power Board © 2001-2025 Invision Power Services, Inc.