PageRenderTime 41ms CodeModel.GetById 15ms RepoModel.GetById 0ms app.codeStats 1ms

/source/class/class_template.php

https://github.com/kuaileshike/upload
PHP | 332 lines | 291 code | 35 blank | 6 comment | 46 complexity | 086389bf1e4065d803f887214aa9f918 MD5 | raw file
  1. <?php
  2. /**
  3. * [Discuz!] (C)2001-2099 Comsenz Inc.
  4. * This is NOT a freeware, use is subject to license terms
  5. *
  6. * $Id: class_template.php 27948 2012-02-17 04:31:24Z monkey $
  7. */
  8. if(!defined('IN_DISCUZ')) {
  9. exit('Access Denied');
  10. }
  11. class template {
  12. var $subtemplates = array();
  13. var $csscurmodules = '';
  14. var $replacecode = array('search' => array(), 'replace' => array());
  15. var $blocks = array();
  16. var $language = array();
  17. var $file = '';
  18. function parse_template($tplfile, $templateid, $tpldir, $file, $cachefile) {
  19. $basefile = basename(DISCUZ_ROOT.$tplfile, '.htm');
  20. $file == 'common/header' && defined('CURMODULE') && CURMODULE && $file = 'common/header_'.CURMODULE;
  21. $this->file = $file;
  22. if($fp = @fopen(DISCUZ_ROOT.$tplfile, 'r')) {
  23. $template = @fread($fp, filesize(DISCUZ_ROOT.$tplfile));
  24. fclose($fp);
  25. } elseif($fp = @fopen($filename = substr(DISCUZ_ROOT.$tplfile, 0, -4).'.php', 'r')) {
  26. $template = $this->getphptemplate(@fread($fp, filesize($filename)));
  27. fclose($fp);
  28. } else {
  29. $tpl = $tpldir.'/'.$file.'.htm';
  30. $tplfile = $tplfile != $tpl ? $tpl.', '.$tplfile : $tplfile;
  31. $this->error('template_notfound', $tplfile);
  32. }
  33. $var_regexp = "((\\\$[a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*(\-\>)?[a-zA-Z0-9_\x7f-\xff]*)(\[[a-zA-Z0-9_\-\.\"\'\[\]\$\x7f-\xff]+\])*)";
  34. $const_regexp = "([a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*)";
  35. $headerexists = preg_match("/{(sub)?template\s+[\w\/]+?header\}/", $template);
  36. $this->subtemplates = array();
  37. for($i = 1; $i <= 3; $i++) {
  38. if(strexists($template, '{subtemplate')) {
  39. $template = preg_replace("/[\n\r\t]*(\<\!\-\-)?\{subtemplate\s+([a-z0-9_:\/]+)\}(\-\-\>)?[\n\r\t]*/ies", "\$this->loadsubtemplate('\\2')", $template);
  40. }
  41. }
  42. $template = preg_replace("/([\n\r]+)\t+/s", "\\1", $template);
  43. $template = preg_replace("/\<\!\-\-\{(.+?)\}\-\-\>/s", "{\\1}", $template);
  44. $template = preg_replace("/\{lang\s+(.+?)\}/ies", "\$this->languagevar('\\1')", $template);
  45. $template = preg_replace("/[\n\r\t]*\{block\/(\d+?)\}[\n\r\t]*/ie", "\$this->blocktags('\\1')", $template);
  46. $template = preg_replace("/[\n\r\t]*\{blockdata\/(\d+?)\}[\n\r\t]*/ie", "\$this->blockdatatags('\\1')", $template);
  47. $template = preg_replace("/[\n\r\t]*\{ad\/(.+?)\}[\n\r\t]*/ie", "\$this->adtags('\\1')", $template);
  48. $template = preg_replace("/[\n\r\t]*\{ad\s+([a-zA-Z0-9_\[\]]+)\/(.+?)\}[\n\r\t]*/ie", "\$this->adtags('\\2', '\\1')", $template);
  49. $template = preg_replace("/[\n\r\t]*\{date\((.+?)\)\}[\n\r\t]*/ie", "\$this->datetags('\\1')", $template);
  50. $template = preg_replace("/[\n\r\t]*\{avatar\((.+?)\)\}[\n\r\t]*/ie", "\$this->avatartags('\\1')", $template);
  51. $template = preg_replace("/[\n\r\t]*\{eval\s+(.+?)\s*\}[\n\r\t]*/ies", "\$this->evaltags('\\1')", $template);
  52. $template = preg_replace("/[\n\r\t]*\{csstemplate\}[\n\r\t]*/ies", "\$this->loadcsstemplate('\\1')", $template);
  53. $template = str_replace("{LF}", "<?=\"\\n\"?>", $template);
  54. $template = preg_replace("/\{(\\\$[a-zA-Z0-9_\-\>\[\]\'\"\$\.\x7f-\xff]+)\}/s", "<?=\\1?>", $template);
  55. $template = preg_replace("/\{hook\/(\w+?)(\s+(.+?))?\}/ie", "\$this->hooktags('\\1', '\\3')", $template);
  56. $template = preg_replace("/$var_regexp/es", "template::addquote('<?=\\1?>')", $template);
  57. $template = preg_replace("/\<\?\=\<\?\=$var_regexp\?\>\?\>/es", "\$this->addquote('<?=\\1?>')", $template);
  58. $headeradd = $headerexists ? "hookscriptoutput('$basefile');" : '';
  59. if(!empty($this->subtemplates)) {
  60. $headeradd .= "\n0\n";
  61. foreach($this->subtemplates as $fname) {
  62. $headeradd .= "|| checktplrefresh('$tplfile', '$fname', ".time().", '$templateid', '$cachefile', '$tpldir', '$file')\n";
  63. }
  64. $headeradd .= ';';
  65. }
  66. if(!empty($this->blocks)) {
  67. $headeradd .= "\n";
  68. $headeradd .= "block_get('".implode(',', $this->blocks)."');";
  69. }
  70. $template = "<? if(!defined('IN_DISCUZ')) exit('Access Denied'); {$headeradd}?>\n$template";
  71. $template = preg_replace("/[\n\r\t]*\{template\s+([a-z0-9_:\/]+)\}[\n\r\t]*/ies", "\$this->stripvtags('<? include template(\'\\1\'); ?>')", $template);
  72. $template = preg_replace("/[\n\r\t]*\{template\s+(.+?)\}[\n\r\t]*/ies", "\$this->stripvtags('<? include template(\'\\1\'); ?>')", $template);
  73. $template = preg_replace("/[\n\r\t]*\{echo\s+(.+?)\}[\n\r\t]*/ies", "\$this->stripvtags('<? echo \\1; ?>')", $template);
  74. $template = preg_replace("/([\n\r\t]*)\{if\s+(.+?)\}([\n\r\t]*)/ies", "\$this->stripvtags('\\1<? if(\\2) { ?>\\3')", $template);
  75. $template = preg_replace("/([\n\r\t]*)\{elseif\s+(.+?)\}([\n\r\t]*)/ies", "\$this->stripvtags('\\1<? } elseif(\\2) { ?>\\3')", $template);
  76. $template = preg_replace("/\{else\}/i", "<? } else { ?>", $template);
  77. $template = preg_replace("/\{\/if\}/i", "<? } ?>", $template);
  78. $template = preg_replace("/[\n\r\t]*\{loop\s+(\S+)\s+(\S+)\}[\n\r\t]*/ies", "\$this->stripvtags('<? if(is_array(\\1)) foreach(\\1 as \\2) { ?>')", $template);
  79. $template = preg_replace("/[\n\r\t]*\{loop\s+(\S+)\s+(\S+)\s+(\S+)\}[\n\r\t]*/ies", "\$this->stripvtags('<? if(is_array(\\1)) foreach(\\1 as \\2 => \\3) { ?>')", $template);
  80. $template = preg_replace("/\{\/loop\}/i", "<? } ?>", $template);
  81. $template = preg_replace("/\{$const_regexp\}/s", "<?=\\1?>", $template);
  82. if(!empty($this->replacecode)) {
  83. $template = str_replace($this->replacecode['search'], $this->replacecode['replace'], $template);
  84. }
  85. $template = preg_replace("/ \?\>[\n\r]*\<\? /s", " ", $template);
  86. if(!@$fp = fopen(DISCUZ_ROOT.$cachefile, 'w')) {
  87. $this->error('directory_notfound', dirname(DISCUZ_ROOT.$cachefile));
  88. }
  89. $template = preg_replace("/\"(http)?[\w\.\/:]+\?[^\"]+?&[^\"]+?\"/e", "\$this->transamp('\\0')", $template);
  90. $template = preg_replace("/\<script[^\>]*?src=\"(.+?)\"(.*?)\>\s*\<\/script\>/ies", "\$this->stripscriptamp('\\1', '\\2')", $template);
  91. $template = preg_replace("/[\n\r\t]*\{block\s+([a-zA-Z0-9_\[\]]+)\}(.+?)\{\/block\}/ies", "\$this->stripblock('\\1', '\\2')", $template);
  92. $template = preg_replace("/\<\?(\s{1})/is", "<?php\\1", $template);
  93. $template = preg_replace("/\<\?\=(.+?)\?\>/is", "<?php echo \\1;?>", $template);
  94. flock($fp, 2);
  95. fwrite($fp, $template);
  96. fclose($fp);
  97. }
  98. function languagevar($var) {
  99. $vars = explode(':', $var);
  100. $isplugin = count($vars) == 2;
  101. if(!$isplugin) {
  102. !isset($this->language['inner']) && $this->language['inner'] = array();
  103. $langvar = &$this->language['inner'];
  104. } else {
  105. !isset($this->language['plugin'][$vars[0]]) && $this->language['plugin'][$vars[0]] = array();
  106. $langvar = &$this->language['plugin'][$vars[0]];
  107. $var = &$vars[1];
  108. }
  109. if(!isset($langvar[$var])) {
  110. $lang = array();
  111. @include DISCUZ_ROOT.'./source/language/lang_template.php';
  112. $this->language['inner'] = $lang;
  113. if(!$isplugin) {
  114. if(defined('IN_MOBILE')) {
  115. list($path) = explode('/', str_replace('mobile/', '', $this->file));
  116. } else {
  117. list($path) = explode('/', $this->file);
  118. }
  119. @include DISCUZ_ROOT.'./source/language/'.$path.'/lang_template.php';
  120. $this->language['inner'] = array_merge($this->language['inner'], $lang);
  121. if(defined('IN_MOBILE')) {
  122. @include DISCUZ_ROOT.'./source/language/mobile/lang_template.php';
  123. $this->language['inner'] = array_merge($this->language['inner'], $lang);
  124. }
  125. } else {
  126. global $_G;
  127. if(empty($_G['config']['plugindeveloper'])) {
  128. loadcache('pluginlanguage_template');
  129. } elseif(!isset($_G['cache']['pluginlanguage_template'][$vars[0]]) && preg_match("/^[a-z]+[a-z0-9_]*$/i", $vars[0])) {
  130. if(@include(DISCUZ_ROOT.'./data/plugindata/'.$vars[0].'.lang.php')) {
  131. $_G['cache']['pluginlanguage_template'][$vars[0]] = $templatelang[$vars[0]];
  132. } else {
  133. loadcache('pluginlanguage_template');
  134. }
  135. }
  136. $this->language['plugin'][$vars[0]] = $_G['cache']['pluginlanguage_template'][$vars[0]];
  137. }
  138. }
  139. if(isset($langvar[$var])) {
  140. return $langvar[$var];
  141. } else {
  142. return '!'.$var.'!';
  143. }
  144. }
  145. function blocktags($parameter) {
  146. $bid = intval(trim($parameter));
  147. $this->blocks[] = $bid;
  148. $i = count($this->replacecode['search']);
  149. $this->replacecode['search'][$i] = $search = "<!--BLOCK_TAG_$i-->";
  150. $this->replacecode['replace'][$i] = "<?php block_display('$bid');?>";
  151. return $search;
  152. }
  153. function blockdatatags($parameter) {
  154. $bid = intval(trim($parameter));
  155. $this->blocks[] = $bid;
  156. $i = count($this->replacecode['search']);
  157. $this->replacecode['search'][$i] = $search = "<!--BLOCKDATA_TAG_$i-->";
  158. $this->replacecode['replace'][$i] = "";
  159. return $search;
  160. }
  161. function adtags($parameter, $varname = '') {
  162. $parameter = stripslashes($parameter);
  163. $i = count($this->replacecode['search']);
  164. $this->replacecode['search'][$i] = $search = "<!--AD_TAG_$i-->";
  165. $this->replacecode['replace'][$i] = "<?php ".(!$varname ? 'echo ' : '$'.$varname.'=')."adshow(\"$parameter\");?>";
  166. return $search;
  167. }
  168. function datetags($parameter) {
  169. $parameter = stripslashes($parameter);
  170. $i = count($this->replacecode['search']);
  171. $this->replacecode['search'][$i] = $search = "<!--DATE_TAG_$i-->";
  172. $this->replacecode['replace'][$i] = "<?php echo dgmdate($parameter);?>";
  173. return $search;
  174. }
  175. function avatartags($parameter) {
  176. $parameter = stripslashes($parameter);
  177. $i = count($this->replacecode['search']);
  178. $this->replacecode['search'][$i] = $search = "<!--AVATAR_TAG_$i-->";
  179. $this->replacecode['replace'][$i] = "<?php echo avatar($parameter);?>";
  180. return $search;
  181. }
  182. function evaltags($php) {
  183. $php = str_replace('\"', '"', $php);
  184. $i = count($this->replacecode['search']);
  185. $this->replacecode['search'][$i] = $search = "<!--EVAL_TAG_$i-->";
  186. $this->replacecode['replace'][$i] = "<?php $php?>";
  187. return $search;
  188. }
  189. function hooktags($hookid, $key = '') {
  190. global $_G;
  191. $i = count($this->replacecode['search']);
  192. $this->replacecode['search'][$i] = $search = "<!--HOOK_TAG_$i-->";
  193. $dev = '';
  194. if(isset($_G['config']['plugindeveloper']) && $_G['config']['plugindeveloper'] == 2) {
  195. $dev = "echo '<hook>[".($key ? 'array' : 'string')." $hookid".($key ? '/\'.'.$key.'.\'' : '')."]</hook>';";
  196. }
  197. $key = $key !== '' ? "[$key]" : '';
  198. $this->replacecode['replace'][$i] = "<?php {$dev}if(!empty(\$_G['setting']['pluginhooks']['$hookid']$key)) echo \$_G['setting']['pluginhooks']['$hookid']$key;?>";
  199. return $search;
  200. }
  201. function stripphpcode($type, $code) {
  202. $this->phpcode[$type][] = $code;
  203. return '{phpcode:'.$type.'/'.(count($this->phpcode[$type]) - 1).'}';
  204. }
  205. function loadsubtemplate($file) {
  206. $tplfile = template($file, 0, '', 1);
  207. $filename = DISCUZ_ROOT.$tplfile;
  208. if(($content = @implode('', file($filename))) || ($content = $this->getphptemplate(@implode('', file(substr($filename, 0, -4).'.php'))))) {
  209. $this->subtemplates[] = $tplfile;
  210. return $content;
  211. } else {
  212. return '<!-- '.$file.' -->';
  213. }
  214. }
  215. function getphptemplate($content) {
  216. $pos = strpos($content, "\n");
  217. return $pos !== false ? substr($content, $pos + 1) : $content;
  218. }
  219. function loadcsstemplate() {
  220. global $_G;
  221. $scriptcss = '<link rel="stylesheet" type="text/css" href="data/cache/style_{STYLEID}_common.css?{VERHASH}" />';
  222. $content = $this->csscurmodules = '';
  223. $content = @implode('', file(DISCUZ_ROOT.'./data/cache/style_'.STYLEID.'_module.css'));
  224. $content = preg_replace("/\[(.+?)\](.*?)\[end\]/ies", "\$this->cssvtags('\\1','\\2')", $content);
  225. if($this->csscurmodules) {
  226. $this->csscurmodules = preg_replace(array('/\s*([,;:\{\}])\s*/', '/[\t\n\r]/', '/\/\*.+?\*\//'), array('\\1', '',''), $this->csscurmodules);
  227. if(@$fp = fopen(DISCUZ_ROOT.'./data/cache/style_'.STYLEID.'_'.$_G['basescript'].'_'.CURMODULE.'.css', 'w')) {
  228. fwrite($fp, $this->csscurmodules);
  229. fclose($fp);
  230. } else {
  231. exit('Can not write to cache files, please check directory ./data/ and ./data/cache/ .');
  232. }
  233. $scriptcss .= '<link rel="stylesheet" type="text/css" href="data/cache/style_{STYLEID}_'.$_G['basescript'].'_'.CURMODULE.'.css?{VERHASH}" />';
  234. }
  235. $scriptcss .= '{if $_G[uid] && isset($_G[cookie][extstyle]) && strpos($_G[cookie][extstyle], TPLDIR) !== false}<link rel="stylesheet" id="css_extstyle" type="text/css" href="$_G[cookie][extstyle]/style.css" />{elseif $_G[style][defaultextstyle]}<link rel="stylesheet" id="css_extstyle" type="text/css" href="$_G[style][defaultextstyle]/style.css" />{/if}';
  236. return $scriptcss;
  237. }
  238. function cssvtags($param, $content) {
  239. global $_G;
  240. $modules = explode(',', $param);
  241. foreach($modules as $module) {
  242. $module .= '::'; //fix notice
  243. list($b, $m) = explode('::', $module);
  244. if($b && $b == $_G['basescript'] && (!$m || $m == CURMODULE)) {
  245. $this->csscurmodules .= $content;
  246. return;
  247. }
  248. }
  249. return;
  250. }
  251. function transamp($str) {
  252. $str = str_replace('&', '&amp;', $str);
  253. $str = str_replace('&amp;amp;', '&amp;', $str);
  254. $str = str_replace('\"', '"', $str);
  255. return $str;
  256. }
  257. function addquote($var) {
  258. return str_replace("\\\"", "\"", preg_replace("/\[([a-zA-Z0-9_\-\.\x7f-\xff]+)\]/s", "['\\1']", $var));
  259. }
  260. function stripvtags($expr, $statement = '') {
  261. $expr = str_replace("\\\"", "\"", preg_replace("/\<\?\=(\\\$.+?)\?\>/s", "\\1", $expr));
  262. $statement = str_replace("\\\"", "\"", $statement);
  263. return $expr.$statement;
  264. }
  265. function stripscriptamp($s, $extra) {
  266. $extra = str_replace('\\"', '"', $extra);
  267. $s = str_replace('&amp;', '&', $s);
  268. return "<script src=\"$s\" type=\"text/javascript\"$extra></script>";
  269. }
  270. function stripblock($var, $s) {
  271. $s = str_replace('\\"', '"', $s);
  272. $s = preg_replace("/<\?=\\\$(.+?)\?>/", "{\$\\1}", $s);
  273. preg_match_all("/<\?=(.+?)\?>/e", $s, $constary);
  274. $constadd = '';
  275. $constary[1] = array_unique($constary[1]);
  276. foreach($constary[1] as $const) {
  277. $constadd .= '$__'.$const.' = '.$const.';';
  278. }
  279. $s = preg_replace("/<\?=(.+?)\?>/", "{\$__\\1}", $s);
  280. $s = str_replace('?>', "\n\$$var .= <<<EOF\n", $s);
  281. $s = str_replace('<?', "\nEOF;\n", $s);
  282. return "<?\n$constadd\$$var = <<<EOF\n".$s."\nEOF;\n?>";
  283. }
  284. function error($message, $tplname) {
  285. discuz_error::template_error($message, $tplname);
  286. }
  287. }
  288. ?>