Some very old PHP code originally intended to become an image management tool.
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

595 lines
15 KiB

<?php
/**
* Mit der Funktion printCachedPage kann ein Script/Modul seinen dynamisch
* erzeugten HTML-Inhalt cachen und als statisches HTML einbinden. Die
* erzeugten HTML-Dateien liegen unter CACHEDIR/<subclientid>/<script-path>/
* <scriptname>?md5(<request-parameter-liste>).html
*
* Es wird für jede Seite und jeden Request-Parameter-Kombination, der in
* $allowed_req_params angegeben ist, eine Seite im Cache angelegt.
*
* Parameter:
* - $auto_update: erzeugt bei Scriptaufruf eine neue Cache-Datei, wenn:
* a) die Cachedatei älter ist als die Scriptdatei oder
* b) die Cachedatei älter ist als eine per include/require eingebunden
* Scriptdatei
* - $update_interval: eine Erneuerung der Cachedatei wird vorgenommen, wenn
* die Cachedatei älter als $update_interval ist.
* - $script-file: das Script, dessen Inhalt gecached werden soll, i.d.R
* __FILE__
* - $allowed_req_params: Liste der erlaubten Request-Parameter, dient zur
* Bildung des Cachedateinamens
* - $debug: erzeugt Debug-Ausgaben
*
* Die Einbindung in ein Script erfolgt nach Einbindung per include/require
* der zusätzlich erforderlichen Bibliothen mit:
*
* if (printCachedPage($auto_update,$update_interval,__FILE__))
* return;
*
* Der mit printCachedPage erzeugte HTML-Bereich wird mit HTML-Kommentaren
* umrandet und kann so im Gesamt-Quelltext identifiziert werden.
*/
define ('MAX_CACHE_WAIT_SECS',1);
function printCachedPage (
$script_file,
$auto_update = true,
$update_interval = 86400,
$allowed_req_params = -1,
$debug = 0)
{
if (USE_SCRIPT_CACHE == 0)
return 0;
$em_parameter = "";
if (isset ($_REQUEST["em_parameter"]))
$em_parameter = $_REQUEST["em_parameter"];
if (!empty($em_parameter))
$GLOBALS["em_parameter"] = $em_parameter;
if (!empty($GLOBALS["em_parameter"]))
$em_parameter = $GLOBALS["em_parameter"];
$content = "";
if (isset($_REQUEST["NOCACHE"]))
{
if (isset($_REQUEST["PHP_SELF"]))
{
$_SERVER["PHP_SELF"]=$_REQUEST["PHP_SELF"];
// --- DEBUG OUTPUT -------
if ($debug)
echo "<br />PHP_SELF wurde gesetzt: " . $_SERVER["PHP_SELF"];
// --- END DEBUG OUTPUT ---
}
return 0;
}
// --- DEBUG OUTPUT -------
$t1 = NULL;
if ($debug)
$t1 = getMilliSeconds ();
if ($debug)
{
echo "<br />Startzeit: ".strftime("%H:%M:%S");
echo "<br />Script-Datei: ".$script_file;
echo "<br />PHP_SELF: ".$_SERVER["PHP_SELF"];
echo "<br />Erlaubte Cache-Dateien pro Verzeichnis: " .
MAX_FILES_IN_CACHE_DIR;
}
// --- END DEBUG OUTPUT ---
$subclient_id = getSubclientIDByUrl();
$len = strlen ($_SERVER["DOCUMENT_ROOT"]);
$script_name = substr ($script_file, $len);
// --- DEBUG OUTPUT -------
if ($debug)
echo "<br>DOCUMENT ROOT: " . $_SERVER["DOCUMENT_ROOT"];
if ($debug)
echo "<br />Script-Name: $script_name";
// --- END DEBUG OUTPUT ---
$cache_file = realpath (CACHEDIR) . "/" . $subclient_id . "/" .
substr(dirname($script_name),1) . "/" . basename($script_name) . "/" .
basename($script_name,".php");
$params = "";
$query_string = "";
foreach ($_REQUEST as $key => $val)
{
if (is_array ($allowed_req_params) &&
in_array ($key,$allowed_req_params))
{
$val = urlencode (trim($val));
$key = urlencode (trim($key));
// --- DEBUG OUTPUT -------
if ($debug)
echo "<br />Hänge Request-Parameter an: _$key-$val";
// --- END DEBUG OUTPUT ---
$params .= "_". $key . "-" . $val;
$query_string .= $key . "=" . $val . "&";
}
}
if (!empty ($em_parameter))
{
$params .= "_" . $em_parameter;
$query_string .= "em_parameter=" . $em_parameter;
}
if (!empty ($params))
$cache_file = $cache_file . "_" . md5($params) . ".html";
else
$cache_file = $cache_file . ".html";
$url = getProtocol () . "://" . $_SERVER["SERVER_NAME"] . $script_name .
"?" . $query_string;
$cached_dir = dirname($cache_file);
// --- DEBUG OUTPUT -------
if ($debug)
{
echo "<br />Cache-Datei: $cache_file";
echo "<br />Script-Datei: $script_file";
echo "<br />URL: ".htmlspecialchars($url);
echo "<br />Cache Dir: $cached_dir";
}
// --- END DEBUG OUTPUT ---
if (!is_dir ($cached_dir))
{
if (!is_dir (CACHEDIR . $subclient_id))
mkdir (CACHEDIR . $subclient_id);
$cachedir = CACHEDIR . $subclient_id;
$dir_arr = explode ("/", dirname($script_name) . "/" .
basename($script_name));
foreach ($dir_arr as $dir)
{
if (!is_dir($cachedir . "/" . $dir))
{
mkdir ($cachedir. "/" . $dir);
chmod ($cachedir. "/" . $dir, 0777);
// --- DEBUG OUTPUT -------
if ($debug)
echo "<br />Erzeuge Verzeichnis: $cachedir/$dir";
// --- END DEBUG OUTPUT ---
}
$cachedir .= "/" . $dir;
}
}
$is_updated = 0;
if (!file_exists ($cache_file))
{
$file_count = count (scandir ($cached_dir)) - 2;
// --- DEBUG OUTPUT -------
if ($debug)
echo "<br />Es sind $file_count im Cacheverzeichnis. " .
"Erlaubt sind " . MAX_FILES_IN_CACHE_DIR. ".";
// --- END DEBUG OUTPUT ---
if ($file_count <= MAX_FILES_IN_CACHE_DIR)
{
$content = makeCacheFile ($cache_file, $url, $debug);
$is_updated = 1;
// --- DEBUG OUTPUT -------
if ($debug)
echo "<br />Cache-Datei wurde erzeugt, " .
"weil diese nicht existierte.";
// --- END DEBUG OUTPUT ---
}
else
{
// --- DEBUG OUTPUT -------
if ($debug)
{
echo "<br />Es sind mehr Dateien im Cacheverzeichnis als " .
"erlaubt: " . $file_count .
"<br />Die Seite kann daher nicht gecached werden.";
}
// --- END DEBUG OUTPUT ---
}
}
else
{
if ($auto_update)
{
$do_update=0;
if (filemtime($cache_file) < filemtime($script_file))
{
$do_update = 1;
// --- DEBUG OUTPUT -------
if ($debug)
echo "<br />Cache-Datei wird erzeugt, weil die Cache-Datei " .
"älter als die Script-Datei ist.";
// --- END DEBUG OUTPUT ---
}
else
{
$includes = get_included_files ();
foreach($includes as $inc)
{
if (strstr ($inc, realpath (HOME . "/../")))
{
// --- DEBUG OUTPUT -------
if ($debug)
echo "<br />Untersuche Abhängigkeiten von $inc";
// --- END DEBUG OUTPUT ---
if (filemtime($inc) > filemtime($cache_file))
{
$do_update=1;
// --- DEBUG OUTPUT -------
if ($debug)
echo "<br />Cache-Datei wird erzeugt, weil " .
$inc . "verändert wurde.";
// --- END DEBUG OUTPUT ---
break;
}
}
}
}
if (!$do_update)
{
$content = getCacheContent ($cache_file, $debug);
}
else
{
$content = makeCacheFile ($cache_file, $url, $debug);
$is_updated = 1;
// --- DEBUG OUTPUT -------
if ($debug)
echo "<br />Cache-Datei wurde erzeugt: Auto-Update";
// --- END DEBUG OUTPUT ---
}
}
if ($update_interval >= 10 && !$is_updated)
{
$diff = time() - filemtime($cache_file);
// --- DEBUG OUTPUT -------
if ($debug)
echo "<br />Noch " . $update_interval - $diff .
" Sekunden bis zum nächsten Interval-Update";
// --- END DEBUG OUTPUT ---
if ($diff > $update_interval)
{
$content = makeCacheFile($cache_file, $url, $debug);
$is_updated=1;
// --- DEBUG OUTPUT -------
if ($debug)
echo "<br />Cache-Datei wurde erzeugt: Interval-Update";
// --- END DEBUG OUTPUT ---
}
else
{
$content = getCacheContent($cache_file, $debug);
}
}
}
// --- DEBUG OUTPUT -------
if ($debug)
echo "<hr />";
// --- END DEBUG OUTPUT ---
if (!empty($content))
echo "\n<!-- Cache-Bereich Anfang: ".basename($script_name)." -->\n";
echo $content;
if (!empty($content))
echo "\n<!-- Cache-Bereich Ende: ".basename($script_name)." -->\n";
// --- DEBUG OUTPUT -------
if ($debug)
echo "<hr /><p />Gecachter Content wurde ausgeliefert.";
if ($debug)
echo "<br />Verarbeitungsdauer (in ms): ".(intval(getMilliSeconds()-$t1));
// --- END DEBUG OUTPUT ---
if (empty($content))
return 0;
else
return 1;
}
function makeCacheFile($cache_file, $url, $debug)
{
if (preg_match("/^http.*\?.*/",$url))
$url = $url."&NOCACHE=1&PHP_SELF=".urlencode($_SERVER["PHP_SELF"]);
else
$url = $url."?NOCACHE=1&PHP_SELF=".urlencode($_SERVER["PHP_SELF"]);
if ($debug)
echo "<br />Encoded URL: $url";
// --- DEBUG OUTPUT -------
$t1 = '';
if ($debug)
$t1=getMilliSeconds();
// --- END DEBUG OUTPUT ---
$content = file_get_contents($url);
// --- DEBUG OUTPUT -------
if ($debug)
echo "<br />Laden der Seite ohne Cache dauerte: " .
getMilliSeconds() - $t1 . " ms";
flush();
if ($debug)
{
echo "<br />Cache-Datei ist gesperrt: ";
var_dump (is_file ($cache_file.".LCK"));
}
// --- END DEBUG OUTPUT ---
$ctr = 0;
while (cacheFileIsLocked ($cache_file))
{
usleep (100000);
$ctr++;
if ($debug)
{
echo "<br />Cache-Datei ist gesperrt ...";
flush();
}
if ($ctr>(MAX_CACHE_WAIT_SECS*10))
return $content;
clearstatcache();
}
$is_locked = lockCacheFile($cache_file);
if ($is_locked)
{
$fp = fopen($cache_file, "w");
if ($fp)
{
fwrite($fp,$content);
// for ($x=0;$x<25;$x++)
// {
// echo "<br />Test sleep ... $x";
// flush();
// sleep(1);
// }
fclose($fp);
chmod($cache_file,0777);
}
} else
if ($debug)
echo "<br />Cache-Datei konnte nicht geschrieben werden, " .
"weil die Lock-Datei nicht gesperrt werden konnte";
if ($is_locked)
unlockCacheFile($cache_file);
return $content;
}
function lockCacheFile($cache_file)
{
$lock_file = $cache_file.".LCK";
if (is_file($lock_file))
{
if (is_writable($lock_file))
{
chmod($lock_file,0555);
clearstatcache();
return 1;
}
else
return 0;
} else
{
$fp = fopen($lock_file,'w');
if ($fp)
{
fclose($fp);
chmod($lock_file,0555);
clearstatcache();
return 1;
} else
return 0;
}
}
function unlockCacheFile($cache_file)
{
$lock_file = $cache_file.".LCK";
chmod($lock_file,0777);
if (is_file($lock_file))
{
unlink($lock_file);
clearstatcache();
}
}
function cacheFileIsLocked($cache_file)
{
$lock_file = $cache_file.".LCK";
$is_locked = is_file($lock_file);
if ($is_locked)
return 1;
return 0;
}
function getProtocol()
{
$proto = $_SERVER["SERVER_PROTOCOL"];
if (preg_match("/^HTTP\/.*$/",$proto))
return 'http';
if (preg_match("/^HTTPS\/.*$/",$proto))
return 'https';
}
function getCacheContent($cache_file, $debug)
{
$ctr = 0;
while (cacheFileIsLocked($cache_file))
{
usleep(100000);
$ctr++;
if ($debug)
{
echo "<br />Kann Content nicht ausliefern, da Cache-Datei gesperrt ist ...";
flush();
}
if ($ctr>(MAX_CACHE_WAIT_SECS*10))
return "";
clearstatcache();
}
return file_get_contents($cache_file);
}
function cleanupCache()
{
$log = "<h3>Cleanup Cache Script</h3>\n<ul>";
$def_vars = get_defined_constants();
if (!array_key_exists('CACHE_CLEANUP_TIME',$def_vars))
{
$log .= "<li>Konstante CACHE_CLEANUP_TIME ist nicht definiert - breche Cleanup-Skript ab.</li></ul>";
return $log;
} else if (!array_key_exists('CACHECLEANUPFILE',$def_vars))
{
$log .= "<li>Konstante CACHECLEANUPFILE ist nicht definiert - breche Cleanup-Skript ab.</li></ul>";
return $log;
} else
if (!preg_match("/^([0-9][0-9]:[0-9][0-9],{0,1})*$/",CACHE_CLEANUP_TIME))
{
$log .= "<li>Konstante CACHE_CLEANUP_TIME '".CACHE_CLEANUP_TIME."' ist im falschen Format - breche Cleanup-Skript ab.</li></ul>";
return $log;
}
$cachecleanup_file = CACHEDIR.CACHECLEANUPFILE;
$cleanup = 0;
$err_reporting = ini_get("error_reporting");
ini_set("error_reporting",0);
if (file_exists($cachecleanup_file))
{
$lastmodified = filemtime($cachecleanup_file);
$cachecleanup_file = realpath($cachecleanup_file);
$log .= "<li>Cache-Cleanup-Datei $cachecleanup_file existiert.</li>";
$log .= "<li>Cache-Cleanup-Datei $cachecleanup_file wurde letzmals aktualisiert am: ".strftime("%d.%m.%Y %H:%M:%S",$lastmodified)." Uhr</li>";
}
else
$lastmodified = -1;
$cleanuptime_arr = explode(",",CACHE_CLEANUP_TIME);
foreach($cleanuptime_arr as $cleanup_time)
{
$log .= "<li><b>Checke Cleanup-Time $cleanup_time Uhr</b><ul>";
$ct_arr = explode(":",$cleanup_time);
if (count($ct_arr)>=2)
{
$hour = $ct_arr[0];
$minute = $ct_arr[1];
$today = getdate();
$cleanup_timestamp = mktime($hour,$minute,0,$today["mon"],$today["mday"],$today["year"]);
$now = time();
$diff1 = $now-$cleanup_timestamp;
$log .= "<li>Untersuche Differenz: now()-$cleanup_time=$diff1 Sekunden</li>";
if ($diff1>0)
{
$log .= "<li>Cleanup-Zeitpunkt ist überschritten</li>";
if ($cleanup_timestamp>$lastmodified)
{
$cleanup=1;
$log .= "<li>Cleanup-Zeitpunkt muss durchgeführt werden.</li>";
} else
$log .= "<li>Kein Cleanup erforderlich, weil ".basename($cachecleanup_file)." nach der Cleanup-Zeit" .
" $cleanup_time Uhr verändert wurde.";
} else
$log .= "<li>Kein Cleanup erforderlich. Es dauert noch ".(-$diff1)." Sekunden bis zum nächsten Cleanup.</li>";
}
$log .= "</ul></li>";
}
if ($cleanup)
{
$log .= "<li><b>Führe jetzt Cleanup durch ...</b>";
$files = scandir(CACHEDIR);
foreach($files as $key=>$file)
{
if ($file=='.' ||
$file=='..' ||
$file=='.svn' ||
$file==LASTLOGFILE ||
$file==CACHECLEANUPFILE)
unset($files[$key]);
}
if (count($files)==0)
$log .= "<li>Cache ist leer.</li>";
foreach($files as $file)
{
$file = realpath(CACHEDIR.$file);
$success = 0;
if (is_file($file))
{
$log .= "<li>lösche Datei $file : ";
$success = unlink($file);
} else if (is_dir($file))
{
$log .= "<li>lösche Verzeichnis $file : ";
delTree($file);
if (!is_dir($file))
$success = 1;
}
if ($success)
$log .= " gelöscht.</li>";
else
$log .= " <b style=\"color:red\">Löschen fehlgeschlagen.</b></li>";
}
$fp = fopen($cachecleanup_file,"w");
fclose($fp);
}
$log .= "\n</ul>\nCleanup beendet.";
ini_set($err_reporting);
return $log;
}
function delTree($path) {
if (is_dir($path)) {
$entries = scandir($path);
foreach ($entries as $entry) {
if ($entry != '.' && $entry != '..') {
deltree($path.DIRECTORY_SEPARATOR.$entry);
}
}
rmdir($path);
} else {
unlink($path);
}
}
?>