Detecting an AJAX request in PHP

After going through this recipe you will be able to distinguish between AJAX requests and simple HTTP requests in your PHP code.

Getting ready

Create a new directory named Recipe3 in the chapter2 directory. Inside it create an HTML file named index.html and another PHP file check.php.

How to do it...

  1. Open the index.html file and create a button that will load a string from a PHP file using the $.get() method.
    <html>
      <head>
        <title>Detecting AJAX Requests</title>
      </head>
      <body>
        <form>
          <p>
            <input type="button" value="Load Some data"/>
          </p>
        </form>
      </body>
    </html>
  2. Next, include jQuery and write the code for a click event of the button. Clicking on the button will simply send an AJAX request to check.php, which will return a string. The response string will be appended to the page after the input button.
    <script type="text/javascript" src="../jquery.js"></script>
    <script type="text/javascript">
      $(document).ready(function ()
      {
        $('input:button').click(function()
        {
          $.get(
            'check.php', 
            function(data)
            {
              $('input:button').after(data);
            });
        });
      });
    </script>
  3. To validate that the request is indeed an AJAX request and not a direct one from the browser, open the check.php file and write the following code:
    <?php
      if(isset($_SERVER['HTTP_X_REQUESTED_WITH']) &&  $_SERVER['HTTP_X_REQUESTED_WITH'] == 'XMLHttpRequest')
      {
        echo 'YaY!!! Request successful.';
      }
      else
      {
        echo 'This is not an AJAX request. This page cannot be accessed directly.';
      }
    ?>
  4. Run the index.html file in a browser and click on the Load Some Data button. You will see the text YaY!!! Request successful. inserted after the button. Now in another window enter the direct path to the check.php file. You will see the following message:

    This is not an AJAX request. This page cannot be accessed directly.

How it works...

Browsers send HTTP headers with every request that goes to a server. To distinguish between normal requests and AJAX requests, modern libraries send an additional header with AJAX request. The header's name is X-Requested-With and its value is XMLHttpRequest.

Superglobal $_SERVER contains the headers sent with the request. In the example, we have checked whether the $_SERVER array has an entry for the HTTP_X_REQUESTED_WITH key or not. If an entry is found and its value is XMLHttpRequest, we can assume it is an AJAX request. Depending upon the result of the if expression we display the resulting string to the user.

There's more...

Don't rely on X-Requested-With alone

jQuery and most of the other modern libraries (such as Prototype and Dojo) send an X-Requested-With header for the ease of the server. However, relying on this header alone is not recommended.

This is due to the reason that HTTP headers can be easily spoofed. So a user can send a request with this header that the code will assume to be an AJAX request but that won't be.

There are other ways through which you can ensure the request is legitimate but that is beyond the scope of this book.