File: gimmecache.php

Recommend this page to a friend!
  Classes of Sam Yapp  >  gimmeCache  >  gimmecache.php  >  Download  
File: gimmecache.php
Role: ???
Content type: text/plain
Description: The cache class file (include it in your scripts)
Class: gimmeCache
SImple to use but powerful caching class.
Author: By
Last change:
Date: 18 years ago
Size: 7,445 bytes
 

Contents

Class file image Download
<?php

/***********************************

	gimmecache.php 

	@ 2002 Sam Yapp www.samscripts.com

	You are free to use modify and do whatever you like with this script.

	Usage:

	***	To cache a whole page, ***

	near the top of your script, 

	include_once("gimmecache.php");

	$cache = new gimmecache("path/to/store/cached/files/in", 60);	// refresh cache after 60 seconds

	$cache->cache("a_unique_name_identifying_this_cache");


	*** To cache part of a script, ie. big database query ***

	include_once("gimmecache.php");

	$cache = new gimmecache("path/to/store/cached/files/in", date("Y-m-d 00:00:00"));	// refresh cache once a day

	if( $cache->cache("a_unique_name_identifying_this_cache")){		// cache() returns true if the code needs to be refreshed

		// all the code you want to cache goes here, eg.

		$result = mysql_query($really_big_and_slow_query);

		while( list( $f1, $f2, $f3, $f4) = mysql_fetch_row($result)){
			echo "Field1 $f1, Field2 $f2, Field3 $f3, Field4 $f4<br>\n";
		}

		$cache->stop();	// finish caching this bit of code
	}
	
	// The sql query and output of the data will only occur the first time each day that the script is requested.
	// the output is stored in the cache and is output to the browser as html which for a big query will be faster.

	*** To remove a cached file - sometimes you may need to refresh a script the next time it is called, but not this time ***

	$cache->expirecache($cache_identifier);

	*** to replace one or more strings in the cached output before outputting it to the web browser

	$cache->cache($cachepath, $expirytime, $search = array("firstvalue", "secondvalue"), array("firstreplacement", "secondreplacement"));

	// error checking: the variable $_THE_CACHE_ERRORS is an array containing text descriptions of any errors. It will be empty if no errors occur

************************************/

// you can change these:

$_DEFAULT_CACHE_PATH = "./cached";	// path to store cached files in - must be php writable
$_USE_DATABASE = "";		// enter the database table name here to use db instead of files - see below

/*******************************

if you want to cache to a mysql database, enter the name of the table
in $_USE_DATABASE above.

the database should have the following structure:

CREATE TABLE cached (
  id varchar(32) NOT NULL default '',
  updated datetime NOT NULL default '0000-00-00 00:00:00',
  file text NOT NULL,
  PRIMARY KEY  (id)
)

at present, this class simply calls mysql_query($sql) - ie it assumes that you
have already opened a database connection with mysql_connect and mysql_select_db
elsewhere in the script.

if $_USE_DATABASE = "" then files will be used for caching. (quicker, in most cases ? )

******************************/

// do NOT change the names of these - unless you change them throughout the script

$_THE_CACHE_FILENAME = array();	// global variable holds filenames of cached files
$_THE_CACHE_ERRORS = array();		// store any error messages generated
$_THE_CACHE_EXISTS = array();
$_THE_CACHE_REPLACE = array();

class gimmecache{

	var $cachepath;
	var $expireafter;
	var $expiretype;
	var $filename;
	var $connection;
	var $usedb;

	function setexpiry($expireafter = 60){		// sets either the number of seconds before re-caching or a date-string after which to expire the cache
		$this->expireafter = $expireafter;
		if( is_int($expireafter) ){
			$this->expiretype = "sec";
		}else{
			$this->expiretype = "date";
		}
	}

	function gimmecache( $cachepath = "", $expireafter = 60, $connection = 0){	// cachepath is where cached files will be stored
		global $_DEFAULT_CACHE_PATH;
		global $_USE_DATABASE;
		if( $_USE_DATABASE != "" ){
			$this->usedb = $_USE_DATABASE;
			$this->connection = $connection;
		}else{
			$this->usedb = false;
		}
		$this->cachepath = ($cachepath == "" ? $_DEFAULT_CACHE_PATH : $cachepath);
		$this->setexpiry($expireafter);
		$this->filename = "";
	}

	function expirecache($cachename){
			$filename = $this->cachepath."/".md5($cachename).".cache";
			@unlink($filename);
	}

	function cache($cachename, $expireafter = "", $search = array(), $replace=array()){
		$this->cachename = $cachename;
		if( $expireafter == "" ) $expireafter = $this->expireafter;
		$this->setexpiry($expireafter);

		$update = 0;
		if( $this->usedb ){
			$filename = md5($cachename);
			$res = @mysql_query("SELECT updated, file FROM ".$this->usedb." WHERE id='".$filename."'")or die(mysql_error());
			if( mysql_num_rows($res) == 0 ){
				$update = 1;
				$exist = 0;
			}else{
				list( $updated, $f) = mysql_fetch_row($res);
				$updated = strtotime($updated);
				$exist = 1;
			}
		}else{
			$filename = $this->cachepath."/".md5($cachename).".cache";
			if( !file_exists($filename) ){
				$update = 1;
				$exist = 0;
			}else{
				$exist = 1;
				$updated = filemtime($filename);
			}
		}

		if( $exist ==0 || $updated < ($this->expiretype == "sec" ? time() - $this->expireafter : strtotime($this->expireafter))){
			$update = 1;
		}

		if( $update){ 
			ob_start( "_the_cache_capture");
			global $_THE_CACHE_FILENAME;
			global $_THE_CACHE_EXISTS;
			global $_THE_CACHE_REPLACE;
			$_THE_CACHE_FILENAME[] = $filename;
			$_THE_CACHE_EXISTS[] = $exist;
			$countcache = count( $_THE_CACHE_REPLACE);
			$_THE_CACHE_REPLACE[$countcache]["search"] = $search;
			$_THE_CACHE_REPLACE[$countcache]["replace"] = $replace;
			return true;
		}else{
			global $_THE_CACHED_ERRORS;
			if( $this->usedb ){
				echo str_replace($search, $replace, $f);
			}else{
				if( count($search) == 0 ){
					if( !@readfile( $filename)) $_THE_CACHE_ERRORS = "readfile failed for ".$this->filename;
				}else{
					$f = join("", file($filename));
					echo str_replace($search, $replace, $f);
				}
			}
			return false;
		}
	}

	function stop($returnbuffer = false){		// if returnbuffer is true, returns the contents of the cache to the calling script
		if( $returnbuffer ){
			$ret = ob_get_contents();
		}else{
			$ret = "";
		}
		ob_end_flush();
		return $ret;
	}

}

function _the_cache_capture(&$output){
	global $_THE_CACHE_FILENAME;
	global $_THE_CACHE_ERRORS;
	global $_THE_CACHE_EXISTS;
	global $_THE_CACHE_REPLACE;
	global $_USE_DATABASE;

	$numcaches = count($_THE_CACHE_FILENAME);
	if( $numcaches != 0 ){
		$filename = $_THE_CACHE_FILENAME[$numcaches-1];
		if( $_USE_DATABASE != "" ){
			if( $_THE_CACHE_EXISTS[$numcaches-1] == 1 ){
				$sql = "UPDATE cached SET updated=now(), file='".addslashes($output)."' WHERE id='".$filename."'";
			}else{
				$sql = "INSERT INTO cached (id, updated, file) VALUES ('".$filename."', now(), '".addslashes($output)."')";
			}
			@mysql_query($sql);
		}else{
			$fo = @fopen($filename, "w");
			if( $fo ){
				if( !@fwrite( $fo, $output)) $_THE_CACHE_ERRORS[] = "Error writing to file $filename.";
				@fclose( fo);
			}else{
				$_THE_CACHE_ERRORS[] = "Failed opening file $filename for output.";
			}
		}
		array_pop($_THE_CACHE_FILENAME);
	}else{
		$_THE_CACHE_ERRORS[] = "No active caches.";
	}
	if( count( $_THE_CACHE_REPLACE[$numcaches-1]["search"]) != 0 ){
		$result = str_replace($_THE_CACHE_REPLACE[$numcaches-1]["search"], $_THE_CACHE_REPLACE[$numcaches-1]["replace"], &$output);
	}else{
		$result = &$output;
	}
	return $result;
}

?>

For more information send a message to info at phpclasses dot org.