Bit Fracture
Bit Fracture

Reputation: 717

How can I make my PHP controlled downloader stop repeating downloads for IP addresses?

I have a simple download page that receives a file URL, download counter .TXT file url, and a redirect link for after the download. This is all sent through PHP arguments. Problem is, someone has been spamming the downloaders and messing up the count. I want to put a cap on the download counter so it will only count 3 hits from each address, per downloadable item.

I need to be able to do this with only PHP, and without a MySQL database. I do have reasoning for this, my database server is trash and unreliable, I can't have the counter going down.

This is my current downloader PHP file. Further information, this PHP file is in its own folder at /counter with a /counter/data directory for each download counting TXT file. These files store just a single integer value.

<?
    //Retrieve downloadable file URL
    $c_url = urldecode($_GET['url']);

    //retrieve redirect page URL
    $c_page = urldecode($_GET['page']);

    //Retrieve download counter TXT URL
    $c_file = "../" . $_GET['file'];
?>

<!-- Set up simple styles -->
<head>
    <style type="text/css">
        body{
            background: url("../images/background.png");
            color: #ffffff;
        }
    </style>
</head>

<!-- Creates download file URL in hidden iFrame -->
<iframe src="<?echo $c_url;?>" id="hiddenFrm" style="display:none;" frameborder="0"></iframe>

<body>
<center>
    <h1>Your download is starting</h1><br>
    <p>You should be redirected momentarily...<br>

    <?
    <br><br>

    if (file_exists($c_file))
    {
        //Add one value to the counter file
        file_put_contents($c_file, ((int) file_get_contents($c_file)) + 1);

        //Set an automatic redirect for the page (Return home)
        ?>
        <meta http-equiv="refresh" content="0;url=<?echo $c_page;?>" />
        <?

        //Display information about the download, and alternate exits to the page
        if ($c_url != "") 
        {?>
            <b><a href="<?echo $c_url?>">Click here</a> if the download did not start.<br><br>
            <a href="<?echo $c_page?>">Click here</a> if this page does not close after your download.</b></p>
        <?} 
        else 
        {
        ?>
            <b><a href="<?echo $c_page?>">Click here</a> if you are not redirected automatically</b></p>
        <?
        }
    }
    else
    {
        //In case our counter file is improperly specified
        echo "<br><br><br>Error, the counter file was not found!";
    }
    ?>
    </center>
</body>

My question simplified: How can I store IP addresses of people who download each product and prevent the download counter from counting more than 3 downloads from that address using only PHP and no databases?

Help is much appreciated.

EDIT: As I said above, I can't use databases. Also, I am interested in two solutions but not sure how to make them work (I am looking for code examples), one being cookies, and the other being text-files acting as databases.

Upvotes: 2

Views: 622

Answers (3)

kdazzle
kdazzle

Reputation: 4300

I would use Memcache. You can see PHP's docs here: http://php.net/manual/en/book.memcache.php

You can use a string of the IP address as the key, and then on each download request, you would attempt to do a $memcache->get($key). If that doesn't exist, you would do a $memcache->set($key, $downloadCount). If the key does exist, you would increment the downloadCount.

Upvotes: 1

Explosion Pills
Explosion Pills

Reputation: 191789

Without using any database at all it would be pretty tough. I'd be surprised if you can't use MySQL at all, but maybe something even simpler like SQLite might work. Other than that there are two solutions I can think of: the file system and cookies.

The problem with cookies are that they are transient, and if you have bots spamming you they will probably reject the cookie setting anyway.

What you can do is maintain a file of

IP    download-count    last-download-time

If the file is small enough you can load it into memory with file and search for the IP address with preg_grep and update the count that way.

Note that IP Address may not be the best bet either because some valid and invalid users may share mobile routers and IP Addresses can potentially be spoofed by use of a proxy, etc. Your best bet would be some sort of user authentication system, but that would be prohibitively difficult without a DB

Upvotes: 2

Jaakko Kaski
Jaakko Kaski

Reputation: 72

The data has to be stored somewhere since PHP always 'starts from the scratch'. How about a text file to represent the database?

Upvotes: 0

Related Questions