Garden Preview Part III: Anatomy of a Request

mod_rewrite was an afterthought in Vanilla 1. As a result, markosullivan.ca have always felt that the mod_rewrite mappings were sloppy and really just didn’t make much sense. In Garden, the way pages are accessed is completely different, and definitely deserves explaining. Let’s start by looking at a typical url request in Garden without mod_rewrite enabled:

http://localhost/garden/default.php/garden/settings/configure

Let’s look closer at each part of the request:

http://localhost/garden/default.php: On my development server, I’ve created a folder called garden, and placed all of the garden files I discussed in last week’s preview in it. As you can see, the default.php file that handles all requests is sitting within that folder’s root.

/garden: The next part of the url is the application that is being requested. In this case, we are requesting the “garden” application within the garden framework’s application folder.

/settings: The next part of the url is the controller that is being requested within the garden application. In this example, we are requesting a controller called “Settings”.

/configure: the final part of the url in this example is the method within the “Settings” controller that we are calling. In this example, we are calling $SettingsController->Configure();.

I could take the same request and add information to the end, like this:

http://localhost/garden/default.php/garden/settings/configure/arg1/arg2/argn

And it would take any other parameters after the controller’s configure method as if they are arguments being passed into that method. In other words, the above request would be essentially the same as calling that method like so:

$SettingsController->Configure('arg1', 'arg2', 'argn');

This can get pretty handy when doing things like paging through records, or specifying which user to load in a page. For example, to edit a user, the url would be:

http://localhost/garden/default.php/garden/user/edit/mark

Which would map to:

$UserController->Edit('mark');

Analyzing the Request
All requests are handled through the Dispatcher class. The dispatcher class looks at the request (everything after default.php) and tries to figure out the best way to handle it. As far as the dispatcher is concerned, in a perfect world the request would always include the application name, the controller name, and the method name. But in reality you might not always want all three items in your url. For example, you might want your application invisible to the user – so that, for example, a request to vanilla’s discussion list goes to

http://yourwebsite.com/default.php/discussions/all

… instead of …

http://yourwebsite.com/default.php/vanilla/discussions/all

Furthermore, you might want your controller’s method hidden as well. So you could end up with something like:

http://yourwebsite.com/default.php/discussions

The dispatcher can handle all of these and a lot more. First of all, when no method is defined in the request, the dispatcher assumes that you are calling the “index” method of the controller. So, a request to:

http://yourwebsite.com/default.php/vanilla/discussions

… is the same as calling …

$DiscussionsController->Index();

Furthermore, when the dispatcher gets a request that doesn’t include the application name, it starts to look through all of the enabled applications for the requested controller name. As soon as it finds one, it records it’s mapping in the cache folder and calls it appropriately. There is the possibility that two different applications could have the same controller name, and in that case, it would return the first application’s controller that it found.

Probably the nicest thing about this method of handling requests is that a 6-line .htaccess file:

<IfModule mod_rewrite.c>
   RewriteEngine On
   RewriteCond %{REQUEST_FILENAME} !-d
   RewriteCond %{REQUEST_FILENAME} !-f
   RewriteRule ^(.*)$ default.php/$1 [QSA,L]
</IfModule>

… allows you to remove the default.php from the url and makes all requests look like this:

http://yourdomain.com/application/controller/method

Or, in it’s simplest form:

http://yourdomain.com/controller

Next
In the next garden preview, I’ll be getting into how controllers work, how views are found and rendered, and how master views can let you customize layouts between applications and themes.

Leave a comment