/** Write sth. to log * @param int $level * Loglevel of message * @param string $msg * Log message */ public function doLog($level, $msg) { global $Config; if ($level > $this->level) { return; } // create log message $msg = date("Y-m-d H:i:s") . "|{$level}|{$msg}\n"; // write log ts_FileHandler::writeFile($Config->get('dir_data') . '/log/backend.log', $msg) or die("ts_Log::doLog: Unable to log message: {$msg}"); }
/** Parse help pages of this module * * @return bool */ protected function parseHelp() { global $Parser, $Config; // get prefix and paths $prefix = 'mod' . $this->id . '__'; $path_source = $this->path . '/templates/help'; $path_destination = $Config->get('dir_runtime') . '/help'; // get all files $files = ts_FileHandler::getSubfiles($path_source); // parse all files foreach ($files as $index => $value) { // read and parse $content = ts_FileHandler::readFile($path_source . '/' . $value); $content = $Parser->parse($content); // write if (!$content or !ts_FileHandler::writeFile($path_destination . '/' . $prefix . $value, $content, true)) { return false; } } return true; }
/** Write CSS files * * @return bool */ public function writeFiles() { global $Config; // add pseudo-style $this->format_styles[0] = array(); // loop styles foreach ($this->format_styles as $index => $values) { // merge formats $current = $this->format; foreach ($values as $in => $val) { if (isset($current[$in])) { $current[$in] = array_merge($current[$in], $val); } else { $current[$in] = $val; } } // order formats $css1 = array(); $css2 = array(); $css3 = array(); foreach ($current as $in => $val) { $in = trim($in); if (substr($in, 0, 1) == '#') { $css3[$in] = $val; } elseif (substr($in, 0, 1) == '.') { $css2[$in] = $val; } else { $css1[$in] = $val; } } ksort($css1); ksort($css2); ksort($css3); $current = array_merge($css1, $css2, $css3); // sum for output $output = ''; foreach ($current as $in => $val) { $output .= $in . ' {'; foreach ($val as $i => $v) { $output .= $i . ':' . $v . ';'; } $output .= '} '; } // write file if (!($index === 0) and !empty($values)) { $path = $Config->get('dir_runtime') . '/css/style' . $index . '__format.css'; } else { $path = $Config->get('dir_runtime') . '/css/format.css'; } // write file if (!ts_FileHandler::writeFile($path, $output, true)) { return false; } } return true; }
/** Write language-files * * @return string */ public function writeFiles() { global $Config; // add pseudo-style $this->lang_styles[0] = false; // loop all styles foreach ($this->lang_styles as $index => $values) { // loop all modules if (empty($this->lang) or !is_array($this->lang)) { return true; } foreach ($this->lang as $in => $val) { // loop all languages if (empty($val) or !is_array($val)) { continue; } foreach ($val as $i => $v) { // merge current if (isset($values[$in], $values[$in][$i]) and is_array($values[$in][$i])) { $current = array_merge($v, $values[$in][$i]); } else { $current = $v; } // create file-content $content = ''; foreach ($current as $ii => $vv) { // escape single-quotes $vv = str_replace("'", '\\\'', $vv); $content .= ",'" . strtoupper('MOD' . $in . '__' . $ii) . "'=>'" . $vv . "'"; } $content = '<?php $lang = array(' . substr($content, 1) . '); ?>'; // get path if (!($index === 0)) { $path = $Config->get('dir_runtime') . '/lang/style' . $index . '__mod' . $in . '__' . $i . '.lang.php'; } else { $path = $Config->get('dir_runtime') . '/lang/mod' . $in . '__' . $i . '.lang.php'; } // try to write if (!ts_FileHandler::writeFile($path, $content, true)) { return false; } } } } return true; }
/** Inject all subcodes and complete file-rendering * @param string|bool $path * Path to folder in which all files will be * * @return bool */ public function parseAll($path = false) { global $Config, $Parser, $Log; // run all? if ($path == false) { if ($this->parseAll($Config->get('dir_runtime') . '/functions') and $this->parseAll($Config->get('dir_runtime') . '/classes') and $this->parseAll($Config->get('dir_runtime') . '/templates')) { return true; } return false; } // validate path if (!is_dir($path)) { $Log->doLog(3, "SubcodeHandler: Failed to parse path '{$path}'"); return false; } // parse all files $subfiles = ts_FileHandler::getSubfiles($path); foreach ($subfiles as $index => $value) { // get filepath $filepath = $path . '/' . $value; // read file $content = ts_FileHandler::readFile($filepath); if ($content === false) { $Log->doLog(3, "SubcodeHandler: Failed to read file '{$filepath}'"); return false; } // check, if anything to replace in this file if (isset($this->subcodes[$filepath])) { // parse all lines to be add foreach ($this->subcodes[$filepath] as $in => $val) { $to_add = ''; // sum everything to add to this line foreach ($val as $i => $v) { $to_add .= $v; } // replace line by subfunctions $content = str_replace('{line_' . $in . '}', $to_add, $content); } } // strip all {line_xx} $content = preg_replace('#\\{line_[0-9]*\\}#Usi', '', $content); // trim again $content = $Parser->trim($content, true); // write file if (!ts_FileHandler::writeFile($filepath, $content, true)) { $Log->doLog(3, "SubcodeHandler: Failed to write file '{$filepath}'"); return false; } } // parse all subfolders $subfolders = ts_FileHandler::getSubfolders($path); foreach ($subfolders as $index => $value) { if (!$this->parseAll($path . '/' . $value)) { return false; } } return true; }
/** Parse template files of this module * * @return bool */ protected function parseTemplates() { global $Config, $Parser; // source-path $path_source = $this->path . '/modules'; // loop modules $modules = ts_FileHandler::getSubfolders($path_source); foreach ($modules as $index => $value) { // get id__module $id__module = $Parser->replaceModule('$' . $value . '$'); if (!$id__module) { continue; } $id__module = substr($id__module, 3, strlen($id__module) - 5); // set id__module $Parser->setModule($id__module); // get path_new $path_new = $Config->get('dir_runtime') . '/templates'; $prefix = 'style' . $this->id . '__mod' . $id__module . '__'; // get current path $path_current = $path_source . '/' . $value; // get all files $files = ts_FileHandler::getSubfiles($path_current); // parse all files foreach ($files as $in => $val) { // read $content = ts_FileHandler::readFile($path_current . '/' . $val); // parse $content = $Parser->parse($content, true); // write if (!$content or !ts_FileHandler::writeFile($path_new . '/' . $prefix . $val, $content, true)) { return false; } } } return true; }
function parseAll() { global $Database, $Config, $ModuleHandler, $Log; // allow only, if logged in if (!isset($_SESSION['admin_auth']) or empty($_SESSION['admin_auth'])) { return false; } // reset session var, if accessing page normally if (!isset($_GET['call'])) { unset($_SESSION['parseAll__call']); } // set global Objects global $FormatHandler, $SubcodeHandler, $Parser, $LanguageHandler, $AccessParser, $ConfigParser, $USERSYSTEM; // is first call or a consecutive one? if (isset($_SESSION['parseAll__call']) and !empty($_SESSION['parseAll__call'])) { // is consecutive call $call_num = $_SESSION['parseAll__call']['num']; $LanguageHandler = $_SESSION['parseAll__call']['LanguageHandler']; $FormatHandler = $_SESSION['parseAll__call']['FormatHandler']; $SubcodeHandler = $_SESSION['parseAll__call']['SubcodeHandler']; $AccessParser = $_SESSION['parseAll__call']['AccessParser']; $ConfigParser = $_SESSION['parseAll__call']['ConfigParser']; $USERSYSTEM = $_SESSION['parseAll__call']['USERSYSTEM']; $Parser = $_SESSION['parseAll__call']['Parser']; $modules_all = $_SESSION['parseAll__call']['modules_all']; $pre_system_online = $_SESSION['parseAll__call']['pre_system_online']; } else { // is first call $call_num = 0; $FormatHandler = new ts_FormatHandler(); $SubcodeHandler = new ts_SubcodeHandler(); $AccessParser = new ts_AccessParser(); $ConfigParser = new ts_ConfigParser(); $modules_all = $ModuleHandler->getModules(true); $Parser = new ts_Parser($Config->get('prefix'), $modules_all, $Config->get('debug_mode')); $USERSYSTEM = 0; $LanguageHandler = new ts_LanguageHandler(); $pre_system_online = false; } if ($call_num == 0) { // log $Log->doLog(3, "Rendering: remove old files"); // all directories and files that will be recreated $dir_runtime = $Config->get('dir_runtime'); $rc_dirs = array($Config->get('dir_runtime') . '/classes', $Config->get('dir_runtime') . '/functions', $Config->get('dir_runtime') . '/templates', $Config->get('dir_runtime') . '/files', $Config->get('dir_runtime') . '/static', $Config->get('dir_runtime') . '/lang', $Config->get('dir_runtime') . '/javascript', $Config->get('dir_runtime') . '/xmlResponses', $Config->get('dir_runtime') . '/help'); $rc_files = array($Config->get('dir_runtime') . '/index.php', $Config->get('dir_runtime') . '/ajax.php', $Config->get('dir_runtime') . '/init.php', $Config->get('dir_runtime') . '/offline.php', $Config->get('dir_runtime') . '/webdav.php', $Config->get('dir_runtime') . '/file.php'); // set system as offline $pre_system_online = $Config->get('system_online'); $Config->set('system_online', false); $Config->set('system_offline_since', date('m/d/y H:i:s')); // backup current runtime /* if (!ts_BackupHandler::backupRuntime(true)) { $_SESSION['admin_error'] = 'ERROR__RENDER (backup runtime dir)'; return false; } */ // delete all dirs and files which will be recreated foreach ($rc_dirs as $index => $value) { if (!ts_FileHandler::emptyFolder($value)) { $_SESSION['admin_error'] = 'ERROR__RENDER (empty runtime dirs)'; return false; } } foreach ($rc_files as $index => $value) { if (file_exists($value)) { unlink($value); } } } elseif ($call_num > 0 and $call_num <= count($modules_all)) { // render all activated modules $call_counter = 0; $counter = 0; foreach ($modules_all as $index => $Value) { $counter++; // skip those, already parsed if ($counter < $call_num) { continue; } // parse module if (!$Value->parse()) { $_SESSION['admin_error'] = 'ERROR__RENDER (module: ' . $Value->getInfo('name') . ')'; return false; } $call_counter++; // always parse 2 modules at a time if ($call_counter <= 1) { $call_num++; continue; } break; } } else { // log $Log->doLog(3, "Rendering: finish"); // USERSYSTEM set? if (!$USERSYSTEM) { $_SESSION['admin_error'] = 'ERROR__RENDER (usersystem is missing!)'; return false; } // render subcodes if (!$SubcodeHandler->parseAll()) { $_SESSION['admin_error'] = 'ERROR__RENDER (subfunction-parsing)'; return false; } // render all activated styles $StyleHandler = new ts_StyleHandler(); $styles_all = $StyleHandler->getStyles(true); $selected_default_style = $Config->get('default_style'); $is_default_style = false; foreach ($styles_all as $index => $Value) { if ($selected_default_style and $Value->getInfo('id') == $selected_default_style) { $is_default_style = true; } if (!$Value->parse()) { $_SESSION['admin_error'] = 'ERROR__RENDER (style: ' . $Value->getInfo('name') . ')'; return false; } } // set default style, if missing if (!$is_default_style) { $first_style = array_shift($styles_all); $Config->set('default_style', $first_style->getInfo('id')); } // make sure, a default-style is chosen $StyleHandler->validateDefault(); // get format.css if ($format = $FormatHandler->writeFiles() === false) { $_SESSION['admin_error'] = 'ERROR__RENDER (format.css)'; return false; } // render language-files if (!$LanguageHandler->writeFiles()) { $_SESSION['admin_error'] = 'ERROR__RENDER (language-files)'; return false; } // parse Access if (!$AccessParser->parseAll($Config->get("prefix") . "mod{$USERSYSTEM}__")) { $_SESSION['admin_error'] = 'ERROR__RENDER (access-files)'; return false; } // parse Config if (!$ConfigParser->parseAll($Config->get('prefix') . "mod{$USERSYSTEM}__config")) { $_SESSION['admin_error'] = 'ERROR__RENDER (config-files)'; return false; } // move special files to runtime root $special_files = array('index.php', 'ajax.php', 'webdav.php', 'offline.php', 'init.php', 'file.php'); foreach ($special_files as $index => $value) { if (file_exists($Config->get('dir_runtime') . "/static/{$value}") and !ts_FileHandler::moveFile($Config->get('dir_runtime') . "/static/{$value}", $Config->get('dir_runtime') . "/{$value}")) { $_SESSION['admin_error'] = 'ERROR__RENDER (copy special files "' . $value . '")'; return false; } } // config $config = '<?php include "' . $Config->get('dir_data') . '/config.php"; ?>'; if (!ts_FileHandler::writeFile($Config->get('dir_runtime') . '/config.php', $config, 1)) { $_SESSION['admin_error'] = 'ERROR__RENDER (write config)'; return false; } // reset system_online $Config->set('system_online', $pre_system_online); // update installation-progress if ($Config->get('installation') < 100) { $Config->setArray('installation_progress', 'parseAll', true); } $_SESSION['admin_info'] = 'INFO__RENDER_SUCCESS'; } // update call-progress if ($call_num > count($modules_all) + 2) { // finished unset($_SESSION['parseAll__call']); } else { // save vars if (!isset($_SESSION['parseAll__call']) or empty($_SESSION['parseAll__call'])) { $_SESSION['parseAll__call'] = array(); } $_SESSION['parseAll__call']['num'] = $call_num + 1; $_SESSION['parseAll__call']['LanguageHandler'] = $LanguageHandler; $_SESSION['parseAll__call']['FormatHandler'] = $FormatHandler; $_SESSION['parseAll__call']['SubcodeHandler'] = $SubcodeHandler; $_SESSION['parseAll__call']['AccessParser'] = $AccessParser; $_SESSION['parseAll__call']['ConfigParser'] = $ConfigParser; $_SESSION['parseAll__call']['USERSYSTEM'] = $USERSYSTEM; $_SESSION['parseAll__call']['Parser'] = $Parser; $_SESSION['parseAll__call']['modules_all'] = $modules_all; $_SESSION['parseAll__call']['pre_system_online'] = $pre_system_online; // redirect to next header('Location:?event=parseAll&call=' . $call_num); exit; } return true; }
/** Preparse file * @param string $source * Source file * @param string $destination * Destination file * @param string $path_to_cut * Path to root * @param bool $rm_flags * Remove flag comments? * * @return bool */ public function parseFile($source, $destination, $path_to_cut = "", $rm_flags = false) { global $Config, $Log; // is packet set? if (empty($this->Packet)) { return false; } // read $Log->doLog(8, "PreParser: Read file '{$source}'"); $content = ts_FileHandler::readFile($source); if ($content === false) { $Log->doLog(3, "PreParser: Unable to read file '{$source}'"); return false; } // get filetype $cache = explode('.', basename($source)); $filetype = end($cache); // filetype to move only? if (!in_array($filetype, $this->parse_ext)) { if ($source != $destination and !ts_FileHandler::writeFile($destination, $content)) { $Log->doLog(3, "PreParser: Unable to move file to '{$destination}'"); return false; } return true; } // split flag comment from rest of content if (substr($content, 0, 4) != '<!--') { $content = '<!-- | -->' . chr(10) . $content; } $content_lines = explode(chr(10), $content); $flag_comment = trim($content_lines[0]); unset($content_lines[0]); $content = implode(chr(10), $content_lines); // read flags and get path to display $flags = $this->getFlags($flag_comment); if (isset($flags['p'])) { return true; } $displaypath = substr($destination, strlen($path_to_cut) + 1); // add header if (!isset($flags['h'])) { // remove existing headers $content = preg_replace('#(\\/\\*\\* header .* \\*\\/)#Usi', '', $content); $content = preg_replace('#(\\<\\?php[\\s]*\\?\\>)#Usi', '', $content); $content = preg_replace('#(\\<!--[\\s]*--\\>)#Usi', '', $content); // generate new header // First two lines have to be separated or the publish // script will remove the following header definition! $header = '/*' . '* header *********************************************************' . chr(10) . ' * project: TSunic ' . $Config->get('version') . ' | ' . $this->Packet->getInfo('name') . ' ' . $this->Packet->getInfo('version') . chr(10) . ' * file: ' . $displaypath . chr(10); if ($this->Packet->getInfo('author')) { $header .= ' * author: ' . $this->Packet->getInfo('author') . chr(10); } if ($this->Packet->getInfo('copyright')) { $header .= ' * copyright: ' . $this->Packet->getInfo('copyright') . chr(10); } if ($this->Packet->getInfo('licence')) { $cache = explode(chr(10), $this->Packet->getInfo('licence')); $header .= ' * licence: ' . trim($cache[0]) . chr(10); if (count($cache) > 1) { for ($i = 1; $i < count($cache); $i++) { $cache[$i] = trim($cache[$i]); $header .= empty($cache[$i]) ? ' *' . chr(10) : ' * ' . $cache[$i] . chr(10); } } } $header .= ' * ************************************************************** */' . chr(10); // embed header in required tags switch ($filetype) { case 'php': $header = '<?php' . chr(10) . $header . '?>'; break; case 'js': case 'css': break; default: $header = '<!--' . chr(10) . $header . '-->'; break; } // add header to content $content = $header . chr(10) . $content; // skip empty lines at the beginning $cache = explode(chr(10), $content); foreach ($cache as $index => $value) { $value = trim($value); if (empty($value)) { unset($cache[$index]); continue; } elseif ($value == '<?php') { continue; } break; } $content = implode(chr(10), $cache); } // add flag comment again if (!$rm_flags) { $content = $flag_comment . chr(10) . $content; } // trim $content = str_replace('?>' . chr(10) . '<?php', '', $content); // write $Log->doLog(8, "PreParser: Write file '{$source}'"); if (!ts_FileHandler::writeFile($destination, $content, 1)) { $Log->doLog(3, "PreParser: Unable to write file ({$destination})"); return false; } return true; }