As Web applications become more and more complex, cleverdevelopers can use application-level caching to improve the performanceof their PHP scripts. This article shows you how, discussing the PEARCache_Lite class with examples that illustrate how it can be used in alive environment.
It's also possible to use the Cache_Lite object to cache certain sections of a page, rather than the entire page - useful if some parts of the page are updated more frequently than others. This is accomplished by specifying a different cache identifier for each block of data that is to be cached, and using these different identifiers to retrieve data when needed. Data that is not to be cached (that is, data that is to be retrieved from source every time it is needed) will simply not be included in the call to the Cache_Lite object's save() method.
Consider the following example, which demonstrates:
<?php
// include the class
require_once('Lite.php');
// initalize the cache for 24 hours
$objCache = new Cache_Lite( array("cacheDir" => "cache/",
"lifeTime" =>
86400) );
// open connection to database
$connection = mysql_connect("localhost", "joe", "secret")
or die ("Unable to connect!");
mysql_select_db("db111") or die ("Unable to select database!");
// first data block
if ($data = $objCache->get("featured_quote"))
{
// retrieve the header from the cache, if available
// display cached data
echo $data;
}
else
{
// else query database for it, and also store it in cache
// formulate and execute query
$query = "SELECT quote FROM quotes ORDER BY RAND() LIMIT 1";
$result = mysql_query($query) or die("Error in query: " . mysql_error());
// get record
$row = mysql_fetch_object($result);
// display it
echo $row->quote;
// and also cache it
$objCache->save($row->quote, "featured_quote");
}
// //
// dynamic, non-cacheable page content goes here //
// //
// second data block
// test if there is a valid cache for this block
if ($data = $objCache->get("featured_character"))
{
// if so, display it
echo $data;
}
else
{
// formulate and execute query
$query = "SELECT char FROM characters ORDER BY RAND() LIMIT 1";
$result = mysql_query($query) or die("Error in query: " . mysql_error());
In this case, the code for the header and footer blocks is cached; however, the data in between the two is not. Note the use of two different cache identifiers in this example, one for each block.
{mospagebreak title=Of Form And Function}
Just as you can cache HTML markup and PHP command output, it's also possible to cache the output of user-defined functions with the Cache_Lite class...or, more precisely, with the Cache_Lite_Function subclass. This subclass inherits all the methods and properties of the parent Cache_Lite class, and adds an additional one: the call() method, which is used to save the return value of a PHP function to the cache.
Using the Cache_Lite_Function object's call() method is simplicity itself: the methods accepts the name of the function to be cached as its first argument, and input parameters to that function as additional arguments. It then first checks the cache to see if the function has been cached previously. If it has, the previous return value is retrieved without actually executing the function; if it has not, the function is executed (with appropriate arguments) and the result returned to the caller and simultaneously saved to the cache for future use.
Here's a simple example which demonstrates how this works:
<?php
// returns the current time
function get_time()
{
return date("H:i:s", mktime());
}
// include the class
require_once('Function.php');
// configure the cache
$options = array(
'cacheDir' => 'cache/',
'lifeTime' => 600
);
// create an instance of the Cache_Lite_Function
// object $objCache = new Cache_Lite_Function($options);
// cache the call to the get_time() function
// if return value is present in cache,
// Cache_Lite_Function will fetch it from the cache
// else the function will be called and the result returned $time = $objCache->call('get_time');
echo "The cached time is " . $time . ". The real time is "
. get_time();
?>
And here's an example of the output:
The cached time is 13:08:50. The real time is 13:11:40
As you might imagine, this class has the potential to do much more than simply confuse users in search of the time. Flip the page to see what I mean.