/** * Handles the upload request. * * @param array $conf * * @return array|bool */ static function handleRequest($conf = array()) { $cx = Cx::instanciate(); // 5 minutes execution time @set_time_limit(5 * 60); self::$_error = null; // start fresh $conf = self::$conf = array_merge(array('file_data_name' => 'file', 'tmp_dir' => $_SESSION->getTempPath(), 'target_dir' => 'images/content/', 'cleanup' => true, 'max_file_age' => 5 * 3600, 'chunk' => isset($_REQUEST['chunk']) ? intval($_REQUEST['chunk']) : 0, 'chunks' => isset($_REQUEST['chunks']) ? intval($_REQUEST['chunks']) : 0, 'fileName' => isset($_REQUEST['name']) ? $_REQUEST['name'] : false, 'allow_extensions' => false, 'delay' => 0, 'cb_sanitizeFileName' => array(__CLASS__, 'sanitizeFileName'), 'cb_check_file' => false), $conf); try { if (!$conf['fileName']) { if (!empty($_FILES)) { $conf['fileName'] = $_FILES[$conf['file_data_name']]['name']; } else { throw new UploaderException('', PLUPLOAD_INPUT_ERR); } } // Cleanup outdated temp files and folders if ($conf['cleanup']) { self::cleanup(); } // Fake network congestion if ($conf['delay']) { usleep($conf['delay']); } // callback function for sanitizie filename if (is_callable($conf['cb_sanitizeFileName'])) { $fileName = call_user_func($conf['cb_sanitizeFileName'], $conf['fileName']); } else { $fileName = $conf['fileName']; } // Check if file type is allowed if ($conf['allow_extensions']) { if (is_string($conf['allow_extensions'])) { $conf['allow_extensions'] = preg_split('{\\s*,\\s*}', $conf['allow_extensions']); } if (!in_array(strtolower(pathinfo($fileName, PATHINFO_EXTENSION)), $conf['allow_extensions'])) { throw new UploaderException('', PLUPLOAD_TYPE_ERR); } } $file_path = rtrim($conf['tmp_dir'], DIRECTORY_SEPARATOR) . DIRECTORY_SEPARATOR . $fileName; $tmp_path = $file_path . ".part"; // Write file or chunk to appropriate temp location if ($conf['chunks']) { self::writeFileTo("{$file_path}.dir.part" . DIRECTORY_SEPARATOR . $conf['chunk']); // Check if all chunks already uploaded if ($conf['chunk'] == $conf['chunks'] - 1) { self::writeChunksToFile("{$file_path}.dir.part", $tmp_path); } } else { self::writeFileTo($tmp_path); } // Upload complete write a temp file to the final destination if (!$conf['chunks'] || $conf['chunk'] == $conf['chunks'] - 1) { if (is_callable($conf['cb_check_file']) && !call_user_func($conf['cb_check_file'], $tmp_path)) { @unlink($tmp_path); throw new UploaderException('', PLUPLOAD_SECURITY_ERR); } $new_path = $conf['target_dir'] . $fileName; \Cx\Lib\FileSystem\FileSystem::move($tmp_path, $new_path, true); $rootPath = $cx->getWebsitePath() . $conf['target_dir']; $rootPathFull = $cx->getWebsitePath() . $new_path; $filePathinfo = pathinfo($rootPathFull); $fileExtension = $filePathinfo['extension']; $fileNamePlain = $filePathinfo['filename']; $im = new \ImageManager(); if ($im->_isImage($rootPathFull)) { foreach (UploaderConfiguration::getInstance()->getThumbnails() as $thumbnail) { $im->_createThumb($rootPath, $conf['target_dir'], $fileName, $thumbnail['size'], $thumbnail['quality'], $fileNamePlain . $thumbnail['value'] . '.' . $fileExtension); } } return array('name' => $fileName, 'path' => $file_path, 'size' => filesize($file_path)); } // ok so far return true; } catch (UploaderException $ex) { self::$_error = $ex->getCode(); return array('error' => $ex->getCode()); } }
/** * Notifies the callback. Invoked on upload completion. */ public function notifyCallback() { //temporary path where files were uploaded $tempDir = '/upload_' . $this->uploadId; $tempPath = $_SESSION->getTempPath() . $tempDir; $tempWebPath = $_SESSION->getWebTempPath() . $tempDir; //we're going to call the callbck, so the data is not needed anymore //well... not quite sure. need it again in contact form. //TODO: code session cleanup properly if time. //$this->cleanupCallbackData(); $classFile = $this->callbackData[0]; //call the callback, get return code if ($classFile != null) { if (!file_exists($classFile)) { throw new UploaderException("Class file '{$classFile}' specified for callback does not exist!"); } require_once $this->callbackData[0]; } $originalFileNames = array(); if (isset($_SESSION['upload']['handlers'][$this->uploadId]['originalFileNames'])) { $originalFileNames = $_SESSION['upload']['handlers'][$this->uploadId]['originalFileNames']; } //various file infos are passed via this array $fileInfos = array('originalFileNames' => $originalFileNames); $response = null; //the response data. if (isset($_SESSION['upload']['handlers'][$this->uploadId]['response_data'])) { $response = UploadResponse::fromSession($_SESSION['upload']['handlers'][$this->uploadId]['response_data']); } else { $response = new UploadResponse(); } $ret = call_user_func(array($this->callbackData[1], $this->callbackData[2]), $tempPath, $tempWebPath, $this->getData(), $this->uploadId, $fileInfos, $response); //clean up session: we do no longer need the array with the original file names unset($_SESSION['upload']['handlers'][$this->uploadId]['originalFileNames']); //same goes for the data //if(isset($_SESSION['upload']['handlers'][$this->uploadId]['data'])) // TODO: unset this when closing the uploader dialog, but not before // unset($_SESSION['upload']['handlers'][$this->uploadId]['data']); if (\Cx\Lib\FileSystem\FileSystem::exists($tempWebPath)) { //the callback could have returned a path where he wants the files moved to // check that $ret[1] is not empty is VERY important!!! if (!is_null($ret) && !empty($ret[1])) { //we need to move the files //gather target information $path = pathinfo($ret[0]); $pathWeb = pathinfo($ret[1]); //make sure the target directory is writable \Cx\Lib\FileSystem\FileSystem::makeWritable($pathWeb['dirname'] . '/' . $path['basename']); //revert $path and $pathWeb to whole path instead of pathinfo path for copying $path = $path['dirname'] . '/' . $path['basename'] . '/'; $pathWeb = $pathWeb['dirname'] . '/' . $pathWeb['basename'] . '/'; //trailing slash needed for File-class calls $tempPath .= '/'; $tempWebPath .= '/'; //move everything uploaded to target dir $h = opendir($tempPath); $im = new \ImageManager(); while (false != ($f = readdir($h))) { //skip . and .. if ($f == '.' || $f == '..') { continue; } //TODO: if return value = 'error' => react \Cx\Lib\FileSystem\FileSystem::move($tempWebPath . $f, $pathWeb . $f, true); if ($im->_isImage($path . $f)) { $im->_createThumb($path, $pathWeb, $f); } $response->increaseUploadedFilesCount(); } closedir($h); } else { // TODO: what now???? } //delete the folder \Cx\Lib\FileSystem\FileSystem::delete_folder($tempWebPath, true); } else { // TODO: output error message to user that no files had been uploaded!!! } $response->uploadFinished(); $_SESSION['upload']['handlers'][$this->uploadId]['response_data'] = $response->toSessionValue(); }
/** * Regenerate the thumbnails * * @param array $post $_POST values */ protected function generateThumbnail($post) { // release the locks, session not needed $session = \cmsSession::getInstance(); $session->releaseLocks(); session_write_close(); $cx = Cx::instanciate(); $key = $_GET['key']; if (!preg_match("/[A-Z0-9]{5}/i", $key)) { die; } $processFile = $session->getTempPath() . '/progress' . $key . '.txt'; if (\Cx\Lib\FileSystem\FileSystem::exists($processFile)) { die; } try { $objProcessFile = new \Cx\Lib\FileSystem\File($processFile); $objProcessFile->touch(); } catch (\Cx\Lib\FileSystem\FileSystemException $ex) { die; } $recursiveIteratorIterator = new \RecursiveIteratorIterator(new \RecursiveDirectoryIterator($cx->getWebsiteImagesPath() . '/'), \RecursiveIteratorIterator::SELF_FIRST); $jsonFileArray = array(); $thumbnailList = UploaderConfiguration::getInstance()->getThumbnails(); $imageManager = new \ImageManager(); $fileCounter = 0; $generalSuccess = true; $imageFiles = array(); foreach ($recursiveIteratorIterator as $file) { /** * @var $file \SplFileInfo */ $extension = 'Dir'; if (!$file->isDir()) { $extension = ucfirst(pathinfo($file->getFilename(), PATHINFO_EXTENSION)); } $filePathinfo = pathinfo($file->getRealPath()); $fileNamePlain = $filePathinfo['filename']; // set preview if image $preview = 'none'; $fileInfos = array('filepath' => mb_strcut($file->getPath() . '/' . $file->getFilename(), mb_strlen($cx->getCodeBasePath())), 'name' => $file->getFilename(), 'cleansize' => $file->getSize(), 'extension' => ucfirst(mb_strtolower($extension)), 'type' => $file->getType()); // filters if ($fileInfos['name'] == '.' || preg_match('/\\.thumb/', $fileInfos['name']) || $fileInfos['name'] == 'index.php' || 0 === strpos($fileInfos['name'], '.')) { continue; } if (!preg_match("/(jpg|jpeg|gif|png)/i", ucfirst($extension))) { continue; } $imageFiles[] = $file; } $imageFilesCount = count($imageFiles); if ($imageFilesCount == 0) { $objProcessFile->write(100); die; } foreach ($imageFiles as $file) { /** * @var $file \SplFileInfo */ $extension = 'Dir'; if (!$file->isDir()) { $extension = ucfirst(pathinfo($file->getFilename(), PATHINFO_EXTENSION)); } $filePathinfo = pathinfo($file->getRealPath()); $fileNamePlain = $filePathinfo['filename']; $fileInfos = array('filepath' => mb_strcut($file->getPath() . '/' . $file->getFilename(), mb_strlen(ASCMS_PATH)), 'name' => $file->getFilename(), 'cleansize' => $file->getSize(), 'extension' => ucfirst(mb_strtolower($extension)), 'type' => $file->getType()); $filePathinfo = pathinfo($file->getRealPath()); $fileExtension = isset($filePathinfo['extension']) ? $filePathinfo['extension'] : ''; $preview = $cx->getCodeBaseOffsetPath() . str_replace($cx->getCodeBaseDocumentRootPath(), '', $file->getRealPath()); $previewList = array(); foreach ($thumbnailList as $thumbnail) { $previewList[] = str_replace('.' . lcfirst($extension), $thumbnail['value'] . '.' . lcfirst($extension), $preview); } $allThumbnailsExists = true; foreach ($previewList as $previewImage) { if (!FileSystem::exists($previewImage)) { $allThumbnailsExists = false; } } if (!$allThumbnailsExists) { if ($imageManager->_isImage($file->getRealPath())) { ThumbnailGenerator::createThumbnail($file->getPath(), $fileNamePlain, $fileExtension, $imageManager, true); } } $fileCounter++; $objProcessFile->write($fileCounter / $imageFilesCount * 100); } $objProcessFile->write(100); die; }
/** * Gets the themes pages file content * @access public * @param string $filePath * @param string $relativeFilePath * * @return string $fileContent */ function getFilesContent($filePath, $relativeFilePath) { global $objTemplate, $_ARRAYLANG; if (file_exists($filePath)) { $objImageManager = new \ImageManager(); $fileIsImage = $objImageManager->_isImage($filePath); $contenthtml = ''; if (!$fileIsImage) { $contenthtml = file_get_contents($filePath); $contenthtml = preg_replace('/\\{([A-Z0-9_]*?)\\}/', '[[\\1]]', $contenthtml); $contenthtml = htmlspecialchars($contenthtml); } $objTemplate->setVariable(array('CONTENT_HTML' => $contenthtml)); if ($fileIsImage) { $objTemplate->setVariable(array('THEMES_CONTENT_IMAGE_PATH' => $relativeFilePath)); $objTemplate->touchBlock('template_image'); $objTemplate->hideBlock('template_content'); $objTemplate->hideBlock('file_actions_bottom'); $objTemplate->hideBlock('file_editor_fullscreen'); } else { \JS::activate('ace'); $pathInfo = pathinfo($filePath, PATHINFO_EXTENSION); $mode = 'html'; switch ($pathInfo) { case 'html': case 'css': $mode = $pathInfo; break; case 'js': $mode = 'javascript'; break; case 'yml': case 'yaml': $mode = 'yaml'; break; } $jsCode = <<<CODE var editor; \$J(function(){ if (\$J("#editor").length) { editor = ace.edit("editor"); editor.getSession().setMode("ace/mode/{$mode}"); editor.setShowPrintMargin(false); editor.commands.addCommand({ name: "fullscreen", bindKey: "F11", exec: function(editor) { if (\$J('body').hasClass('fullScreen')) { \$J('body').removeClass('fullScreen'); \$J(editor.container).removeClass('fullScreen-editor'); cx.tools.StatusMessage.removeAllDialogs(); } else { \$J('body').addClass('fullScreen'); \$J(editor.container).addClass('fullScreen-editor'); cx.tools.StatusMessage.showMessage( "<div style='text-align: center;'><span style='cursor: pointer;' onClick=\\"editor.execCommand('fullscreen');\\">{$_ARRAYLANG['TXT_THEME_EXIT_FULLSCREEN']}</span></div>", null, null, null, {closeOnEscape: false} ); } editor.resize(); editor.focus(); } }); editor.focus(); editor.gotoLine(1); \$J('.fullscreen').click(function(){ editor.execCommand('fullscreen'); }); } \$J('#theme_content').submit(function(){ \$J('#editorContent').val(editor.getSession().getValue()); }); \$J('.select_all').click(function() { editor.selectAll(); }); \$J('input:reset').click(function() { editor.setValue(\$J('#editorContent').val(), -1); }); }); CODE; \JS::registerCode($jsCode); $objTemplate->touchBlock('file_editor_fullscreen'); $objTemplate->touchBlock('file_actions_bottom'); $objTemplate->touchBlock('template_content'); $objTemplate->hideBlock('template_image'); } } else { //TO-DO : } }