etzel42 has asked for the wisdom of the Perl Monks concerning the following question:

I have a download manger that allows visitors a certen number of times they can download a file. My question is this, is there a way to detect that they have actually downloaded a file rather than just attemped to download the file? (In other words, when the download completed it counts as a download rather than when they click on the download link it counts as a download.)

I am using a basic this method to send the files to the browser:

$currnet_count++; open(FILE2, "$file") or die "Can't open $file: $!\n"; print "Content-Type: application/unknown\n"; print "Content-Disposition: attachment; filename=$filename\n"; print "Content-Length: $filesize\n\n"; while (<FILE2>) { print; } close(FILE2);

Perhaps there is way to read how many bytes are sent and compare it to the file size. But then if a download had been ended for any reason the bytes would not total right. So maybe a way to determind if it is the last byte.

Replies are listed 'Best First'.
Re: download attempted vs completed
by clinton (Priest) on Mar 22, 2006 at 18:51 UTC
    I haven't tried it myself, but it looks like you can use mod_perl2 with Apache 2 to trap a timeout error.

    mod_perl docs : APR::Error

    edited Also have a look at Apache2::RequestIO->sendfile which you can use to send a file, and it returns a status code or throws an exception.

    good luck

Re: download attempted vs completed
by codeacrobat (Chaplain) on Mar 22, 2006 at 17:59 UTC
    My quick shot is using syswrite.

    syswrite FILEHANDLE,SCALAR ... Returns the number of bytes actually written, or "undef" if there was an error (in this case the errno variable $! is also set).

    Counting the bytes send should go like this:
    ... while(<FILE2>){ $count += syswrite STDOUT, $_ } ...

      syswrite seems to be the best answer, only I have never used this before. I have looked into it, but seems a bit complicated to use. Also if I got this working, how would I go about finding out how much a user has already downloaded on a partial download?

      It seems to me that if I could find out the partial download then it would work great. Otherwise I would not know what they have already downloaded and thus not be able to set the offset and would not be able to count the download when it finished, as I would not know it was finished.

      There must a way to just find out when a download completes. Using a eof like statement or something.

Re: download attempted vs completed
by jdtoronto (Prior) on Mar 22, 2006 at 18:09 UTC
    I think the answer is no.

    HTTP is stateless, you can feed anything you like into the HTTP 'pipe', but you have no idea what is accepted out of the other end. If something times out, or data is corrupted, then you have no way of knowing this.

    jdtoronto

Re: download attempted vs completed
by superfrink (Curate) on Mar 22, 2006 at 17:55 UTC
    In the past I have updated a SQL database after close(FILE2); to say "user X has downloaded file Y".

    You will probably also have to look into how HTTP can download files from part way through. It's been a long time since I dealt with it. Maybe google for things like "HTTP partial download" or read the HTTP RFC.