Monthly Archives: April 2007

Evolving Framework, Step 4: Handle requests with a request handler

So, picking up from where I left off in Step 3, cleaning up the server-side, we’ve now got a simple HTML form that sends a clean request into the server, and a nice little Request class to make the incoming data easy to work with. To jog your memory, the form looks like:

<form action="/session" method="post">
  <input type="hidden" name="method" value="put" />
  Username: <input type="text" name="username" /><br />  
  Password: <input type="password" name="password" /><br />  
  <input type="submit" value="Login..." />  
</form>

When the form gets submitted, index.php creates a new Request object to encapsulate all the request data. But once the Request is all set up, then what? My goal here is to log the user into their account, or if I read the HTTP request the way I intended it to be interpreted, I want to:

Create a session on the server with the specified username and password.

Well, the most straightforward way to do this would be to just stick all the input-sanitizing, database-connecting, user-authenticating logic directly after the Request object is born, making index.php look something like this:

<?php
    include 'Request.php';
 
    /**
     * create the request
     */
    $req = new Request();
 
    /**
     * pull the necessary data out of the request
     * i.e., 
     *  username=drew&password=qwerty
     *
     * In real life, error checking and validation would be a good idea here
     */
    $username = $req->params['username'];
    $password = $req->params['password'];
 
    /** 
     * Connect to the db and see if the username/password combo is valid
     * I like mysqli: http://www.php.net/mysqli
     */
    $db = new MySQLi('localhost', 'dbuser', 'securepassword', 'dbname');
 
    $sql = 'SELECT UserID FROM Users WHERE Username = ? AND Password = MD5(?)';
    if ($stmt = $db->prepare($sql))
    {
        $stmt->bind_param('ss', $username, $password);
        $stmt->execute();
        $stmt->bind_result($userID);
        $stmt->fetch();
 
        if ($userID == 0) {
            die("access denied, try again.");
        } else {
            die("access granted! userid: $userid");
        }
    }
 

Hopefully it is obvious to you that putting all that code smack in the middle of the site’s one-and-only index.php would suck really badly. Afterall, index.php has to handle every single request. The only reasonable way to go about this is to have some sort of dynamically loaded request-examining code. I’ll have to decide on some standard way to look at every request, and depending on the method, path, and parameters, load up some request-specific logic on the fly. Something to this affect:

<?php
 
    include 'Request.php';
    include 'RequestHandler.php';
 
    $request = new Request();
 
    /**
     * Create this magical object that "handles" the given $request object
     */
    $handler = new RequestHandler($request);
 
    /**
     * Tell the RequestHandler to do the dirty work
     */
    $handler->run();
 

This would get the clutter out of index.php and into the RequestHandler object. Of course, the RequestHandler is a black box at this point, but the idea is to use that class in such a way as to load up and run the request-specific logic, i.e., form validation, database querying, and of course output.

Step 5 will consider what exactly the RequestHandler needs to do, and how we might need to modify our currently bare-bones index.php bootstrap.