1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33: 34: 35: 36: 37: 38: 39: 40: 41: 42: 43: 44: 45: 46: 47: 48: 49: 50: 51: 52: 53: 54: 55: 56: 57: 58: 59: 60: 61: 62: 63: 64: 65: 66: 67: 68: 69: 70: 71: 72: 73: 74: 75: 76: 77: 78: 79: 80: 81: 82: 83: 84: 85: 86: 87: 88: 89: 90: 91: 92: 93: 94: 95: 96: 97: 98: 99: 100: 101: 102: 103: 104: 105: 106: 107: 108: 109: 110: 111: 112: 113: 114: 115: 116: 117: 118: 119: 120: 121: 122: 123: 124: 125: 126: 127: 128: 129: 130: 131: 132: 133: 134: 135: 136:
<?php
/**
* "Rewrite" handling for Zenphoto
*
* The basic rules are found in the zenphoto-rewrite.txt file. Additional rules can be provided by plugins. But
* for the plugin to load in time for the rules to be seen it must be either a CLASS_PLUGIN or a FEATURE_PLUGIN.
* Plugins add rules by inserting them into the $_zp_conf_vars['special_pages'] array. Each "rule" is an array
* of three elements: <var>define</var>, <var>rewrite</var>, and (optionally) <var>rule</rule>.
*
* Elemments which have a <var>define</var> and no <var>rule</rule> are processed by rewrite rules in the
* zenphoto-rewrite.txt file and the <var>define</var> is used internally to Zenphoto to reference
* the rewrite text when building links.
*
* Elements with a <var>rule</rule> defined are processed after Search, Pages, and News rewrite rules and before
* Image and album rewrite rules. The tag %REWRITE% in the rule is replaced with the <var>rewrite</var> text
* before processing the rule. Thus <var>rewrite</var> is the token that should appear in the acutal URL.
*
* It makes no sense to have an element without either a <var>define</var> or a <var>rule</rule> as nothing will happen.
*
* At present all rules are presumed to to stop processing the rule set. Historically that is what all our rules have done, but I suppose
* we could change that. The "R" flag may be used to cause a <var>header</var> status to be sent. However, we do not redirect
* back to index.php, so the "R" flag is only useful if the target is a different script.
*
* @package admin
*/
function rewriteHandler() {
global $_zp_conf_vars, $_zp_rewritten;
$_zp_rewritten = false;
$definitions = array();
// query parameters should already be loaded into the $_GET and $_REQUEST arrays, so we discard them here
$request = explode('?', getRequestURI());
//rewrite base
$requesturi = ltrim(substr($request[0], strlen(WEBPATH)), '/');
list($definitions, $rules) = getRules();
//process the rules
foreach ($rules as $rule) {
if ($rule = trim($rule)) {
if ($rule[0] != '#') {
if (preg_match('~^rewriterule~i', $rule)) {
// it is a rewrite rule, see if it is applicable
$rule = strtr($rule, $definitions);
preg_match('~^rewriterule\s+(.*?)\s+(.*?)\s*\[(.*)\]$~i', $rule, $matches);
if (array_key_exists(1, $matches)) {
if (preg_match('~' . $matches[1] . '~', $requesturi, $subs)) {
$params = array();
// setup the rule replacement values
foreach ($subs as $key => $sub) {
$params['$' . $key] = urlencode($sub); // parse_str is going to decode the string!
}
// parse rewrite rule flags
$flags = array();
$banner = explode(',', strtoupper($matches[3]));
foreach ($banner as $flag) {
$flag = strtoupper(trim($flag));
$f = explode('=', $flag);
$flags[trim($f[0])] = isset($f[1]) ? trim($f[1]) : NULL;
}
if (!array_key_exists('QSA', $flags)) {
// QSA means merge the query parameters. Otherwise we clear them
$_REQUEST = array_diff($_REQUEST, $_GET);
$_GET = array();
}
preg_match('~(.*?)\?(.*)~', $matches[2], $action);
if (empty($action)) {
$action[1] = $matches[2];
}
if (array_key_exists(2, $action)) {
// process the rules replacements
$query = strtr($action[2], $params);
parse_str($query, $gets);
$_GET = array_merge($_GET, $gets);
$_REQUEST = array_merge($_REQUEST, $gets);
}
// we will execute the index.php script in due course. But if the rule
// action takes us elsewhere we will have to re-direct to that script.
if (isset($action[1]) && $action[1] != 'index.php') {
$qs = http_build_query($_GET);
if ($qs) {
$qs = '?' . $qs;
}
if (array_key_exists('R', $flags)) {
header('Status: ' . $flags['R']);
}
redirectURL(FULLWEBPATH . '/' . $action[1] . $qs);
}
$_zp_rewritten = true;
break;
}
} else {
zp_error(sprintf(gettext('Error processing rewrite rule: ā%sā'), trim(preg_replace('~^rewriterule~i', '', $rule))), E_USER_WARNING);
}
} else {
if (preg_match('~define\s+(.*?)\s*\=\>\s*(.*)$~i', $rule, $matches)) {
// store definitions
eval('$definitions[$matches[1]] = ' . $matches[2] . ';');
}
}
}
}
}
}
function getRules() {
global $_zp_conf_vars;
// load rewrite rules
$rules = trim(file_get_contents(SERVERPATH . '/' . ZENFOLDER . '/zenphoto-rewrite.txt'));
$definitions = $specialPageRules = array();
foreach ($_zp_conf_vars['special_pages'] as $special) {
if (array_key_exists('rule', $special)) {
$specialPageRules[] = "\tRewriteRule " . str_replace('%REWRITE%', $special['rewrite'], $special['rule']);
}
if (array_key_exists('definition', $special)) {
eval('$definitions[$special[\'definition\']] = ' . $special['rewrite'] . ';');
}
}
$rules = explode("_SPECIAL_", trim($rules));
$rules = array_merge(explode("\n", $rules[0]), $specialPageRules, explode("\n", $rules[1]), array("\t#### Catch-all", "\t" . 'RewriteRule ^(.*)/?$ index.php?album=$1 [L,QSA]'));
return array($definitions, $rules);
}
$_definitions = array();
foreach ($_zp_conf_vars['special_pages'] as $definition) {
if (@$definition['define']) {
define($definition['define'], strtr($definition['rewrite'], $_definitions));
eval('$_definitions[$definition[\'define\']]=' . $definition['define'] . ';');
}
}
unset($definition);
unset($_definitions);
?>