View Full Version : [PHP] ignore_user_abort() & register_shutdown_function() QUANDO USARLI?
SimoneLucca
19-02-2004, 09:50
Cosa fanno di preciso queste due funzioni?
Quando devono essere usate?
E' possibile intercettate l'utente che chiude la finestra del browser?
Simo, ti consiglio di usare il timeout come ti avevo scritto tempo fa... Anche le sessioni usano il timeout...
register_shutdown_function serve per far sì che una funzione php venga eseguita quando l'elaborazione della pagina è stata completata (anche dopo che il buffer di output viene inviato all'utente)...
Con ignore_user_abort puoi settare se interrompere o meno l'esecuzione dello script in caso di disconnessione da parte del client (quando ad esempio il client chiude il browser oppure quando viene arrestato il caricamento)...
http://it.php.net/manual/it/features.connection-handling.php
SimoneLucca
19-02-2004, 11:00
ma il problema è che voglio che ci stia loggato al massimo un utente alla vosta con lo stesso nome...
lo blocco al login e lo sblocco al logout.
se l'utente non fa il logout e chiude il browser.... deve aspettare che scada la sessione.
E' ragionevole questo?
Che tempi metteresti di scadenza?
Conta che se deve scarica' un file grosso ed è con una connesione lenta, alla fine deve riconnettersi tutte le volte...
Con ignore_user_abort puoi settare se interrompere o meno l'esecuzione dello script in caso di disconnessione da parte del client (quando ad esempio il client chiude il browser oppure quando viene arrestato il caricamento)...
e se ilcliente chiude il borwser dopo che la pagina è stata caricata tutta?
mettere ignore_user_abort(0) cosa implica?
Non implica niente perchè la sessione TCP è già stata chiusa... In pratica non te ne accorgi se lo chiudi dopo che è finito il download della pagina...
Per i downlaod puoi gestirteli a mano (questo può evitare anche che ti linkino i downlaod da fuori)...e così alla fine setti come data e ora dell'ultima operazione, ogni tot minuti, durante il downlaod...così eviti che scada al sessione...
Per gestirteli a mano intendo: settare il mime-type e dare in output il file richiesto leggendolo da disco a pacchetti (che so, di 10Kb)... Puoi usare fopen e fread come nel C....
SimoneLucca
19-02-2004, 11:30
download a mano...
ma non potevo proteggere i file da scaricare in una cartella protetta?
sii più preciso in merito al download "a mano"...
Cos'è un download ?
Quando richiedi il download l'output del server, oltre agli header standard, aggiunge il mime-type del file che si vuole scaricareè fatto così (ad esempio per uno zip):
Content-Type: application/zip
E dopo i dati binari...
Una cosa del genere dovrebbe andere bene:
header("Content-Type: application/zip");
ob_implicit_flush(); //invia l'output immediatamente al browser
$fp = fopen ("pippo.zip", "r");
if(!$fp)
exit("errore nell'apertura del file");
while(!feof($fp)) {
if($tempo_attuale >= $tempo_salvato + $20minuti)
aggiorna_ultima_operazione_database($tempo_attuale);
echo fread($fp, 10240); //legge 10Kb alla volta e li da in output
}
SimoneLucca
19-02-2004, 11:56
ok, grazie!
Ho provato e c'è ancora qualcosa da rielaborare... Comunque la strada è quella...
Ho risolto qualcosa, metti il file di prova in una directory e chiamalo index.php:
<?php
ob_implicit_flush(); //invia l'output immediatamente al browser
$fp = fopen ("I:/Downloads/adstudio-novm1.zip", "rb");
if(!$fp)
exit("errore nell'apertura del file");
header("Content-Length: ".filesize("I:/Downloads/adstudio-novm1.zip"));
header("Content-Type: application/zip");
while(!feof($fp)) {
sleep(1); //ho messo una pausa per simulare un canale di trasmissione
echo fread($fp, 10240); //legge 10Kb alla volta e li da in output
}
?>
Il fiel che apre ora è fisso (ma per provare va benissimo)...
Apri il link in questo modo: http://127.0.0.1/dire/?pippo.zip...
In questo modo IE riceve il file con l'estensione giusta, ma il nome è sbagliato (prende quello della dir)...
Comunque credo che si possa risolvere il problema con mod_rewrite di Apache (devo ancora guardarmelo)...
Ho risolto quasi andando a caso...
Allora le mdoifiche da fare in httpd.conf sono queste:
Caricare mod_proxy e mod_rewrite (magari ho caricato anche qualche modulo in più, non ho avuto tempo di provare)...
LoadModule proxy_module modules/mod_proxy.so
LoadModule proxy_connect_module modules/mod_proxy_connect.so
LoadModule proxy_http_module modules/mod_proxy_http.so
#LoadModule proxy_ftp_module modules/mod_proxy_ftp.so
LoadModule rewrite_module modules/mod_rewrite.so
Impostare il prxy per accettare solametne connessioni dal localhost...
<IfModule mod_proxy.c>
ProxyRequests On
<Proxy *>
Order deny,allow
Deny from all
Allow from 127.0.0.1
</Proxy>
#
# Enable/disable the handling of HTTP/1.1 "Via:" headers.
# ("Full" adds the server version; "Block" removes all outgoing Via: headers)
# Set to one of: Off | On | Full | Block
#
#ProxyVia On
#
# To enable the cache as well, edit and uncomment the following lines:
# (no cacheing without CacheRoot)
#
#CacheRoot "H:/Programmi/Apache Group/Apache2/proxy"
#CacheSize 5
#CacheGcInterval 4
#CacheMaxExpire 24
#CacheLastModifiedFactor 0.1
#CacheDefaultExpire 1
#NoCache a-domain.com another-domain.edu joes.garage-sale.com
</IfModule>
Impostare nel VirtualHost interessato o a livello globale questa regola del mod_rewrite:
RewriteEngine on
RewriteRule ^/pippo/(.*) /download.php?file=$1 [P]
/pippo è una directory inesistente !!!
download.php è di questo tipo:
<?php
ob_implicit_flush(); //invia l'output immediatamente al browser
$fp = fopen ("I:/Downloads/".$_GET["file"], "rb");
if(!$fp)
exit("errore nell'apertura del file");
header("Content-Length: ".filesize("I:/Downloads/".$_GET["file"]));
header("Connection: close");
header("Content-Type: application/zip");
while(!feof($fp)) {
sleep(1); //ho messo una pausa per simulare un canale di trasmissione
echo fread($fp, 10240); //legge 10Kb alla volta e li da in output
}
?>
L'esempio ovviamente non controlla il parametro (va controllato che non venga messo alcuno / nel nome del file) ;)
In pratica la richiesta passa tramite il proxy... Ho provato con IE e funziona... La devo verificare anche con altri browser...
L'unico problema è che se il download supera i 30 secondi si ferma (basta allungare il timout dello script, dopo guardo)...
SimoneLucca
19-02-2004, 14:00
ma io non posso modificare http.conf del server che mi ospita....
P.S. (mandami una foto della "bimba"... la voglio vedere....;) )
SimoneLucca
19-02-2004, 14:02
ma non posso mettere i file sensibili in dir protette del server?
Ah cacchio, non ci avevo epnsato che non potevi modificarlo... Anche se credo che (a parte il md_proxy) tu possa fare tutto con un file .htaccess da mettere nello spazio web...
Comunque ormai termino dicendo: scrivendo http://server/pippo/nomefile.zip si crede di scaricare un file direttamente dal server ed invece siamo noi farlo scaricare tramite PHP ;)
<?php
ob_implicit_flush(); //invia l'output immediatamente al browser
$fp = fopen ("I:/Downloads/".$_GET["file"], "rb");
if(!$fp)
exit("errore nell'apertura del file");
header("Content-Length: ".filesize("I:/Downloads/".$_GET["file"]));
header("Connection: close");
header("Content-Type: application/zip");
while(!feof($fp) && !connection_aborted()) {
set_time_limit(20);
sleep(1); //ho messo una pausa per simulare un canale di trasmissione
echo fread($fp, 10240); //legge 10Kb alla volta e li da in output
}
?>
Mettere i file su una directory protetta ti porta comunque ad avere problemi... Il client conosce username e password del file in fase di download...quindi potenzialmente è linkabile esternamente...
Insomma, la soluzione è vicina...e probabilmente è in mod_rewrite (che credo sia solitamente attivo)... Ora bisogna scoprire come fare scaricare il file con il nome giusto...
SimoneLucca
19-02-2004, 14:51
sto mettendo un sito in rete sotto serverplan.
offrono dei servizi tra cui:
http://www.serverplan.com/tutorial/
1) protezione con pass di cartella (.HTACCESS)
2) abilitare protezione hotlink....
ho visto i tutorials, che ne dici?
il mio sito starà la.
Originariamente inviato da SimoneLucca
sto mettendo un sito in rete sotto serverplan.
offrono dei servizi tra cui:
http://www.serverplan.com/tutorial/
1) protezione con pass di cartella (.HTACCESS)
Questo serve a poco...perchè chi accede deve comunque avere username e password...
Originariamente inviato da SimoneLucca
2) abilitare protezione hotlink....
Anche questa serve a poco... Basta costruirsi una richiesta HTTP con un campo referer tra quelli nella lista e ti fa scaricare...
Quindi secondo me devi cercare di trovare una soluzione simile a quella sopra... Ricordati che con quella sopra puoi impedire che scada la sessione nel DB... Con questi modi non puoi impedirlo...
SimoneLucca
19-02-2004, 15:09
come mai dici con .HTACCESS non posso proteggere una cartella?
La puoi proteggere, ma username e password devi darli (in qualche modo) al client... E chi scarica di fatto può linkare il file in questo modo:
http://username:password@tuosito/nomedownload.zip
SimoneLucca
19-02-2004, 15:23
non posso darli io da script? in questo modo l'utente che si è precedentemente autenticato non deve fare nulla... e chi non si è autenticato, non può accedere...
Sì...le puoi dare, ma transitano comunque da server a client e poi di nuovo da client a server...
<?php
ob_implicit_flush(); //invia l'output immediatamente al browser
$fp = fopen ("I:/Downloads/".$_GET["file"], "rb");
if(!$fp)
exit("errore nell'apertura del file");
header("Expires: Mon, 26 Jul 2001 05:00:00 GMT");
header("Last-Modified: " . gmdate("D, d M Y H:i:s") . " GMT");
header("Cache-Control: no-store, no-cache, must-revalidate");
header("Cache-Control: post-check=0, pre-check=0", false);
header("Pragma: no-cache");
header("Cache-control: private");
header("Connection: close");
header("Content-Type: application/zip");
while(!feof($fp) && !connection_aborted()) {
set_time_limit(20);
sleep(1); //ho messo una pausa per simulare un canale di trasmissione
echo fread($fp, 10240); //legge 10Kb alla volta e li da in output
}
?>
Ora basta che tu chieda se è attivo il mod rewrite e con queste due righe nel file .htaccess puoi far salvare con il nome giusto:
RewriteEngine on
RewriteRule ^/download/(.*) /download.php?file=$1 [PT]
Digitando http://tuoserver/download/pippo.zip sarà come chiamare http://tuoserver/download.php?file=pippo.zip e scarichi il file controllandolo tramite download.php ;)
SimoneLucca
19-02-2004, 15:42
torniamo alla base:
io ho, per ogni utente che si logga, una cartella a cui solo lui (più l'amministratore) può accedere per scaricare i files.
voglio fare in modo che i permessi per scaricare i files da quella cartella siano dati dallo script (nomeutente.php).
voglio anche evitare che lo script che contiene i dati della connessione con i database sia leggibile (da uno script malizioso che mi legge il contenuto e mi stampa).
Come posso implementare questo marchingegno?
voglio, chiaramente, evitare che uno da fuori faccia:
www.miosito.com/cartellautente/file.zip e che lo scarichi.
è fattibile?
SimoneLucca
19-02-2004, 15:58
ho fatto:
http://199.232.160.15/~simonest/protetta/user_on_line.zip
e mi chiede la password e l'username?
dove possono stare i problemi di sicurezza?
come posso passare user e pass da script?
se metto il sito in SSL non passano criptate le informazioni?
Passano criptate, ma chi ci accede anche solo una volta ha la password e può linkare i file esternamente nel formato che ho scritto prima, semi fai un cartella di prova ed un file di prova te lo faccio vedere...e poi ti si ripresenterebbe comunque il problema della sessione sul DB che ti scade ;)
Originariamente inviato da SimoneLucca
voglio, chiaramente, evitare che uno da fuori faccia:
www.miosito.com/cartellautente/file.zip e che lo scarichi.
è fattibile?
Questo, con uno script come quello sopra lo fai tranquillamente...
Con una cartella protetta da password quando un client accede c'è la possibilità di salvare username e password...e quindi linkare il file dall'esterno...
SimoneLucca
19-02-2004, 16:33
la sessione sul db che scade non è un grosso problema rispetto alla sicurezza...
e se mettessi queste info in una cartella fuori dalla document root?
SimoneLucca
19-02-2004, 16:36
io ho esposto il problema al supporto dove ho il sito e mi hanno detto:
http://forum.serverplan.com/viewtopic.php?p=2809#2809
che ne dici?
Sinceramente preferisco l'autentificazione su DB rispetto a quella di Apache... Lo script che ti ha consigliato serve per gestire gli utenti nel file .htpasswd, ma non per fare l'autentificaizone...
L'autentificazione tramite script PHP (con i dettagli di cui abbiamo parlato tempo fa) può essere ben più sicura di quella tramite Apache... Ripeto...l'autotentificazione tramite Apache può essere rubata semplicemente copiando il link da IE o andando a vedere nella history ;) L'utentificazione tramite PHP è un po' più difficile...
Chiedigli se hanno mod_rewrite abilitato...
vBulletin® v3.6.4, Copyright ©2000-2025, Jelsoft Enterprises Ltd.