Created
March 9, 2017 12:23
-
-
Save eyecatchup/435c55634d6d1e8bf3a7ace8ab78ffc8 to your computer and use it in GitHub Desktop.
Standalone PHP script to extract a packed TYPO3 extension t3x package.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| <?php | |
| // Standalone PHP script to extract a packed TYPO3 extension (.t3x packages). | |
| // Based on snippets found here and there. License: WTFPL => do what you want. | |
| // Print usage | |
| function printUsageAndDie(){ | |
| global $argv; | |
| print <<<EOM | |
| ------------------------------------------------------------------------------ | |
| Usage: extract_t3x.php [filename.t3x] <directory> | |
| * filename.t3x = Name of your t3x-file | |
| * directory = optional extraction directory (default="unpacked_extension") | |
| ------------------------------------------------------------------------------ | |
| EOM; | |
| die(); | |
| } | |
| // Create the TYPO3 extension directory structure in the output directory. | |
| function autocreate_subdirs($dir) { | |
| $path = array(); | |
| $subdirs = explode("/", $dir); | |
| foreach ($subdirs as $subdir) { | |
| $path[] = $subdir; | |
| $fullPath = implode("/", $path); | |
| if ($fullPath && !file_exists($fullPath)) { | |
| $msg = !mkdir($fullPath) ? "ERROR: directory '%s' not created" : "OK: created directory '%s'"; | |
| sprintf($msg . PHP_EOL, $fullPath); | |
| } | |
| } | |
| } | |
| /** | |
| * Decodes extension upload array. | |
| * This kind of data is when an extension is uploaded to TER. | |
| * Stolen from SC_mod_tools_em_terconnection | |
| * | |
| * @param string Data stream | |
| * @return mixed Array with result on success, otherwise an error string. | |
| */ | |
| function decodeExchangeData($str) { | |
| $parts = explode(':', $str, 3); | |
| if ($parts[1] == 'gzcompress') { | |
| if (function_exists('gzuncompress')) { | |
| $parts[2] = gzuncompress($parts[2]); | |
| } else return 'Decoding Error: No decompressor available for compressed content. gzcompress()/gzuncompress() functions are not available!'; | |
| } | |
| if (md5($parts[2]) == $parts[0]) { | |
| $output = unserialize($parts[2]); | |
| if (is_array($output)) { | |
| return array($output, ''); | |
| } else return 'Error: Content could not be unserialized to an array. Strange (since MD5 hashes match!)'; | |
| } else return 'Error: MD5 mismatch. Maybe the extension file was downloaded and saved as a text file by the browser and thereby corrupted!? (Always select "All" filetype when saving extensions)'; | |
| } | |
| // Print usage if no command line args given. | |
| if (count($argv) <= 1) { | |
| printUsageAndDie(); | |
| } | |
| // Get t3x file from command line args. | |
| $extFile = $argv[1]; | |
| // Optional: Get output directory from command line args. | |
| $unpackDir = ($argv[2] != '') ? $argv[2] : "unpacked_extension"; | |
| // Check if the given t3x file exists. If not, print usage and exit. | |
| if (file_exists($extFile)) { | |
| print PHP_EOL . " Entpacke Datei: '$extFile'... " . PHP_EOL . PHP_EOL; | |
| } | |
| else { | |
| print PHP_EOL . " Datei: '$extFile' wurde leider nicht gefunden " . PHP_EOL; | |
| printUsageAndDie(); | |
| } | |
| // Start unpacking... | |
| $fileContent = file_get_contents($extFile); | |
| $ext = decodeExchangeData($fileContent); | |
| // Unpack extension(s)... | |
| foreach ($ext as $e) { | |
| if (is_array($e) && isset($e["EM_CONF"])) { | |
| // Create unpack directory. | |
| if (!file_exists($unpackDir)) { | |
| mkdir($unpackDir); | |
| } | |
| // Create extension sub-directories. | |
| $dirs = explode(",", $e["EM_CONF"]["createDirs"]); | |
| foreach ($dirs as $dir) { | |
| // Start in unpack directory if any. | |
| if ($unpackDir) { | |
| $dir = $unpackDir . "/" . $dir; | |
| } | |
| autocreate_subdirs($dir); | |
| } | |
| // Write files. | |
| foreach ($e["FILES"] as $file) { | |
| // Start in unpack directory. | |
| $path = empty($unpackDir) ? array() : array($unpackDir); | |
| $temp = explode("/", $file["name"]); | |
| // Separate file name and rest path. | |
| $fileName = array_pop($temp); | |
| $path = array_merge($path, $temp); | |
| unset($temp); | |
| // Create subdirectories (if neccessary). | |
| $dirPath = implode("/", $path); | |
| autocreate_subdirs($dirPath); | |
| // Write file. | |
| $path[] = $fileName; | |
| $fullPath = implode("/", $path); | |
| $handle = fopen($fullPath, "w"); | |
| if ($handle && fwrite($handle, $file["content"])) { | |
| fclose($handle); | |
| echo sprintf("OK: wrote file '%s'" . PHP_EOL, $fullPath); | |
| } else { | |
| echo sprintf("ERROR: file '%s' not written" . PHP_EOL, $fullPath); | |
| } | |
| } | |
| } | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment