Documentation TYPO3 par Ameos

class.em_index.php

00001 <?php
00002 /***************************************************************
00003 *  Copyright notice
00004 *
00005 *  (c) 1999-2005 Kasper Skaarhoj (kasperYYYY@typo3.com)
00006  * (c) 2005-2006 Karsten Dambekalns <karsten@typo3.org>
00007 *  All rights reserved
00008 *
00009 *  This script is part of the TYPO3 project. The TYPO3 project is
00010 *  free software; you can redistribute it and/or modify
00011 *  it under the terms of the GNU General Public License as published by
00012 *  the Free Software Foundation; either version 2 of the License, or
00013 *  (at your option) any later version.
00014 *
00015 *  The GNU General Public License can be found at
00016 *  http://www.gnu.org/copyleft/gpl.html.
00017 *  A copy is found in the textfile GPL.txt and important notices to the license
00018 *  from the author is found in LICENSE.txt distributed with these scripts.
00019 *
00020 *
00021 *  This script is distributed in the hope that it will be useful,
00022 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
00023 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00024 *  GNU General Public License for more details.
00025 *
00026 *  This copyright notice MUST APPEAR in all copies of the script!
00027 ***************************************************************/
00170         // Include classes needed:
00171 require_once(PATH_t3lib.'class.t3lib_tcemain.php');
00172 require_once(PATH_t3lib.'class.t3lib_install.php');
00173 require_once(PATH_t3lib.'class.t3lib_tsstyleconfig.php');
00174 require_once(PATH_t3lib.'class.t3lib_scbase.php');
00175 
00176 require_once('class.em_xmlhandler.php');
00177 require_once('class.em_terconnection.php');
00178 require_once('class.em_unzip.php');
00179 
00180         // from tx_ter by Robert Lemke
00181 define('TX_TER_RESULT_EXTENSIONSUCCESSFULLYUPLOADED', '10504');
00182 
00183 define('EM_INSTALL_VERSION_MIN', 1);
00184 define('EM_INSTALL_VERSION_MAX', 2);
00185 define('EM_INSTALL_VERSION_STRICT', 3);
00186 
00195 class SC_mod_tools_em_index extends t3lib_SCbase {
00196 
00197                 // Internal, static:
00198         var $versionDiffFactor = 1;             // This means that version difference testing for import is detected for sub-versions only, not dev-versions. Default: 1000
00199         var $systemInstall = 0;                         // If "1" then installs in the sysext directory is allowed. Default: 0
00200         var $requiredExt = '';                          // List of required extension (from TYPO3_CONF_VARS)
00201         var $maxUploadSize = 31457280;          // Max size in bytes of extension upload to repository
00202         var $kbMax = 500;                                       // Max size in kilobytes for files to be edited.
00203         var $doPrintContent = true;                     // If set (default), the function printContent() will echo the content which was collected in $this->content. You can set this to FALSE in order to echo content from elsewhere, fx. when using outbut buffering
00204 
00209         var $defaultCategories = Array(
00210                 'cat' => Array (
00211                         'be' => array(),
00212                         'module' => array(),
00213                         'fe' => array(),
00214                         'plugin' => array(),
00215                         'misc' => array(),
00216                         'services' => array(),
00217                         'templates' => array(),
00218                         'example' => array(),
00219                         'doc' => array()
00220                 )
00221         );
00222 
00227         var $categories = Array(
00228                 'be' => 'Backend',
00229                 'module' => 'Backend Modules',
00230                 'fe' => 'Frontend',
00231                 'plugin' => 'Frontend Plugins',
00232                 'misc' => 'Miscellaneous',
00233                 'services' => 'Services',
00234                 'templates' => 'Templates',
00235                 'example' => 'Examples',
00236                 'doc' => 'Documentation'
00237         );
00238 
00243         var $states = Array (
00244                 'alpha' => 'Alpha',
00245                 'beta' => 'Beta',
00246                 'stable' => 'Stable',
00247                 'experimental' => 'Experimental',
00248                 'test' => 'Test',
00249                 'obsolete' => 'Obsolete',
00250         );
00251 
00255         var $stateColors = Array (
00256                 'alpha' => '#d12438',
00257                 'beta' => '#97b17e',
00258                 'stable' => '#3bb65c',
00259                 'experimental' => '#007eba',
00260                 'test' => '#979797',
00261                 'obsolete' => '#000000',
00262         );
00263 
00267         var $typeLabels = Array (
00268                 'S' => 'System',
00269                 'G' => 'Global',
00270                 'L' => 'Local',
00271         );
00272         var $typeDescr = Array (
00273                 'S' => 'System extension (typo3/sysext/) - Always distributed with source code (Static).',
00274                 'G' => 'Global extensions (typo3/ext/) - Available for shared source on server (Dynamic).',
00275                 'L' => 'Local extensions (typo3conf/ext/) - Local for this TYPO3 installation only (Dynamic).',
00276         );
00277         var $typePaths = Array();                       // Also static, set in init()
00278         var $typeBackPaths = Array();           // Also static, set in init()
00279 
00280         var $typeRelPaths = Array (
00281                 'S' => 'sysext/',
00282                 'G' => 'ext/',
00283                 'L' => '../typo3conf/ext/',
00284         );
00285 
00286         var $detailCols = Array (
00287                 0 => 2,
00288                 1 => 5,
00289                 2 => 6,
00290                 3 => 6,
00291                 4 => 4,
00292                 5 => 1
00293         );
00294 
00295         var $fe_user = array(
00296                 'username' => '',
00297                 'password' => '',
00298         );
00299 
00300         var $privacyNotice = 'When you interact with the online repository, server information may be sent and stored in the repository for statistics.';
00301         var $editTextExtensions = 'html,htm,txt,css,tmpl,inc,php,sql,conf,cnf,pl,pm,sh,xml,ChangeLog';
00302         var $nameSpaceExceptions = 'beuser_tracking,design_components,impexp,static_file_edit,cms,freesite,quickhelp,classic_welcome,indexed_search,sys_action,sys_workflows,sys_todos,sys_messages,direct_mail,sys_stat,tt_address,tt_board,tt_calender,tt_guest,tt_links,tt_news,tt_poll,tt_rating,tt_products,setup,taskcenter,tsconfig_help,context_help,sys_note,tstemplate,lowlevel,install,belog,beuser,phpmyadmin,aboutmodules,imagelist,setup,taskcenter,sys_notepad,viewpage,adodb';
00303 
00304 
00305 
00306 
00307 
00308                 // Default variables for backend modules
00309         var $MCONF = array();                           // Module configuration
00310         var $MOD_MENU = array();                        // Module menu items
00311         var $MOD_SETTINGS = array();            // Module session settings
00312         var $doc;                                                       // Document Template Object
00313         var $content;                                           // Accumulated content
00314 
00315         var $inst_keys = array();                       // Storage of installed extensions
00316         var $gzcompress = 0;                            // Is set true, if system support compression.
00317 
00318         var $terConnection;                     // instance of TER connection handler
00319 
00320                 // GPvars:
00321         var $CMD = array();                                     // CMD array
00322         var $listRemote;                                        // If set, connects to remote repository
00323         var $lookUpStr;                                         // Search string when listing local extensions
00324 
00325 
00326 
00327 
00328         /*********************************
00329         *
00330         * Standard module initialization
00331         *
00332         *********************************/
00333 
00339         function init() {
00340                 global $BE_USER,$LANG,$BACK_PATH,$TYPO3_CONF_VARS;
00341 
00342                 // Setting paths of install scopes:
00343                 $this->typePaths = Array (
00344                         'S' => TYPO3_mainDir.'sysext/',
00345                         'G' => TYPO3_mainDir.'ext/',
00346                         'L' => 'typo3conf/ext/'
00347                 );
00348                 $this->typeBackPaths = Array (
00349                         'S' => '../../../',
00350                         'G' => '../../../',
00351                         'L' => '../../../../'.TYPO3_mainDir
00352                 );
00353 
00354                 // Setting module configuration:
00355                 $this->MCONF = $GLOBALS['MCONF'];
00356 
00357                 // Setting GPvars:
00358                 $this->CMD = t3lib_div::_GP('CMD');
00359                 $this->lookUpStr = t3lib_div::_GP('_lookUp');
00360                 $this->listRemote = t3lib_div::_GP('ter_connect');
00361                 $this->listRemote_search = t3lib_div::_GP('ter_search');
00362 
00363 
00364                         // Configure menu
00365                 $this->menuConfig();
00366 
00367                         // Setting internal static:
00368                 if ($TYPO3_CONF_VARS['EXT']['allowSystemInstall'])      $this->systemInstall = 1;
00369                 $this->requiredExt = t3lib_div::trimExplode(',',$TYPO3_CONF_VARS['EXT']['requiredExt'],1);
00370 
00371 
00372                         // Initialize helper object
00373                 $this->terConnection = t3lib_div::makeInstance('SC_mod_tools_em_terconnection');
00374                 $this->terConnection->emObj =& $this;
00375                 $this->terConnection->wsdlURL = $TYPO3_CONF_VARS['EXT']['em_wsdlURL'];
00376                 $this->xmlhandler = t3lib_div::makeInstance('SC_mod_tools_em_xmlhandler');
00377                 $this->xmlhandler->emObj =& $this;
00378                 $this->xmlhandler->useUnsupported = $this->MOD_SETTINGS['display_unsupported'];
00379                 $this->xmlhandler->useObsolete = $this->MOD_SETTINGS['display_obsolete'];
00380 
00381                         // Initialize Document Template object:
00382                 $this->doc = t3lib_div::makeInstance('noDoc');
00383                 $this->doc->backPath = $BACK_PATH;
00384                 $this->doc->docType = 'xhtml_trans';
00385 
00386                         // JavaScript
00387                 $this->doc->JScode = $this->doc->wrapScriptTags('
00388                         script_ended = 0;
00389                         function jumpToUrl(URL) {       //
00390                                 window.location.href = URL;
00391                         }
00392                 ');
00393                 $this->doc->form = '<form action="index.php" method="post" name="pageform">';
00394 
00395                 // Descriptions:
00396                 $this->descrTable = '_MOD_'.$this->MCONF['name'];
00397                 if ($BE_USER->uc['edit_showFieldHelp']) {
00398                         $LANG->loadSingleTableDescription($this->descrTable);
00399                 }
00400 
00401                 // Setting username/password etc. for upload-user:
00402                 $this->fe_user['username'] = $this->MOD_SETTINGS['fe_u'];
00403                 $this->fe_user['password'] = $this->MOD_SETTINGS['fe_p'];
00404                 parent::init();
00405                 $this->handleExternalFunctionValue('singleDetails');
00406         }
00407 
00419         function handleExternalFunctionValue($MM_key='function', $MS_value=NULL)        {
00420                 $MS_value = is_null($MS_value) ? $this->MOD_SETTINGS[$MM_key] : $MS_value;
00421                 $externalItems = $this->getExternalItemConfig($this->MCONF['name'],$MM_key,$MS_value);
00422                 if (is_array($externalItems))   $this->extClassConf = array_merge($externalItems,is_array($this->extClassConf)?$this->extClassConf:array());
00423                 if (is_array($this->extClassConf) && $this->extClassConf['path'])       {
00424                         $this->include_once[]=$this->extClassConf['path'];
00425                 }
00426         }
00427 
00433         function menuConfig()   {
00434                 global $BE_USER, $TYPO3_CONF_VARS;
00435 
00436                 // MENU-ITEMS:
00437                 $this->MOD_MENU = array(
00438                         'function' => array(
00439                                 0 => 'Loaded extensions',
00440                                 1 => 'Install extensions',
00441                                 2 => 'Import extensions',
00442                                 4 => 'Translation handling',
00443                                 3 => 'Settings',
00444                         ),
00445                         'listOrder' => array(
00446                                 'cat' => 'Category',
00447                                 'author_company' => 'Author',
00448                                 'state' => 'State',
00449                                 'type' => 'Type'
00450                         ),
00451                         'display_details' => array(
00452                                 1 => 'Details',
00453                                 0 => 'Description',
00454                                 2 => 'More details',
00455 
00456                                 3 => 'Technical (takes time!)',
00457                                 4 => 'Validating (takes time!)',
00458                                 5 => 'Changed? (takes time!)',
00459                         ),
00460                         'display_shy' => '',
00461                         'display_own' => '',
00462                         'display_unsupported' => '',
00463                         'display_obsolete' => '',
00464 
00465                         'singleDetails' => array(
00466                                 'info' => 'Information',
00467                                 'edit' => 'Edit files',
00468                                 'backup' => 'Backup/Delete',
00469                                 'dump' => 'Dump DB',
00470                                 'upload' => 'Upload to TER',
00471                                 'updateModule' => 'UPDATE!',
00472                         ),
00473                         'fe_u' => '',
00474                         'fe_p' => '',
00475 
00476                         'mirrorListURL' => '',
00477                         'rep_url' => '',
00478                         'extMirrors' => '',
00479                         'selectedMirror' => '',
00480 
00481                         'selectedLanguages' => ''
00482                 );
00483 
00484                 $this->MOD_MENU['singleDetails'] = $this->mergeExternalItems($this->MCONF['name'],'singleDetails',$this->MOD_MENU['singleDetails']);
00485 
00486                 // page/be_user TSconfig settings and blinding of menu-items
00487                 if (!$BE_USER->getTSConfigVal('mod.'.$this->MCONF['name'].'.allowTVlisting'))   {
00488                         unset($this->MOD_MENU['display_details'][3]);
00489                         unset($this->MOD_MENU['display_details'][4]);
00490                         unset($this->MOD_MENU['display_details'][5]);
00491                 }
00492 
00493                 // CLEANSE SETTINGS
00494                 $this->MOD_SETTINGS = t3lib_BEfunc::getModuleData($this->MOD_MENU, t3lib_div::_GP('SET'), $this->MCONF['name']);
00495 
00496                 if ($this->MOD_SETTINGS['function']==2) {
00497                         // If listing from online repository, certain items are removed though:
00498                         unset($this->MOD_MENU['listOrder']['type']);
00499                         unset($this->MOD_MENU['display_details'][2]);
00500                         unset($this->MOD_MENU['display_details'][3]);
00501                         unset($this->MOD_MENU['display_details'][4]);
00502                         unset($this->MOD_MENU['display_details'][5]);
00503                         $this->MOD_SETTINGS = t3lib_BEfunc::getModuleData($this->MOD_MENU, t3lib_div::_GP('SET'), $this->MCONF['name']);
00504                 }
00505                 parent::menuConfig();
00506         }
00507 
00513         function main() {
00514                 global $BE_USER,$LANG,$TYPO3_CONF_VARS;
00515 
00516                 if (empty($this->MOD_SETTINGS['mirrorListURL'])) $this->MOD_SETTINGS['mirrorListURL'] = $TYPO3_CONF_VARS['EXT']['em_mirrorListURL'];
00517 
00518                 // Starting page:
00519                 $this->content.=$this->doc->startPage('Extension Manager');
00520                 $this->content.=$this->doc->header('Extension Manager');
00521                 $this->content.=$this->doc->spacer(5);
00522 
00523                 // Commands given which is executed regardless of main menu setting:
00524                 if ($this->CMD['showExt'])      {       // Show details for a single extension
00525                         $this->showExtDetails($this->CMD['showExt']);
00526                 } elseif ($this->CMD['requestInstallExtensions'])       {       // Show details for a single extension
00527                                 $this->requestInstallExtensions($this->CMD['requestInstallExtensions']);
00528                 } elseif ($this->CMD['importExt'] || $this->CMD['uploadExt'])   {       // Imports an extension from online rep.
00529                         $err = $this->importExtFromRep($this->CMD['importExt'],$this->CMD['extVersion'],$this->CMD['loc'],$this->CMD['uploadExt']);
00530                         if ($err)       {
00531                                 $this->content.=$this->doc->section('',$GLOBALS['TBE_TEMPLATE']->rfw($err));
00532                         }
00533                         if(!$err && $this->CMD['importExt']) {
00534                                 $this->installTranslationsForExtension($this->CMD['importExt'], $this->getMirrorURL());
00535                         }
00536                 } elseif ($this->CMD['importExtInfo'])  {       // Gets detailed information of an extension from online rep.
00537                         $this->importExtInfo($this->CMD['importExtInfo'],$this->CMD['extVersion']);
00538                 } else {        // No command - we show what the menu setting tells us:
00539 
00540                         $menu = $LANG->sL('LLL:EXT:lang/locallang_core.php:labels.menu').' '.
00541                         t3lib_BEfunc::getFuncMenu(0,'SET[function]',$this->MOD_SETTINGS['function'],$this->MOD_MENU['function']);
00542 
00543                         if (t3lib_div::inList('0,1,2',$this->MOD_SETTINGS['function'])) {
00544                                 $menu.='&nbsp;Group by:&nbsp;'.t3lib_BEfunc::getFuncMenu(0,'SET[listOrder]',$this->MOD_SETTINGS['listOrder'],$this->MOD_MENU['listOrder']).
00545                                 '&nbsp;&nbsp;Show:&nbsp;'.t3lib_BEfunc::getFuncMenu(0,'SET[display_details]',$this->MOD_SETTINGS['display_details'],$this->MOD_MENU['display_details']).'<br />';
00546                         }
00547                         if (t3lib_div::inList('0,1',$this->MOD_SETTINGS['function']))   {
00548                                 $menu.='Display shy extensions:&nbsp;&nbsp;'.t3lib_BEfunc::getFuncCheck(0,'SET[display_shy]',$this->MOD_SETTINGS['display_shy']);
00549                         }
00550                         if (t3lib_div::inList('2',$this->MOD_SETTINGS['function']) && strlen($this->fe_user['username']))       {
00551                                 $menu.='Only my extensions:&nbsp;&nbsp;'.t3lib_BEfunc::getFuncCheck(0,'SET[display_own]',$this->MOD_SETTINGS['display_own']);
00552                         }
00553                         if (t3lib_div::inList('0,1,2',$this->MOD_SETTINGS['function'])) {
00554                                 $menu.='&nbsp;&nbsp;Show obsolete:&nbsp;&nbsp;'.t3lib_BEfunc::getFuncCheck(0,'SET[display_obsolete]',$this->MOD_SETTINGS['display_obsolete']);
00555                         }
00556 
00557                         $this->content.=$this->doc->section('','<span class="nobr">'.$menu.'</span>');
00558                         $this->content.=$this->doc->spacer(10);
00559 
00560                         switch((string)$this->MOD_SETTINGS['function']) {
00561                                 case '0':
00562                                         // Lists loaded (installed) extensions
00563                                         $this->extensionList_loaded();
00564                                         break;
00565                                 case '1':
00566                                         // Lists the installed (available) extensions
00567                                         $this->extensionList_installed();
00568                                         break;
00569                                 case '2':
00570                                         // Lists the extensions available from online rep.
00571                                         $this->extensionList_import();
00572                                         break;
00573                                 case '3':
00574                                         // Shows the settings screen
00575                                         $this->alterSettings();
00576                                         break;
00577                                 case '4':
00578                                         // Allows to set the translation preferences and check the status
00579                                         $this->translationHandling();
00580                                         break;
00581                                 default:
00582                                         $this->extObjContent();
00583                                         break;
00584                         }
00585                 }
00586 
00587                 // Shortcuts:
00588                 if ($BE_USER->mayMakeShortcut())        {
00589                         $this->content.=$this->doc->spacer(20).$this->doc->section('',$this->doc->makeShortcutIcon('CMD','function',$this->MCONF['name']));
00590                 }
00591         }
00592 
00598         function printContent() {
00599                 if ($this->doPrintContent) {
00600                         $this->content.= $this->doc->endPage();
00601                         echo $this->content;
00602                 }
00603         }
00604 
00605 
00606 
00607 
00608 
00609 
00610 
00611 
00612 
00613 
00614         /*********************************
00615         *
00616         * Function Menu Applications
00617         *
00618         *********************************/
00619 
00625         function extensionList_loaded() {
00626                 global $TYPO3_LOADED_EXT;
00627 
00628                 list($list,$cat) = $this->getInstalledExtensions();
00629 
00630                 // Loaded extensions
00631                 $content = '';
00632                 $lines = array();
00633 
00634                 // Available extensions
00635                 if (is_array($cat[$this->MOD_SETTINGS['listOrder']]))   {
00636                         $content='';
00637                         $lines=array();
00638                         $lines[] = $this->extensionListRowHeader(' class="bgColor5"',array('<td><img src="clear.gif" width="1" height="1" alt="" /></td>'));
00639 
00640                         foreach($cat[$this->MOD_SETTINGS['listOrder']] as $catName => $extEkeys)        {
00641                                 natcasesort($extEkeys);
00642                                 reset($extEkeys);
00643                                 $extensions = array();
00644                                 while(list($extKey)=each($extEkeys))    {
00645                                         if (array_key_exists($extKey,$TYPO3_LOADED_EXT) && ($this->MOD_SETTINGS['display_shy'] || !$list[$extKey]['EM_CONF']['shy']) && $this->searchExtension($extKey,$list[$extKey])) {
00646                                                 if (in_array($extKey, $this->requiredExt))      {
00647                                                         $loadUnloadLink = '<strong>'.$GLOBALS['TBE_TEMPLATE']->rfw('Rq').'</strong>';
00648                                                 } else {
00649                                                         $loadUnloadLink = '<a href="'.htmlspecialchars('index.php?CMD[showExt]='.$extKey.'&CMD[remove]=1').'">'.$this->removeButton().'</a>';
00650                                                 }
00651 
00652                                                 $extensions[] = $this->extensionListRow($extKey,$list[$extKey],array('<td class="bgColor">'.$loadUnloadLink.'</td>'));
00653                                         }
00654                                 }
00655                                 if(count($extensions)) {
00656                                         $lines[]='<tr><td colspan="'.(3+$this->detailCols[$this->MOD_SETTINGS['display_details']]).'"><br /></td></tr>';
00657                                         $lines[]='<tr><td colspan="'.(3+$this->detailCols[$this->MOD_SETTINGS['display_details']]).'"><img src="'.$GLOBALS['BACK_PATH'].'gfx/i/sysf.gif" width="18" height="16" align="top" alt="" /><strong>'.$this->listOrderTitle($this->MOD_SETTINGS['listOrder'],$catName).'</strong></td></tr>';
00658                                         $lines[] = implode(chr(10),$extensions);
00659                                 }
00660                         }
00661                 }
00662 
00663                 $content.= t3lib_BEfunc::cshItem('_MOD_tools_em', 'loaded', $GLOBALS['BACK_PATH'],'');
00664 
00665                 $content.= 'Look up: <input type="text" name="_lookUp" value="'.htmlspecialchars($this->lookUpStr).'" /><input type="submit" value="Search"/><br/><br/>';
00666 
00667                 $content.= '
00668 
00669                         <!-- Loaded Extensions List -->
00670                         <table border="0" cellpadding="2" cellspacing="1">'.implode('',$lines).'</table>';
00671 
00672                 $this->content.=$this->doc->section('Loaded Extensions',$content,0,1);
00673         }
00674 
00680         function extensionList_installed()      {
00681                 global $TYPO3_LOADED_EXT;
00682 
00683                 list($list,$cat)=$this->getInstalledExtensions();
00684 
00685                 // Available extensions
00686                 if (is_array($cat[$this->MOD_SETTINGS['listOrder']]))   {
00687                         $content='';
00688                         $lines=array();
00689                         $lines[]=$this->extensionListRowHeader(' class="bgColor5"',array('<td><img src="clear.gif" width="18" height="1" alt="" /></td>'));
00690 
00691                         $allKeys=array();
00692                         foreach($cat[$this->MOD_SETTINGS['listOrder']] as $catName => $extEkeys)        {
00693                                 if(!$this->MOD_SETTINGS['display_obsolete'] && $catName=='obsolete') continue;
00694 
00695                                 $allKeys[]='';
00696                                 $allKeys[]='TYPE: '.$catName;
00697 
00698                                 natcasesort($extEkeys);
00699                                 reset($extEkeys);
00700                                 $extensions = array();
00701                                 while(list($extKey)=each($extEkeys))    {
00702                                         $allKeys[]=$extKey;
00703                                         if ((!$list[$extKey]['EM_CONF']['shy'] || $this->MOD_SETTINGS['display_shy']) &&
00704                                                         ($list[$extKey]['EM_CONF']['state']!='obsolete' || $this->MOD_SETTINGS['display_obsolete'])
00705                                          && $this->searchExtension($extKey,$list[$extKey]))     {
00706                                                 $loadUnloadLink = t3lib_extMgm::isLoaded($extKey)?
00707                                                 '<a href="'.htmlspecialchars('index.php?CMD[showExt]='.$extKey.'&CMD[remove]=1&CMD[clrCmd]=1&SET[singleDetails]=info').'">'.$this->removeButton().'</a>':
00708                                                 '<a href="'.htmlspecialchars('index.php?CMD[showExt]='.$extKey.'&CMD[load]=1&CMD[clrCmd]=1&SET[singleDetails]=info').'">'.$this->installButton().'</a>';
00709                                                 if (in_array($extKey,$this->requiredExt))       {
00710                                                         $loadUnloadLink='<strong>'.$GLOBALS['TBE_TEMPLATE']->rfw('Rq').'</strong>';
00711                                                 }
00712                                                 $theRowClass = t3lib_extMgm::isLoaded($extKey)? 'em-listbg1' : 'em-listbg2';
00713                                                 $extensions[]=$this->extensionListRow($extKey,$list[$extKey],array('<td class="bgColor">'.$loadUnloadLink.'</td>'),$theRowClass);
00714                                         }
00715                                 }
00716                                 if(count($extensions)) {
00717                                         $lines[]='<tr><td colspan="'.(3+$this->detailCols[$this->MOD_SETTINGS['display_details']]).'"><br /></td></tr>';
00718                                         $lines[]='<tr><td colspan="'.(3+$this->detailCols[$this->MOD_SETTINGS['display_details']]).'"><img src="'.$GLOBALS['BACK_PATH'].'gfx/i/sysf.gif" width="18" height="16" align="top" alt="" /><strong>'.$this->listOrderTitle($this->MOD_SETTINGS['listOrder'],$catName).'</strong></td></tr>';
00719                                         $lines[] = implode(chr(10),$extensions);
00720                                 }
00721                         }
00722 
00723                         $content.='
00724 
00725 
00726 <!--
00727 EXTENSION KEYS:
00728 
00729 '.trim(implode(chr(10),$allKeys)).'
00730 
00731 -->
00732 
00733 ';
00734 
00735                         $content.= t3lib_BEfunc::cshItem('_MOD_tools_em', 'avail', $GLOBALS['BACK_PATH'],'|<br/>');
00736                         $content.= 'If you want to use an extension in TYPO3, you should simply click the "plus" button '.$this->installButton().' . <br />
00737                                                 Installed extensions can also be removed again - just click the remove button '.$this->removeButton().' .<br /><br />';
00738 
00739                         $content.= 'Look up: <input type="text" name="_lookUp" value="'.htmlspecialchars($this->lookUpStr).'" /><input type="submit" value="Search"/><br/><br/>';
00740 
00741                         $content.= '<table border="0" cellpadding="2" cellspacing="1">'.implode('',$lines).'</table>';
00742 
00743                         $this->content.=$this->doc->section('Available Extensions - Grouped by: '.$this->MOD_MENU['listOrder'][$this->MOD_SETTINGS['listOrder']],$content,0,1);
00744                 }
00745         }
00746 
00752         function extensionList_import() {
00753                 global $TYPO3_LOADED_EXT;
00754                 $content='';
00755 
00756                         // Listing from online repository:
00757                 if ($this->listRemote)  {
00758                         list($inst_list,) = $this->getInstalledExtensions();
00759                         $this->inst_keys = array_flip(array_keys($inst_list));
00760 
00761                         $this->detailCols[1]+=6;
00762 
00763                                 // see if we have an extensionlist at all
00764                         $this->xmlhandler->loadExtensionsXML();
00765                         if (!count($this->xmlhandler->extensionsXML))   {
00766                                 $content .= $this->fetchMetaData('extensions');
00767                         }
00768 
00769                         if($this->MOD_SETTINGS['display_own'] && strlen($this->fe_user['username'])) {
00770                                 $this->xmlhandler->searchExtensionsXML($this->listRemote_search, $this->fe_user['username']);
00771                         } else {
00772                                 $this->xmlhandler->searchExtensionsXML($this->listRemote_search);
00773                         }
00774                         if (count($this->xmlhandler->extensionsXML))    {
00775                                 list($list,$cat) = $this->prepareImportExtList();
00776 
00777                                         // Available extensions
00778                                 if (is_array($cat[$this->MOD_SETTINGS['listOrder']]))   {
00779                                         $lines=array();
00780                                         $lines[]=$this->extensionListRowHeader(' class="bgColor5"',array('<td><img src="clear.gif" width="18" height="1" alt="" /></td>'),1);
00781 
00782                                         foreach($cat[$this->MOD_SETTINGS['listOrder']] as $catName => $extEkeys)        {
00783                                                 if (count($extEkeys))   {
00784                                                         $lines[]='<tr><td colspan="'.(3+$this->detailCols[$this->MOD_SETTINGS['display_details']]).'"><br /></td></tr>';
00785                                                         $lines[]='<tr><td colspan="'.(3+$this->detailCols[$this->MOD_SETTINGS['display_details']]).'"><img src="'.$GLOBALS['BACK_PATH'].'gfx/i/sysf.gif" width="18" height="16" align="top" alt="" /><strong>'.$this->listOrderTitle($this->MOD_SETTINGS['listOrder'],$catName).'</strong></td></tr>';
00786 
00787                                                         natcasesort($extEkeys);
00788                                                         reset($extEkeys);
00789                                                         while(list($extKey)=each($extEkeys))    {
00790                                                                 $version = array_keys($list[$extKey]['versions']);
00791                                                                 $version = end($version);
00792                                                                 $ext = $list[$extKey]['versions'][$version];
00793                                                                 $ext['downloadcounter_all'] = $list[$extKey]['downloadcounter'];
00794                                                                 $ext['_ICON'] = $list[$extKey]['_ICON'];
00795                                                                 $loadUnloadLink='';
00796                                                                 if ($inst_list[$extKey]['type']!='S' && (!isset($inst_list[$extKey]) || $this->versionDifference($version,$inst_list[$extKey]['EM_CONF']['version'],$this->versionDiffFactor))) {
00797                                                                         if (isset($inst_list[$extKey])) {
00798                                                                                         // update
00799                                                                                 $loc= ($inst_list[$extKey]['type']=='G'?'G':'L');
00800                                                                                 $aUrl = 'index.php?CMD[importExt]='.$extKey.'&CMD[extVersion]='.$version.'&CMD[loc]='.$loc;
00801                                                                                 $loadUnloadLink.= '<a href="'.htmlspecialchars($aUrl).'"><img src="'.$GLOBALS['BACK_PATH'].'gfx/import_update.gif" width="12" height="12" title="Update the extension in \''.($loc=='G'?'global':'local').'\' from online repository to server" alt="" /></a>';
00802                                                                         } else {
00803                                                                                         // import
00804                                                                                 $aUrl = 'index.php?CMD[importExt]='.$extKey.'&CMD[extVersion]='.$version.'&CMD[loc]=L';
00805                                                                                 $loadUnloadLink.= '<a href="'.htmlspecialchars($aUrl).'"><img src="'.$GLOBALS['BACK_PATH'].'gfx/import.gif" width="12" height="12" title="Import this extension to \'local\' dir typo3conf/ext/ from online repository." alt="" /></a>';
00806                                                                         }
00807                                                                 } else {
00808                                                                         $loadUnloadLink = '&nbsp;';
00809                                                                 }
00810 
00811                                                                 if (isset($inst_list[$extKey])) {
00812                                                                         $theRowClass = t3lib_extMgm::isLoaded($extKey) ? 'em-listbg1' : 'em-listbg2';
00813                                                                 } else {
00814                                                                         $theRowClass = 'em-listbg3';
00815                                                                 }
00816 
00817                                                                 $lines[]=$this->extensionListRow($extKey,$ext,array('<td class="bgColor">'.$loadUnloadLink.'</td>'),$theRowClass,$inst_list,1,'index.php?CMD[importExtInfo]='.rawurlencode($extKey));
00818                                                         }
00819                                                 }
00820                                         }
00821 
00822                                                 // CSH:
00823                                         $content.= t3lib_BEfunc::cshItem('_MOD_tools_em', 'import_ter', $GLOBALS['BACK_PATH'],'|<br/>');
00824                                         $onsubmit = "window.location.href='index.php?ter_connect=1&ter_search='+escape(this.elements['_lookUp'].value);return false;";
00825                                         $content.= '</form><form action="index.php" method="post" onsubmit="'.htmlspecialchars($onsubmit).'">List or look up extensions<br />
00826                                                         <input type="text" name="_lookUp" value="'.htmlspecialchars($this->listRemote_search).'" /> <input type="submit" value="Look up" /><br /><br />';
00827 
00828                                         $content.= '
00829 
00830                                         <!-- TER Extensions list -->
00831                                         <table border="0" cellpadding="2" cellspacing="1">'.implode(chr(10),$lines).'</table>';
00832                                         $content.= '<br /><br /><strong>PRIVACY NOTICE:</strong><br /> '.$this->privacyNotice;
00833 
00834                                         $this->content.=$this->doc->section('Extensions in TYPO3 Extension Repository (online) - Grouped by: '.$this->MOD_MENU['listOrder'][$this->MOD_SETTINGS['listOrder']],$content,0,1);
00835 
00836                                                 // Plugins which are NOT uploaded to repository but present on this server.
00837                                         $content='';
00838                                         $lines=array();
00839                                         if (count($this->inst_keys))    {
00840                                                 reset($this->inst_keys);
00841                                                 while(list($extKey)=each($this->inst_keys))     {
00842                                                         if(strlen($this->listRemote_search) && !stristr($extKey,$this->listRemote_search)) continue;
00843 
00844                                                         $loadUnloadLink = t3lib_extMgm::isLoaded($extKey)?
00845                                                         '<a href="'.htmlspecialchars('index.php?CMD[showExt]='.$extKey.'&CMD[remove]=1&CMD[clrCmd]=1&SET[singleDetails]=info').'">'.$this->removeButton().'</a>':
00846                                                         '<a href="'.htmlspecialchars('index.php?CMD[showExt]='.$extKey.'&CMD[load]=1&CMD[clrCmd]=1&SET[singleDetails]=info').'">'.$this->installButton().'</a>';
00847                                                         if (in_array($extKey,$this->requiredExt))       $loadUnloadLink='<strong>'.$GLOBALS['TBE_TEMPLATE']->rfw('Rq').'</strong>';
00848                                                         $lines[]=$this->extensionListRow($extKey,$inst_list[$extKey],array('<td class="bgColor">'.$loadUnloadLink.'</td>'),t3lib_extMgm::isLoaded($extKey)?'em-listbg1':'em-listbg2');
00849                                                 }
00850                                         }
00851                                         if(count($lines)) {
00852                                                 $content.= 'This is the list of extensions which are available locally, but not in the repository.<br />The might be user-defined and should be prepended user_ then.<br /><br />';
00853                                                 $content.= '<table border="0" cellpadding="2" cellspacing="1">'.
00854                                                         $this->extensionListRowHeader(' class="bgColor5"',array('<td><img src="clear.gif" width="18" height="1" alt="" /></td>')).
00855                                                         implode('',$lines).'</table>';
00856                                                 $this->content.=$this->doc->spacer(20);
00857                                                 $this->content.=$this->doc->section('Extensions found only on this server',$content,0,1);
00858                                         }
00859                                 }
00860                         }       else {
00861                                 $content.= t3lib_BEfunc::cshItem('_MOD_tools_em', 'import_ter', $GLOBALS['BACK_PATH'],'|<br/>');
00862                                 $onsubmit = "window.location.href='index.php?ter_connect=1&ter_search='+escape(this.elements['_lookUp'].value);return false;";
00863                                 $content.= '</form><form action="index.php" method="post" onsubmit="'.htmlspecialchars($onsubmit).'">List or look up extensions<br />
00864                                         <input type="text" name="_lookUp" value="'.htmlspecialchars($this->listRemote_search).'" /> <input type="submit" value="Look up" /><br /><br />';
00865 
00866                                 $content.= '<p><strong>No matching extensions found.</strong></p>';
00867 
00868                                 $content.= '<br /><br /><strong>PRIVACY NOTICE:</strong><br /> '.$this->privacyNotice;
00869                                 $this->content.=$this->doc->section('Extensions in TYPO3 Extension Repository (online) - Grouped by: '.$this->MOD_MENU['listOrder'][$this->MOD_SETTINGS['listOrder']],$content,0,1);
00870                         }
00871                 } else {
00872                                 // CSH
00873                         $content.= t3lib_BEfunc::cshItem('_MOD_tools_em', 'import', $GLOBALS['BACK_PATH'],'|<br/>');
00874 
00875                         $onsubmit = "window.location.href='index.php?ter_connect=1&ter_search='+escape(this.elements['_lookUp'].value);return false;";
00876                         $content.= '</form><form action="index.php" method="post" onsubmit="'.htmlspecialchars($onsubmit).'">List or look up extensions<br />
00877                         <input type="text" name="_lookUp" value="" /> <input type="submit" value="Look up" /><br /><br />';
00878 
00879                         if ($this->CMD['fetchMetaData'])        {       // fetches mirror/extension data from online rep.
00880                                 $content .= $this->fetchMetaData($this->CMD['fetchMetaData']);
00881                         } else {
00882                                 $onCLick = "window.location.href='index.php?CMD[fetchMetaData]=extensions';return false;";
00883                                 $content.= 'Connect to the current mirror and retrieve the current list of available plugins from the TYPO3 Extension Repository.<br />
00884                                 <input type="submit" value="Retrieve/Update" onclick="'.htmlspecialchars($onCLick).'" />';
00885                                 if(is_file(PATH_site.'typo3temp/extensions.bin')) {
00886                                         $content .= ' (last update: '.date('Y-m-d H:i',filemtime(PATH_site.'typo3temp/extensions.bin')).')';
00887                                 }
00888                         }
00889 
00890                         $content .= '<br /><br /><strong>PRIVACY NOTICE:</strong><br />'.$this->privacyNotice;
00891 
00892                         $this->content.=$this->doc->section('Extensions in TYPO3 Extension Repository',$content,0,1);
00893                 }
00894 
00895                         // Upload:
00896                 if ($this->importAtAll())       {
00897                         $content= '</form><form action="index.php" enctype="'.$GLOBALS['TYPO3_CONF_VARS']['SYS']['form_enctype'].'" method="post">
00898                         Upload extension file (.t3x):<br />
00899                                 <input type="file" size="60" name="upload_ext_file" /><br />
00900                                 ... to location:<br />
00901                                 <select name="CMD[loc]">';
00902                         if ($this->importAsType('L'))   $content.='<option value="L">Local (../typo3conf/ext/)</option>';
00903                         if ($this->importAsType('G'))   $content.='<option value="G">Global (typo3/ext/)</option>';
00904                         if ($this->importAsType('S'))   $content.='<option value="S">System (typo3/sysext/)</option>';
00905                         $content.='</select><br />
00906         <input type="checkbox" value="1" name="CMD[uploadOverwrite]" /> Overwrite any existing extension!<br />
00907         <input type="submit" name="CMD[uploadExt]" value="Upload extension file" /><br />
00908                         ';
00909                 } else $content=$this->noImportMsg();
00910 
00911                 $this->content.=$this->doc->spacer(20);
00912                 $this->content.=$this->doc->section('Upload extension file directly (.t3x):',$content,0,1);
00913         }
00914 
00920         function alterSettings()        {
00921 
00922                         // Prepare the HTML output:
00923                 $content.= '
00924                         '.t3lib_BEfunc::cshItem('_MOD_tools_em', 'settings', $GLOBALS['BACK_PATH'],'|<br/>').'
00925                         <fieldset><legend>Security Settings</legend>
00926                         <table border="0" cellpadding="2" cellspacing="2">
00927                                 <tr class="bgColor4">
00928                                         <td>Enable unsupported extensions:</td>
00929                                         <td>'.t3lib_BEfunc::getFuncCheck(0,'SET[display_unsupported]',$this->MOD_SETTINGS['display_unsupported']).'</td>
00930                                 </tr>
00931                         </table>
00932                         <strong>Notice:</strong> Make sure you know what consequences enabling this checkbox might have. Check the information on typo3.org about security reviewing!
00933                         </fieldset>
00934                         <br />
00935                         <br />
00936                         <fieldset><legend>User Settings</legend>
00937                         <table border="0" cellpadding="2" cellspacing="2">
00938                                 <tr class="bgColor4">
00939                                         <td>Enter repository username:</td>
00940                                         <td><input type="text" name="SET[fe_u]" value="'.htmlspecialchars($this->MOD_SETTINGS['fe_u']).'" /></td>
00941                                 </tr>
00942                                 <tr class="bgColor4">
00943                                         <td>Enter repository password:</td>
00944                                         <td><input type="password" name="SET[fe_p]" value="'.htmlspecialchars($this->MOD_SETTINGS['fe_p']).'" /></td>
00945                                 </tr>
00946                         </table>
00947                         <strong>Notice:</strong> This is <em>not</em> your password to the TYPO3 backend! This user information is what is needed to log in at typo3.org with your account there!
00948                         </fieldset>
00949                         <br />
00950                         <br />
00951                         <fieldset><legend>Mirror selection</legend>
00952                         <table border="0" cellpadding="2" cellspacing="2">
00953                                 <tr class="bgColor4">
00954                                         <td>Enter mirror list URL:</td>
00955                                         <td><input type="text" size="50" name="SET[mirrorListURL]" value="'.htmlspecialchars($this->MOD_SETTINGS['mirrorListURL']).'" /></td>
00956                                 </tr>
00957                         </table>
00958                         <br />
00959                         <p>Select a mirror from below. This list is built from the online mirror list retrieved from the URL above.<br /><br /></p>
00960                         <fieldset><legend>Mirror list</legend>';
00961                 if(!empty($this->MOD_SETTINGS['mirrorListURL'])) {
00962                         if ($this->CMD['fetchMetaData'])        {       // fetches mirror/extension data from online rep.
00963                                 $content .= $this->fetchMetaData($this->CMD['fetchMetaData']);
00964                         } else {
00965                                 $content.= '<a href="index.php?CMD[fetchMetaData]=mirrors">Click here to reload the list.</a>';
00966                         }
00967                 }
00968                 $content .= '<br />
00969                         <table cellspacing="4" style="text-align:left; vertical-alignment:top;">
00970                         <tr><td>Use</td><td>Name</td><td>URL</td><td>Country</td><td>Sponsored by</td></tr>
00971                 ';
00972 
00973                 if (!strlen($this->MOD_SETTINGS['extMirrors'])) $this->fetchMetaData('mirrors');
00974                 $extMirrors = unserialize($this->MOD_SETTINGS['extMirrors']);
00975                 $extMirrors[''] = array('title'=>'Random (recommended!)');
00976                 ksort($extMirrors);
00977                 if(is_array($extMirrors)) {
00978                         foreach($extMirrors as $k => $v) {
00979                                 if(isset($v['sponsor'])) {
00980                                         $sponsor = '<a href="'.htmlspecialchars($v['sponsor']['link']).'" target="_new"><img src="'.$v['sponsor']['logo'].'" title="'.htmlspecialchars($v['sponsor']['name']).'" alt="'.htmlspecialchars($v['sponsor']['name']).'" /></a>';
00981                                 }
00982                                 $selected = ($this->MOD_SETTINGS['selectedMirror']==$k) ? 'checked="checked"' : '';
00983                                 $content.='<tr class="bgColor4">
00984                         <td><input type="radio" name="SET[selectedMirror]" value="'.$k.'" '.$selected.'/></td><td>'.htmlspecialchars($v['title']).'</td><td>'.htmlspecialchars($v['host'].$v['path']).'</td><td>'.$v['country'].'</td><td>'.$sponsor.'</td></tr>';
00985                         }
00986                 }
00987                 $content.= '
00988                         </table>
00989                         </fieldset>
00990                         <br />
00991                         <table border="0" cellpadding="2" cellspacing="2">
00992                                 <tr class="bgColor4">
00993                                         <td>Enter repository URL:</td>
00994                                         <td><input type="text" size="50" name="SET[rep_url]" value="'.htmlspecialchars($this->MOD_SETTINGS['rep_url']).'" /></td>
00995                                 </tr>
00996                         </table>
00997 
00998                         If you set a repository URL, this overrides the use of a mirror. Use this to select a specific (private) repository.<br />
00999                         </fieldset>
01000                         <br />
01001                         <input type="submit" value="Update" />
01002                 ';
01003 
01004                 $this->content.=$this->doc->section('Repository settings',$content,0,1);
01005         }
01006 
01012         function translationHandling()  {
01013                 global $LANG, $TYPO3_LOADED_EXT;
01014                 $LANG->includeLLFile('EXT:setup/mod/locallang.xml');
01015 
01016                 $incoming = t3lib_div::_POST('SET');
01017                 if(isset($incoming['selectedLanguages']) && is_array($incoming['selectedLanguages'])) {
01018                         t3lib_BEfunc::getModuleData($this->MOD_MENU, array('selectedLanguages' => serialize($incoming['selectedLanguages'])), $this->MCONF['name'], '', 'selectedLanguages');
01019                         $this->MOD_SETTINGS['selectedLanguages'] = serialize($incoming['selectedLanguages']);
01020                 }
01021 
01022                 $selectedLanguages = unserialize($this->MOD_SETTINGS['selectedLanguages']);
01023                 if(count($selectedLanguages)==1 && empty($selectedLanguages[0])) $selectedLanguages = array();
01024                 $theLanguages = t3lib_div::trimExplode('|',TYPO3_languages);
01025                 foreach($theLanguages as $val)  {
01026                         if ($val!='default')    {
01027                                 $localLabel = '  -  ['.htmlspecialchars($GLOBALS['LOCAL_LANG']['default']['lang_'.$val]).']';
01028                                 $selected = (is_array($selectedLanguages) && in_array($val, $selectedLanguages)) ? ' selected="selected"' : '';
01029                                 $opt[$GLOBALS['LOCAL_LANG']['default']['lang_'.$val].'--'.$val]='
01030              <option value="'.$val.'"'.$selected.'>'.$LANG->getLL('lang_'.$val,1).$localLabel.'</option>';
01031                         }
01032                 }
01033                 ksort($opt);
01034 
01035                         // Prepare the HTML output:
01036                 $content.= '
01037                         '.t3lib_BEfunc::cshItem('_MOD_tools_em', 'translation', $GLOBALS['BACK_PATH'],'|<br/>').'
01038                         <fieldset><legend>Translation Settings</legend>
01039                         <table border="0" cellpadding="2" cellspacing="2">
01040                                 <tr class="bgColor4">
01041                                         <td>Languages to fetch:</td>
01042                                         <td>
01043                                           <select name="SET[selectedLanguages][]" multiple="multiple" size="10">
01044                                           <option></option>'.
01045             implode('',$opt).'
01046             </select>
01047           </td>
01048                                 </tr>
01049                         </table>
01050                         <br />
01051                         <p>For the selected languages the EM tries to download and install translation files if available, whenever an extension is installed. (This replaces the <code>csh_*</code> extensions that were used to install core translations before TYPO3 version 4!)<br />
01052                         <br />To request an update/install for already loaded extensions, see below.</p>
01053                         </fieldset>
01054                         <br />
01055                         <input type="submit" value="Save selection" />
01056                         <br />
01057                         </fieldset>';
01058 
01059                 $this->content.=$this->doc->section('Translation settings',$content,0,1);
01060 
01061                 if(count($selectedLanguages)>0) {
01062                         $mirrorURL = $this->getMirrorURL();
01063                         $content = '<input type="button" value="Check status against repository" onclick="document.location.href=\''.t3lib_div::linkThisScript(array('l10n'=>'check')).'\'" />&nbsp;<input type="button" value="Update from repository" onclick="document.location.href=\''.t3lib_div::linkThisScript(array('l10n'=>'update')).'\'" />';
01064 
01065                         if(t3lib_div::_GET('l10n') == 'check') {
01066                                 $loadedExtensions = array_keys($TYPO3_LOADED_EXT);
01067                                 $loadedExtensions = array_diff($loadedExtensions,array('_CACHEFILE'));
01068 
01069                                         // Override content output - we now do that ourself:
01070                                 echo ($this->content . $this->doc->section('Translation status',$content,0,1));
01071                                 $this->doPrintContent = FALSE;
01072                                 flush();
01073 
01074                                 echo '
01075                                 <br />
01076                                 <br />
01077                                 <p id="progress-message">
01078                                         Checking translation status, please wait ...
01079                                 </p>
01080                                 <br />
01081                                 <div style="width:100%; height:20px; border: 1px solid black;">
01082                                         <div id="progress-bar" style="float: left; width: 0%; height: 20px; background-color:green;">&nbsp;</div>
01083                                         <div id="transparent-bar" style="float: left; width: 100%; height: 20px; background-color:'.$this->doc->bgColor2.';">&nbsp;</div>
01084                                 </div>
01085                                 <br />
01086                                 <br /><p>This table shows the status of the loaded extension\'s translations.</p><br />
01087                                 <table border="0" cellpadding="2" cellspacing="2">
01088                                         <tr class="bgColor2"><td>Extension key</td>
01089                                 ';
01090 
01091                                 foreach($selectedLanguages as $lang) {
01092                                         echo ('<td>'.$LANG->getLL('lang_'.$lang,1).'</td>');
01093                                 }
01094                                 echo ('</tr>');
01095 
01096                                 $counter = 1;
01097                                 foreach($loadedExtensions as $extKey) {
01098 
01099                                         $percentDone = intval (($counter / count($loadedExtensions)) * 100);
01100                                         echo ('
01101                                         <script>
01102                                                 document.getElementById("progress-bar").style.width = "'.$percentDone.'%";
01103                                                 document.getElementById("transparent-bar").style.width = "'.(100-$percentDone).'%";
01104                                                 document.getElementById("progress-message").firstChild.data="Checking translation status for extension \"'.$extKey.'\" ...";
01105                                         </script>
01106                                         ');
01107 
01108                                         flush();
01109                                         $translationStatusArr = $this->terConnection->fetchTranslationStatus($extKey,$mirrorURL);
01110 
01111                                         echo ('<tr class="bgColor4"><td>'.$extKey.'</td>');
01112                                         foreach($selectedLanguages as $lang) {
01113                                                 // remote unknown -> keine l10n
01114                                                 if(!isset($translationStatusArr[$lang])) {
01115                                                         echo ('<td title="No translation available">N/A</td>');
01116                                                         continue;
01117                                                 }
01118                                                         // determine local md5 from zip
01119                                                 if(is_file(PATH_site.'typo3temp/'.$extKey.'-l10n-'.$lang.'.zip')) {
01120                                                         $localmd5 = md5_file(PATH_site.'typo3temp/'.$extKey.'-l10n-'.$lang.'.zip');
01121                                                 } else {
01122                                                         echo ('<td title="Not installed / Unknown" style="background-color:#ff0">???</td>');
01123                                                         continue;
01124                                                 }
01125                                                         // local!=remote -> needs update
01126                                                 if($localmd5 != $translationStatusArr[$lang]['md5']) {
01127                                                         echo ('<td title="Needs update" style="background-color:#ff0">UPD</td>');
01128                                                         continue;
01129                                                 }
01130                                                 echo ('<td title="Is up to date" style="background-color:#69a550">OK</td>');
01131                                         }
01132                                         echo ('</tr>');
01133 
01134                                         $counter ++;
01135                                 }
01136                                 echo '</table>
01137                                         <script>
01138                                                 document.getElementById("progress-message").firstChild.data="Check done.";
01139                                         </script>
01140                                 ';
01141                                 echo $this->doc->endPage();
01142                                 return '';
01143 
01144                         } elseif(t3lib_div::_GET('l10n') == 'update') {
01145                                 $loadedExtensions = array_keys($TYPO3_LOADED_EXT);
01146                                 $loadedExtensions = array_diff($loadedExtensions,array('_CACHEFILE'));
01147 
01148                                         // Override content output - we now do that ourself:
01149                                 echo ($this->content . $this->doc->section('Translation status',$content,0,1));
01150                                 $this->doPrintContent = FALSE;
01151                                 flush();
01152 
01153                                 echo ('
01154                                 <br />
01155                                 <br />
01156                                 <p id="progress-message">
01157                                         Updating translations, please wait ...
01158                                 </p>
01159                                 <br />
01160                                 <div style="width:100%; height:20px; border: 1px solid black;">
01161                                         <div id="progress-bar" style="float: left; width: 0%; height: 20px; background-color:green;">&nbsp;</div>
01162                                         <div id="transparent-bar" style="float: left; width: 100%; height: 20px; background-color:'.$this->doc->bgColor2.';">&nbsp;</div>
01163                                 </div>
01164                                 <br />
01165                                 <br /><p>This table shows the update results of the loaded extension\'s translations.<br />
01166                                 <em>If you want to force a full check/update, delete the l10n zip-files from the typo3temp folder.</em></p><br />
01167                                 <table border="0" cellpadding="2" cellspacing="2">
01168                                         <tr class="bgColor2"><td>Extension key</td>
01169                                 ');
01170 
01171                                 foreach($selectedLanguages as $lang) {
01172                                         echo '<td>'.$LANG->getLL('lang_'.$lang,1).'</td>';
01173                                 }
01174                                 echo '</tr>';
01175 
01176                                 $counter = 1;
01177                                 foreach($loadedExtensions as $extKey) {
01178                                         $percentDone = intval (($counter / count($loadedExtensions)) * 100);
01179                                         echo ('
01180                                         <script>
01181                                                 document.getElementById("progress-bar").style.width = "'.$percentDone.'%";
01182                                                 document.getElementById("transparent-bar").style.width = "'.(100-$percentDone).'%";
01183                                                 document.getElementById("progress-message").firstChild.data="Updating translation for extension \"'.$extKey.'\" ...";
01184                                         </script>
01185                                         ');
01186 
01187                                         flush();
01188                                         $translationStatusArr = $this->terConnection->fetchTranslationStatus($extKey,$mirrorURL);
01189 
01190                                         echo ('<tr class="bgColor4"><td>'.$extKey.'</td>');
01191                                         foreach($selectedLanguages as $lang) {
01192                                                         // remote unknown -> no l10n available
01193                                                 if(!isset($translationStatusArr[$lang])) {
01194                                                         echo ('<td title="No translation available">N/A</td>');
01195                                                         continue;
01196                                                 }
01197                                                 // determine local md5 from zip
01198                                                 if(is_file(PATH_site.'typo3temp/'.$extKey.'-l10n-'.$lang.'.zip')) {
01199                                                         $localmd5 = md5_file(PATH_site.'typo3temp/'.$extKey.'-l10n-'.$lang.'.zip');
01200                                                 } else {
01201                                                         $localmd5 = 'zzz';
01202                                                 }
01203                                                 // local!=remote or not installed -> needs update
01204                                                 if($localmd5 != $translationStatusArr[$lang]['md5']) {
01205                                                         $ret = $this->updateTranslation($extKey, $lang, $mirrorURL);
01206                                                         if($ret === true) {
01207                                                                 echo ('<td title="Has been updated" style="background-color:#69a550">UPD</td>');
01208                                                         } else {
01209                                                                 echo ('<td title="'.htmlspecialchars($ret).'" style="background-color:#cb3352">ERR</td>');
01210                                                         }
01211                                                         continue;
01212                                                 }
01213                                                 echo ('<td title="Is up to date" style="background-color:#69a550">OK</td>');
01214                                         }
01215                                         echo ('</tr>');
01216 
01217                                         $counter++;
01218                                 }
01219                                 echo '</table>
01220                                         <script>
01221                                                 document.getElementById("progress-message").firstChild.data="Update done.";
01222                                         </script>
01223                                 ';
01224                                 echo $this->doc->endPage();
01225                                 return '';
01226                         }
01227 
01228                         $this->content.=$this->doc->section('Translation status',$content,0,1);
01229                 }
01230         }
01231 
01240         function updateTranslation($extKey, $lang, $mirrorURL) {
01241                 $l10n = $this->terConnection->fetchTranslation($extKey, $lang, $mirrorURL);
01242                 if(is_array($l10n)) {
01243                         $file = PATH_site.'typo3temp/'.$extKey.'-l10n-'.$lang.'.zip';
01244                         $path = 'l10n/'.$lang.'/';
01245                         if(!is_dir(PATH_typo3conf.$path)) t3lib_div::mkdir_deep(PATH_typo3conf,$path);
01246                         t3lib_div::writeFile($file, $l10n[0]);
01247                         if($this->unzip($file, PATH_typo3conf.$path)) {
01248                                 return true;
01249                         } else {
01250                                 return 'Unpacking the language pack failed!';
01251                         }
01252                 } else {
01253                         return $l10n;
01254                 }
01255         }
01256 
01264         function installTranslationsForExtension($extKey, $mirrorURL) {
01265                 $selectedLanguages = unserialize($this->MOD_SETTINGS['selectedLanguages']);
01266                 if(!is_array($selectedLanguages)) $selectedLanguages = array();
01267                 foreach($selectedLanguages as $lang) {
01268                         $l10n = $this->terConnection->fetchTranslation($extKey, $lang, $mirrorURL);
01269                         if(is_array($l10n)) {
01270                                 $file = PATH_typo3conf.'l10n/'.$extKey.'-l10n-'.$lang.'.zip';
01271                                 $path = 'l10n/'.$lang.'/'.$extKey;
01272                                 t3lib_div::writeFile($file, $l10n[0]);
01273                                 if(!is_dir(PATH_typo3conf.$path)) t3lib_div::mkdir_deep(PATH_typo3conf,$path);
01274                                 if($this->unzip($file, PATH_typo3conf.$path)) {
01275                                         return true;
01276                                 } else {
01277                                         return 'Unpacking the language pack failed!';
01278                                 }
01279                         } else {
01280                                 return $l10n;
01281                         }
01282                 }
01283         }
01284 
01294         function unzip($file, $path) {
01295                 if(strlen($GLOBALS['TYPO3_CONF_VARS']['BE']['unzip_path'])) {
01296                         chdir($path);
01297                         $cmd = $GLOBALS['TYPO3_CONF_VARS']['BE']['unzip_path'].' -o '.$file;
01298                         exec($cmd, $list, $ret);
01299                         return ($ret === 0);
01300                 } else {
01301                                 // we use a pure PHP unzip
01302                         $unzip = new em_unzip($file);
01303                         $ret = $unzip->extract(array('add_path'=>$path));
01304                         return (is_array($ret));
01305                 }
01306         }
01307 
01308 
01309 
01310         /*********************************
01311         *
01312         * Command Applications (triggered by GET var)
01313         *
01314         *********************************/
01315 
01323         function importExtInfo($extKey, $version='')    {
01324 
01325                         // "Go back" link
01326                 $content = '<a href="index.php" class="typo3-goBack"><img'.t3lib_iconWorks::skinImg($GLOBALS['BACK_PATH'],'gfx/goback.gif','width="14" height="14"').' alt="" /> Go back</a>';
01327                 $this->content.= $this->doc->section('',$content);
01328                 $content = '';
01329 
01330                         // Fetch remote data:
01331                 $this->xmlhandler->loadExtensionsXML();
01332                 $this->xmlhandler->extensionsXML = array($extKey => $this->xmlhandler->extensionsXML[$extKey]);
01333                 list($fetchData,) = $this->prepareImportExtList();
01334 
01335                 $versions = array_keys($fetchData[$extKey]['versions']);
01336                 $version = ($version == '') ? end($versions) : $version;
01337 
01338                 $opt = array();
01339                 foreach(array_keys($fetchData[$extKey]['versions']) as $ver)    {
01340                         $opt[]='<option value="'.$ver.'"'.(($version == $ver) ? ' selected="selected"' : '').'>'.$ver.'</option>';
01341                 }
01342 
01343                         // "Select version" box:
01344                 $onClick = 'window.location.href=\'index.php?CMD[importExtInfo]='.$extKey.'&CMD[extVersion]=\'+document.pageform.extVersion.options[document.pageform.extVersion.selectedIndex].value; return false;';
01345                 $select='<select name="extVersion">'.implode('',$opt).'</select> <input type="submit" value="Load details" onclick="'.htmlspecialchars($onClick).'" /> or<br /><br />';
01346 
01347                 if ($this->importAtAll())       {
01348                         $onClick = '
01349                                         window.location.href=\'index.php?CMD[importExt]='.$extKey.'\'
01350                                                 +\'&CMD[extVersion]=\'+document.pageform.extVersion.options[document.pageform.extVersion.selectedIndex].value
01351                                                 +\'&CMD[loc]=\'+document.pageform.loc.options[document.pageform.loc.selectedIndex].value;
01352                                                 return false;';
01353                         $select.='
01354                                 <input type="submit" value="Import/Update" onclick="'.htmlspecialchars($onClick).'"> to:
01355                                 <select name="loc">'.
01356                                 ($this->importAsType('G',$fetchData['emconf_lockType'])?'<option value="G">Global: '.$this->typePaths['G'].$extKey.'/'.(@is_dir(PATH_site.$this->typePaths['G'].$extKey)?' (OVERWRITE)':' (empty)').'</option>':'').
01357                                 ($this->importAsType('L',$fetchData['emconf_lockType'])?'<option value="L">Local: '.$this->typePaths['L'].$extKey.'/'.(@is_dir(PATH_site.$this->typePaths['L'].$extKey)?' (OVERWRITE)':' (empty)').'</option>':'').
01358                                 ($this->importAsType('S',$fetchData['emconf_lockType'])?'<option value="S">System: '.$this->typePaths['S'].$extKey.'/'.(@is_dir(PATH_site.$this->typePaths['S'].$extKey)?' (OVERWRITE)':' (empty)').'</option>':'').
01359                                 '</select>';
01360                 } else $select.= $this->noImportMsg();
01361                 $content.= $select;
01362                 $this->content.= $this->doc->section('Select command',$content,0,1);
01363 
01364                         // Details:
01365                 $eInfo = $fetchData[$extKey]['versions'][$version];
01366                 $content='<strong>'.$fetchData[$extKey]['_ICON'].' &nbsp;'.$eInfo['EM_CONF']['title'].' ('.$extKey.', '.$version.')</strong><br /><br />';
01367                 $content.=$this->extInformationArray($extKey,$eInfo,1);
01368                 $this->content.=$this->doc->spacer(10);
01369                 $this->content.=$this->doc->section('Remote Extension Details',$content,0,1);
01370         }
01371 
01380         function fetchMetaData($metaType)       {
01381                 global $TYPO3_CONF_VARS;
01382 
01383                 switch($metaType) {
01384                         case 'mirrors':
01385                                 $mfile = t3lib_div::tempnam('mirrors');
01386                                 $mirrorsFile = t3lib_div::getURL($this->MOD_SETTINGS['mirrorListURL']);
01387                                 if($mirrorsFile===false) {
01388                                         t3lib_div::unlink_tempfile($mfile);
01389                                         $content = '<p>The mirror list was not updated, it could not be fetched from '.$this->MOD_SETTINGS['mirrorListURL'].'. Possible reasons: network problems, allow_url_fopen is off, curl is not enabled in Install tool.</p>';
01390                                 } else {
01391                                         t3lib_div::writeFile($mfile, $mirrorsFile);
01392                                         $mirrors = implode(gzfile($mfile));
01393                                         t3lib_div::unlink_tempfile($mfile);
01394 
01395                                         $mirrors = $this->xmlhandler->parseMirrorsXML($mirrors);
01396                                         if(is_array($mirrors) && count($mirrors)) {
01397                                                 t3lib_BEfunc::getModuleData($this->MOD_MENU, array('extMirrors' => serialize($mirrors)), $this->MCONF['name'], '', 'extMirrors');
01398                                                 $this->MOD_SETTINGS['extMirrors'] = serialize($mirrors);
01399                                                 $content = '<p>The mirror list has been updated and now contains '.count($mirrors).' entries.</p>';
01400                                         }
01401                                         else {
01402                                                 $content = '<p>'.$mirrors.'<br />The mirror list was not updated as it contained no entries.</p>';
01403                                         }
01404                                 }
01405                                 break;
01406                         case 'extensions':
01407                                 $this->fetchMetaData('mirrors'); // if we fetch the extensions anyway, we can as well keep this up-to-date
01408 
01409                                 $mirror = $this->getMirrorURL();
01410                                 $extfile = $mirror.'extensions.xml.gz';
01411                                 $extmd5 = t3lib_div::getURL($mirror.'extensions.md5');
01412                                 if(is_file(PATH_site.'typo3temp/extensions.xml.gz')) $localmd5 = md5_file(PATH_site.'typo3temp/extensions.xml.gz');
01413 
01414                                 if($extmd5 === false) {
01415                                         $content .= '<p>Error: The extension MD5 sum could not be fetched from '.$mirror.'extensions.md5. Possible reasons: network problems, allow_url_fopen is off, curl is not enabled in Install tool.</p>';
01416                                 } elseif($extmd5 == $localmd5) {
01417                                         $content .= '<p>The extension list has not changed remotely, it has thus not been fetched.</p>';
01418                                 } else {
01419                                         $extXML = t3lib_div::getURL($extfile);
01420                                         if($extXML === false) {
01421                                                 $content .= '<p>Error: The extension list could not be fetched from '.$extfile.'. Possible reasons: network problems, allow_url_fopen is off, curl is not enabled in Install tool.</p>';
01422                                         } else {
01423                                                 t3lib_div::writeFile(PATH_site.'typo3temp/extensions.xml.gz', $extXML);
01424                                                 $content .= $this->xmlhandler->parseExtensionsXML(implode(gzfile(PATH_site.'typo3temp/extensions.xml.gz')));
01425                                                 $this->xmlhandler->saveExtensionsXML();
01426                                         }
01427                                 }
01428                                 break;
01429                 }
01430 
01431                 return $content;
01432         }
01433 
01439         function getMirrorURL() {
01440                 if(strlen($this->MOD_SETTINGS['rep_url'])) return $this->MOD_SETTINGS['rep_url'];
01441 
01442                 $mirrors = unserialize($this->MOD_SETTINGS['extMirrors']);
01443                 if(!is_array($mirrors)) {
01444                         $this->fetchMetaData('mirrors');
01445                         $mirrors = unserialize($this->MOD_SETTINGS['extMirrors']);
01446                         if(!is_array($mirrors)) return false;
01447                 }
01448                 if($this->MOD_SETTINGS['selectedMirror']=='') {
01449                         srand((float) microtime() * 10000000); // not needed after PHP 4.2.0...
01450                         $rand = array_rand($mirrors);
01451                         $url = 'http://'.$mirrors[$rand]['host'].$mirrors[$rand]['path'];
01452                 }
01453                 else {
01454                         $url = 'http://'.$mirrors[$this->MOD_SETTINGS['selectedMirror']]['host'].$mirrors[$this->MOD_SETTINGS['selectedMirror']]['path'];
01455                 }
01456 
01457                 return $url;
01458         }
01459 
01460 
01461 
01477         function installExtension($extKey, $version=null, $mode=EM_INSTALL_VERSION_MIN) {
01478                 list($inst_list,) = $this->getInstalledExtensions();
01479 
01480                         // check if it is already installed and loaded with sufficient version
01481                 if(isset($inst_list[$extKey])) {
01482                         $currentVersion = $inst_list[$extKey]['EM_CONF']['version'];
01483 
01484                         if(t3lib_extMgm::isLoaded($extKey)) {
01485                                 if($version===null) {
01486                                         return array(true, 'Extension already installed and loaded.');
01487                                 } else {
01488                                         switch($mode) {
01489                                                 case EM_INSTALL_VERSION_STRICT:
01490                                                         if($currentVersion == $version) {
01491                                                                 return array(true, 'Extension already installed and loaded.');
01492                                                         }
01493                                                         break;
01494                                                 case EM_INSTALL_VERSION_MIN:
01495                                                         if(version_compare($currentVersion, $version, '>=')) {
01496                                                                 return array(true, 'Extension already installed and loaded.');
01497                                                         }
01498                                                         break;
01499                                                 case EM_INSTALL_VERSION_MAX:
01500                                                         if(version_compare($currentVersion, $version, '<=')) {
01501                                                                 return array(true, 'Extension already installed and loaded.');
01502                                                         }
01503                                                         break;
01504                                         }
01505                                 }
01506                         } else {
01507                                 if (!t3lib_extMgm::isLocalconfWritable())       {
01508                                         return array(false, 'localconf.php is not writable!');
01509                                 }
01510                                 $newExtList = -1;
01511                                 switch($mode) {
01512                                         case EM_INSTALL_VERSION_STRICT:
01513                                                 if($currentVersion == $version) {
01514                                                         $newExtList = $this->addExtToList($extKey, $inst_list);
01515                                                 }
01516                                                 break;
01517                                         case EM_INSTALL_VERSION_MIN:
01518                                                 if(version_compare($currentVersion, $version, '>=')) {
01519                                                         $newExtList = $this->addExtToList($extKey, $inst_list);
01520                                                 }
01521                                                 break;
01522                                         case EM_INSTALL_VERSION_MAX:
01523                                                 if(version_compare($currentVersion, $version, '<=')) {
01524                                                         $newExtList = $this->addExtToList($extKey, $inst_list);
01525                                                 }
01526                                                 break;
01527                                 }
01528                                 if ($newExtList!=-1)    {
01529                                         $this->writeNewExtensionList($newExtList);
01530                                         $this->refreshGlobalExtList();
01531                                         $this->forceDBupdates($extKey, $inst_list[$extKey]);
01532                                         return array(true, 'Extension was already installed, it has been loaded.');
01533                                 }
01534                         }
01535                 }
01536 
01537                         // at this point we know we need to import (a matching version of) the extension from TER2
01538 
01539                         // see if we have an extensionlist at all
01540                 $this->xmlhandler->loadExtensionsXML();
01541                 if (!count($this->xmlhandler->extensionsXML))   {
01542                         $this->fetchMetaData('extensions');
01543                 }
01544 
01545                         // check if extension can be fetched
01546                 if(isset($this->xmlhandler->extensionsXML[$extKey])) {
01547                         $versions = array_keys($this->xmlhandler->extensionsXML[$extKey]['versions']);
01548                         $latestVersion = end($versions);
01549                         switch($mode) {
01550                                 case EM_INSTALL_VERSION_STRICT:
01551                                         if(!isset($this->xmlhandler->extensionsXML[$extKey]['versions'][$version])) {
01552                                                 return array(false, 'Extension not available in matching version');
01553                                         }
01554                                         break;
01555                                 case EM_INSTALL_VERSION_MIN:
01556                                         if(version_compare($latestVersion, $version, '>=')) {
01557                                                 $version = $latestVersion;
01558                                         } else {
01559                                                 return array(false, 'Extension not available in matching version');
01560                                         }
01561                                         break;
01562                                 case EM_INSTALL_VERSION_MAX:
01563                                         while(($v = array_pop($versions)) && version_compare($v, $version, '>=')) {}
01564                                         if($v !== null && version_compare($v, $version, '<=')) {
01565                                                 $version = $v;
01566                                         } else {
01567                                                 return array(false, 'Extension not available in matching version');
01568                                         }
01569                                         break;
01570                         }
01571                         $this->importExtFromRep($extKey, $version, 'L');
01572                         $newExtList = $this->addExtToList($extKey, $inst_list);
01573                         if ($newExtList!=-1)    {
01574                                 $this->writeNewExtensionList($newExtList);
01575                                 $this->refreshGlobalExtList();
01576                                 $this->forceDBupdates($extKey, $inst_list[$extKey]);
01577                                 $this->installTranslationsForExtension($extKey, $this->getMirrorURL());
01578                                 return array(true, 'Extension has been imported from repository and loaded.');
01579                         } else {
01580                                 return array(false, 'Extension is in repository, but could not be loaded.');
01581                         }
01582                 } else {
01583                         return array(false, 'Extension not available in repository');
01584                 }
01585         }
01586 
01587         function refreshGlobalExtList() {
01588                 global $TYPO3_LOADED_EXT;
01589 
01590                 $TYPO3_LOADED_EXT = t3lib_extMgm::typo3_loadExtensions();
01591                 if ($TYPO3_LOADED_EXT['_CACHEFILE'])    {
01592                         require(PATH_typo3conf.$TYPO3_LOADED_EXT['_CACHEFILE'].'_ext_localconf.php');
01593                 }
01594                 return;
01595 
01596                 $GLOBALS['TYPO3_LOADED_EXT'] = t3lib_extMgm::typo3_loadExtensions();
01597                 if ($TYPO3_LOADED_EXT['_CACHEFILE'])    {
01598                         require(PATH_typo3conf.$TYPO3_LOADED_EXT['_CACHEFILE'].'_ext_localconf.php');
01599                 } else {
01600                         $temp_TYPO3_LOADED_EXT = $TYPO3_LOADED_EXT;
01601                         reset($temp_TYPO3_LOADED_EXT);
01602                         while(list($_EXTKEY,$temp_lEDat)=each($temp_TYPO3_LOADED_EXT))  {
01603                                 if (is_array($temp_lEDat) && $temp_lEDat['ext_localconf.php'])  {
01604                                         $_EXTCONF = $TYPO3_CONF_VARS['EXT']['extConf'][$_EXTKEY];
01605                                         require($temp_lEDat['ext_localconf.php']);
01606                                 }
01607                         }
01608                 }
01609         }
01610 
01611 
01624         function importExtFromRep($extKey,$version,$loc,$uploadFlag=0,$dontDelete=0,$directInput='')    {
01625 
01626                 if (is_array($directInput))     {
01627                         $fetchData = array($directInput,'');
01628                         $loc = ($loc==='G'||$loc==='S') ? $loc : 'L';
01629                 } elseif ($uploadFlag)  {
01630                         if ($_FILES['upload_ext_file']['tmp_name'])     {
01631 
01632                                         // Read uploaded file:
01633                                 $uploadedTempFile = t3lib_div::upload_to_tempfile($_FILES['upload_ext_file']['tmp_name']);
01634                                 $fileContent = t3lib_div::getUrl($uploadedTempFile);
01635                                 t3lib_div::unlink_tempfile($uploadedTempFile);
01636 
01637                                         // Decode file data:
01638                                 $fetchData = $this->terConnection->decodeExchangeData($fileContent);
01639 
01640                                 if (is_array($fetchData))       {
01641                                         $extKey = $fetchData[0]['extKey'];
01642                                         if ($extKey)    {
01643                                                 if (!$this->CMD['uploadOverwrite'])     {
01644                                                         $loc = ($loc==='G'||$loc==='S') ? $loc : 'L';
01645                                                         $comingExtPath = PATH_site.$this->typePaths[$loc].$extKey.'/';
01646                                                         if (@is_dir($comingExtPath))    {
01647                                                                 return 'Extension was already present in "'.$comingExtPath.'" - and the overwrite flag was not set! So nothing done...';
01648                                                         }       // ... else go on, install...
01649                                                 }       // ... else go on, install...
01650                                         } else return 'No extension key in file. Strange...';
01651                                 } else return 'Wrong file format. No data recognized, '.$fetchData;
01652                         } else return 'No file uploaded! Probably the file was too large for PHPs internal limit for uploadable files.';
01653                 } else {
01654                         $this->xmlhandler->loadExtensionsXML();
01655 
01656                                 // Fetch extension from TER:
01657                         if(!strlen($version)) {
01658                                 $versions = array_keys($this->xmlhandler->extensionsXML[$extKey]['versions']);
01659                                 $version = end($versions);
01660                         }
01661                         $fetchData = $this->terConnection->fetchExtension($extKey, $version, $this->xmlhandler->extensionsXML[$extKey]['versions'][$version]['t3xfilemd5'], $this->getMirrorURL());
01662                 }
01663 
01664                 // At this point the extension data should be present; so we want to write it to disc:
01665                 if ($this->importAsType($loc))  {
01666                         if (is_array($fetchData))       {       // There was some data successfully transferred
01667                                 if ($fetchData[0]['extKey'] && is_array($fetchData[0]['FILES']))        {
01668                                         $extKey = $fetchData[0]['extKey'];
01669                                         if(!isset($fetchData[0]['EM_CONF']['constraints'])) $fetchData[0]['EM_CONF']['constraints'] = $this->xmlhandler->extensionsXML[$extKey]['versions'][$version]['dependencies'];
01670                                         $EM_CONF = $this->fixEMCONF($fetchData[0]['EM_CONF']);
01671                                         if (!$EM_CONF['lockType'] || !strcmp($EM_CONF['lockType'],$loc))        {
01672                                                         // check dependencies, act accordingly if ext is loaded
01673                                                 list($instExtInfo,)=$this->getInstalledExtensions();
01674                                                 $depStatus = $this->checkDependencies($extKey, $EM_CONF, $instExtInfo);
01675                                                 if(t3lib_extMgm::isLoaded($extKey) && !$depStatus['returnCode']) {
01676                                                         $this->content .= $depStatus['html'];
01677                                                 } else {
01678                                                         $res = $this->clearAndMakeExtensionDir($fetchData[0],$loc,$dontDelete);
01679                                                         if (is_array($res))     {
01680                                                                 $extDirPath = trim($res[0]);
01681                                                                 if ($extDirPath && @is_dir($extDirPath) && substr($extDirPath,-1)=='/') {
01682 
01683                                                                         $emConfFile = $this->construct_ext_emconf_file($extKey,$EM_CONF);
01684                                                                         $dirs = $this->extractDirsFromFileList(array_keys($fetchData[0]['FILES']));
01685 
01686                                                                         $res = $this->createDirsInPath($dirs,$extDirPath);
01687                                                                         if (!$res)      {
01688                                                                                 $writeFiles = $fetchData[0]['FILES'];
01689                                                                                 $writeFiles['ext_emconf.php']['content'] = $emConfFile;
01690                                                                                 $writeFiles['ext_emconf.php']['content_md5'] = md5($emConfFile);
01691 
01692                                                                                         // Write files:
01693                                                                                 foreach($writeFiles as $theFile => $fileData)   {
01694                                                                                         t3lib_div::writeFile($extDirPath.$theFile,$fileData['content']);
01695                                                                                         if (!@is_file($extDirPath.$theFile))    {
01696                                                                                                 $content.='Error: File "'.$extDirPath.$theFile.'" could not be created!!!<br />';
01697                                                                                         } elseif (md5(t3lib_div::getUrl($extDirPath.$theFile)) != $fileData['content_md5']) {
01698                                                                                                 $content.='Error: File "'.$extDirPath.$theFile.'" MD5 was different from the original files MD5 - so the file is corrupted!<br />';
01699                                                                                         }
01700                                                                                 }
01701 
01702                                                                                         // No content, no errors. Create success output here:
01703                                                                                 if (!$content)  {
01704                                                                                         $content='SUCCESS: '.$extDirPath.'<br />';
01705 
01706                                                                                                 // Fix TYPO3_MOD_PATH for backend modules in extension:
01707                                                                                         $modules = t3lib_div::trimExplode(',',$EM_CONF['module'],1);
01708                                                                                         if (count($modules))    {
01709                                                                                                 foreach($modules as $mD)        {
01710                                                                                                         $confFileName = $extDirPath.$mD.'/conf.php';
01711                                                                                                         if (@is_file($confFileName))    {
01712                                                                                                                 $content.= $this->writeTYPO3_MOD_PATH($confFileName,$loc,$extKey.'/'.$mD.'/').'<br />';
01713                                                                                                         } else $content.='Error: Couldn\'t find "'.$confFileName.'"<br />';
01714                                                                                                 }
01715                                                                                         }
01716                                                                                                 // NOTICE: I used two hours trying to find out why a script, ext_emconf.php, written twice and in between included by PHP did not update correct the second time. Probably something with PHP-A cache and mtime-stamps.
01717                                                                                                 // But this order of the code works.... (using the empty Array with type, EMCONF and files hereunder).
01718 
01719                                                                                                 // Writing to ext_emconf.php:
01720                                                                                         $sEMD5A = $this->serverExtensionMD5Array($extKey,array('type' => $loc, 'EM_CONF' => array(), 'files' => array()));
01721                                                                                         $EM_CONF['_md5_values_when_last_written'] = serialize($sEMD5A);
01722                                                                                         $emConfFile = $this->construct_ext_emconf_file($extKey,$EM_CONF);
01723                                                                                         t3lib_div::writeFile($extDirPath.'ext_emconf.php',$emConfFile);
01724 
01725                                                                                         $content.='ext_emconf.php: '.$extDirPath.'ext_emconf.php<br />';
01726                                                                                         $content.='Type: '.$loc.'<br />';
01727 
01728                                                                                                 // Remove cache files:
01729                                                                                         if (t3lib_extMgm::isLoaded($extKey))    {
01730                                                                                                 if ($this->removeCacheFiles())  {
01731                                                                                                         $content.='Cache-files are removed and will be re-written upon next hit<br />';
01732                                                                                                 }
01733 
01734                                                                                                 list($new_list)=$this->getInstalledExtensions();
01735                                                                                                 $content.=$this->updatesForm($extKey,$new_list[$extKey],1,'index.php?CMD[showExt]='.$extKey.'&SET[singleDetails]=info');
01736                                                                                         }
01737 
01738                                                                                                 // Install / Uninstall:
01739                                                                                         if(!$this->CMD['standAlone']) {
01740                                                                                                 $content = '<a href="index.php" class="typo3-goBack"><img'.t3lib_iconWorks::skinImg($GLOBALS['BACK_PATH'],'gfx/goback.gif','width="14" height="14"').' alt="" /> Go back</a><br />'.$content;
01741                                                                                                 $content.='<h3>Install / Uninstall Extension:</h3>';
01742                                                                                                 $content.= $new_list[$extKey] ?
01743                                                                                                         '<a href="'.htmlspecialchars('index.php?CMD[showExt]='.$extKey.'&CMD[remove]=1&CMD[clrCmd]=1&SET[singleDetails]=info').'">'.$this->removeButton().' Uninstall extension</a>' :
01744                                                                                                         '<a href="'.htmlspecialchars('index.php?CMD[showExt]='.$extKey.'&CMD[load]=1&CMD[clrCmd]=1&SET[singleDetails]=info').'">'.$this->installButton().' Install extension</a>';
01745                                                                                         } else {
01746                                                                                                 $content = 'Extension has been imported.<br /><br /><a href="javascript:opener.top.content.document.forms[0].submit();window.close();">Close window and recheck dependencies</a>';
01747                                                                                         }
01748 
01749                                                                                 }
01750                                                                         } else $content = $res;
01751                                                                 } else $content = 'Error: The extension path "'.$extDirPath.'" was different than expected...';
01752                                                         } else $content = $res;
01753                                                 }
01754                                         } else $content = 'Error: The extension can only be installed in the path '.$this->typePaths[$EM_CONF['lockType']].' (lockType='.$EM_CONF['lockType'].')';
01755                                 } else $content = 'Error: No extension key!!! Why? - nobody knows... (Or no files in the file-array...)';
01756                         }  else $content = 'Error: The datatransfer did not succeed. '.$fetchData;
01757                 }  else $content = 'Error: Installation is not allowed in this path ('.$this->typePaths[$loc].')';
01758 
01759                 $this->content.=$this->doc->section('Extension import results',$content,0,1);
01760 
01761                 return false;
01762         }
01763 
01770         function showExtDetails($extKey)        {
01771                 global $TYPO3_LOADED_EXT;
01772 
01773                 list($list,)=$this->getInstalledExtensions();
01774                 $absPath = $this->getExtPath($extKey,$list[$extKey]['type']);
01775 
01776                 // Check updateModule:
01777                 if (@is_file($absPath.'class.ext_update.php'))  {
01778                         require_once($absPath.'class.ext_update.php');
01779                         $updateObj = new ext_update;
01780                         if (!$updateObj->access())      {
01781                                 unset($this->MOD_MENU['singleDetails']['updateModule']);
01782                         }
01783                 } else {
01784                         unset($this->MOD_MENU['singleDetails']['updateModule']);
01785                 }
01786 
01787                 if($this->CMD['doDelete']) {
01788                         $this->MOD_MENU['singleDetails'] = array();
01789                 }
01790 
01791                         // Function menu here:
01792                 if(!$this->CMD['standAlone'] && !t3lib_div::_GP('standAlone')) {
01793                         $content = '
01794                                 <table border="0" cellpadding="0" cellspacing="0" width="100%">
01795                                         <tr>
01796                                                 <td nowrap="nowrap">Extension:&nbsp;<strong>'.$this->extensionTitleIconHeader($extKey,$list[$extKey]).'</strong> ('.$extKey.')</td>
01797                                                 <td align="right" nowrap="nowrap">'.
01798                         t3lib_BEfunc::getFuncMenu(0,'SET[singleDetails]',$this->MOD_SETTINGS['singleDetails'],$this->MOD_MENU['singleDetails'],'','&CMD[showExt]='.$extKey).' &nbsp; &nbsp; '.
01799                         '<a href="index.php" class="typo3-goBack"><img'.t3lib_iconWorks::skinImg($this->doc->backPath,'gfx/goback.gif','width="14" height="14"').' class="absmiddle" alt="" /> Go back</a></td>
01800                                         </tr>
01801                                 </table>';
01802                         $this->content.=$this->doc->section('',$content);
01803                 }
01804 
01805                         // Show extension details:
01806                 if ($list[$extKey])     {
01807 
01808                                 // Checking if a command for install/uninstall is executed:
01809                         if (($this->CMD['remove'] || $this->CMD['load']) && !in_array($extKey,$this->requiredExt))      {
01810 
01811                                         // Install / Uninstall extension here:
01812                                 if (t3lib_extMgm::isLocalconfWritable())        {
01813                                                 // Check dependencies:
01814                                         $depStatus = $this->checkDependencies($extKey, $list[$extKey]['EM_CONF'], $list);
01815                                         if(!$this->CMD['remove'] && !$depStatus['returnCode']) {
01816                                                 $this->content .= $depStatus['html'];
01817                                                 $newExtList = -1;
01818                                         } elseif ($this->CMD['remove']) {
01819                                                 $newExtList = $this->removeExtFromList($extKey,$list);
01820                                         } else {
01821                                                 $newExtList = $this->addExtToList($extKey,$list);
01822                                         }
01823 
01824                                         // Success-installation:
01825                                         if ($newExtList!=-1)    {
01826                                                 $updates = '';
01827                                                 if ($this->CMD['load']) {
01828                                                         if($_SERVER['REQUEST_METHOD'] == 'POST') {
01829                                                                 $script = t3lib_div::linkThisScript(array('CMD[showExt]' => $extKey, 'CMD[load]' => 1, 'CMD[clrCmd]' => $this->CMD['clrCmd'], 'SET[singleDetails]' => 'info'));
01830                                                         } else {
01831                                                                 $script = '';
01832                                                         }
01833                                                         $updates = $this->updatesForm($extKey,$list[$extKey],1,$script,'<input type="hidden" name="_do_install" value="1" /><input type="hidden" name="_clrCmd" value="'.$this->CMD['clrCmd'].'" />');
01834                                                         if ($updates)   {
01835                                                                 $updates = 'Before the extension can be installed the database needs to be updated with new tables or fields. Please select which operations to perform:'.$updates;
01836                                                                 if($this->CMD['standAlone']) $updates .= '<input type="hidden" name="standAlone" value="1" />';
01837                                                                 $depsolver = t3lib_div::_POST('depsolver');
01838                                                                 if(is_array($depsolver['ignore'])) {
01839                                                                         foreach($depsolver['ignore'] as $depK => $depV) {
01840                                                                                 $updates .= '<input type="hidden" name="depsolver[ignore]['.$depK.']" value="1" />';
01841                                                                         }
01842                                                                 }
01843 
01844                                                                 $this->content.=$this->doc->section('Installing '.$this->extensionTitleIconHeader($extKey,$list[$extKey]).strtoupper(': Database needs to be updated'),$updates,1,1,1,1);
01845                                                         }
01846                                                 } elseif ($this->CMD['remove']) {
01847                                                         $updates.= $this->checkClearCache($list[$extKey]);
01848                                                         if ($updates)   {
01849                                                                 $updates = '
01850                                                                 </form><form action="'.t3lib_div::linkThisScript().'" method="post">'.$updates.'
01851                                                                 <br /><input type="submit" name="write" value="Remove extension" />
01852                                                                 <input type="hidden" name="_do_install" value="1" />
01853                                                                 <input type="hidden" name="_clrCmd" value="'.$this->CMD['clrCmd'].'" />
01854                                                                 <input type="hidden" name="standAlone" value="'.$this->CMD['standAlone'].'" />
01855                                                                 ';
01856                                                                 $this->content.=$this->doc->section('Removing '.$this->extensionTitleIconHeader($extKey,$list[$extKey]).strtoupper(': Database needs to be updated'),$updates,1,1,1,1);
01857                                                         }
01858                                                 }
01859                                                 if (!$updates || t3lib_div::_GP('_do_install')) {
01860                                                         $this->writeNewExtensionList($newExtList);
01861                                                         $GLOBALS['BE_USER']->writelog(5,1,0,0,'Extension list has been changed, extension %s has been %s',array($extKey,($this->CMD['load']?'installed':'removed')));
01862                                                         if ($this->CMD['clrCmd'] || t3lib_div::_GP('_clrCmd'))  {
01863                                                                 $vA = array('CMD'=>'');
01864                                                         } else {
01865                                                                 $vA = array('CMD'=>Array('showExt'=>$extKey));
01866                                                         }
01867                                                         if($this->CMD['standAlone'] || t3lib_div::_GP('standAlone')) {
01868                                                                 $this->content .= 'Extension has been '.($this->CMD['load'] ? 'installed' : 'removed').'.<br /><br /><a href="javascript:opener.top.content.document.forms[0].submit();window.close();">Close window and recheck dependencies</a>';
01869                                                         } else {
01870                                                                 header('Location: '.t3lib_div::linkThisScript($vA));
01871                                                         }
01872                                                 }
01873                                         }
01874                                 } else {
01875                                         $this->content.=$this->doc->section('Installing '.$this->extensionTitleIconHeader($extKey,$list[$extKey]).strtoupper(': Write access error'),'typo3conf/localconf.php seems not to be writable, so the extension cannot be installed automatically!',1,1,2,1);
01876                                 }
01877 
01878                         } elseif ($this->CMD['downloadFile'] && !in_array($extKey,$this->requiredExt))  {
01879 
01880                                 // Link for downloading extension has been clicked - deliver content stream:
01881                                 $dlFile = $this->CMD['downloadFile'];
01882                                 if (t3lib_div::isFirstPartOfStr($dlFile,PATH_site) && t3lib_div::isFirstPartOfStr($dlFile,$absPath) && @is_file($dlFile))       {
01883                                         $mimeType = 'application/octet-stream';
01884                                         Header('Content-Type: '.$mimeType);
01885                                         Header('Content-Disposition: attachment; filename='.basename($dlFile));
01886                                         echo t3lib_div::getUrl($dlFile);
01887                                         exit;
01888                                 } else die('Error while trying to download extension file...');
01889 
01890                         } elseif ($this->CMD['editFile'] && !in_array($extKey,$this->requiredExt))      {
01891 
01892                                 // Editing extension file:
01893                                 $editFile = $this->CMD['editFile'];
01894                                 if (t3lib_div::isFirstPartOfStr($editFile,PATH_site) && t3lib_div::isFirstPartOfStr($editFile,$absPath))        {       // Paranoia...
01895 
01896                                         $fI = t3lib_div::split_fileref($editFile);
01897                                         if (@is_file($editFile) && t3lib_div::inList($this->editTextExtensions,($fI['fileext']?$fI['fileext']:$fI['filebody'])))        {
01898                                                 if (filesize($editFile)<($this->kbMax*1024))    {
01899                                                         $outCode = '';
01900                                                         $info = '';
01901                                                         $submittedContent = t3lib_div::_POST('edit');
01902                                                         $saveFlag = 0;
01903 
01904                                                         if(isset($submittedContent['file']) && !$GLOBALS['TYPO3_CONF_VARS']['EXT']['noEdit'])   {               // Check referer here?
01905                                                                 $oldFileContent = t3lib_div::getUrl($editFile);
01906                                                                 if($oldFileContent != $submittedContent['file']) {
01907                                                                         $oldMD5 = md5(str_replace(chr(13),'',$oldFileContent));
01908                                                                         $info.= 'MD5: <b>'.$oldMD5.'</b> (Previous File)<br />';
01909                                                                         t3lib_div::writeFile($editFile,$submittedContent['file']);
01910                                                                         $saveFlag = 1;
01911                                                                 } else {
01912                                                                         $info .= 'No changes to the file detected!<br />';
01913                                                                 }
01914                                                         }
01915 
01916                                                         $fileContent = t3lib_div::getUrl($editFile);
01917 
01918                                                         $outCode.= 'File: <b>'.substr($editFile,strlen($absPath)).'</b> ('.t3lib_div::formatSize(filesize($editFile)).')<br />';
01919                                                         $fileMD5 = md5(str_replace(chr(13),'',$fileContent));
01920                                                         $info.= 'MD5: <b>'.$fileMD5.'</b> (Current File)<br />';
01921                                                         if($saveFlag)   {
01922                                                                 $saveMD5 = md5(str_replace(chr(13),'',$submittedContent['file']));
01923                                                                 $info.= 'MD5: <b>'.$saveMD5.'</b> (Submitted)<br />';
01924                                                                 if($fileMD5!=$saveMD5) $info .= $GLOBALS['TBE_TEMPLATE']->rfw('<br /><strong>Saving failed, the content was not correctly written to disk. Changes have been lost!</strong>').'<br />';
01925                                                                 else $info.= $GLOBALS['TBE_TEMPLATE']->rfw('<br /><strong>File saved.</strong>').'<br />';
01926                                                         }
01927 
01928                                                         $outCode.= '<textarea name="edit[file]" rows="35" wrap="off"'.$this->doc->formWidthText(48,'width:98%;height:70%','off').' class="fixed-font enable-tab">'.t3lib_div::formatForTextarea($fileContent).'</textarea>';
01929                                                         $outCode.= '<input type="hidden" name="edit[filename]" value="'.$editFile.'" />';
01930                                                         $outCode.= '<input type="hidden" name="CMD[editFile]" value="'.htmlspecialchars($editFile).'" />';
01931                                                         $outCode.= '<input type="hidden" name="CMD[showExt]" value="'.$extKey.'" />';
01932                                                         $outCode.= $info;
01933 
01934                                                         if (!$GLOBALS['TYPO3_CONF_VARS']['EXT']['noEdit'])      {
01935                                                                 $outCode.='<br /><input type="submit" name="save_file" value="Save file" />';
01936                                                         } else $outCode.=$GLOBALS['TBE_TEMPLATE']->rfw('<br />[SAVING IS DISABLED - can be enabled by the $TYPO3_CONF_VARS[\'EXT\'][\'noEdit\']-flag] ');
01937 
01938                                                         $onClick = 'window.location.href=\'index.php?CMD[showExt]='.$extKey.'\';return false;';
01939                                                         $outCode.='<input type="submit" name="cancel" value="Cancel" onclick="'.htmlspecialchars($onClick).'" />';
01940 
01941                                                         $theOutput.=$this->doc->spacer(15);
01942                                                         $theOutput.=$this->doc->section('Edit file:','',0,1);
01943                                                         $theOutput.=$this->doc->sectionEnd().$outCode;
01944                                                         $this->content.=$theOutput;
01945                                                 } else {
01946                                                         $theOutput.=$this->doc->spacer(15);
01947                                                         $theOutput.=$this->doc->section('Filesize exceeded '.$this->kbMax.' Kbytes','Files larger than '.$this->kbMax.' KBytes are not allowed to be edited.');
01948                                                 }
01949                                         }
01950                                 } else die('Fatal Edit error: File "'.$editFile.'" was not inside the correct path of the TYPO3 Extension!');
01951                         } else {
01952 
01953                                 // MAIN:
01954                                 switch((string)$this->MOD_SETTINGS['singleDetails'])    {
01955                                         case 'info':
01956                                                 // Loaded / Not loaded:
01957                                                 if (!in_array($extKey,$this->requiredExt))      {
01958                                                         if ($TYPO3_LOADED_EXT[$extKey]) {
01959                                                                 $content = '<strong>The extension is installed (loaded and running)!</strong><br />'.
01960                                                                 '<a href="'.htmlspecialchars('index.php?CMD[showExt]='.$extKey.'&CMD[remove]=1').'">Click here to remove the extension: '.$this->removeButton().'</a>';
01961                                                         } else {
01962                                                                 $content = 'The extension is <strong>not</strong> installed yet.<br />'.
01963                                                                 '<a href="'.htmlspecialchars('index.php?CMD[showExt]='.$extKey.'&CMD[load]=1').'">Click here to install the extension: '.$this->installButton().'</a>';
01964                                                         }
01965                                                 } else {
01966                                                         $content = 'This extension is entered in the TYPO3_CONF_VARS[SYS][requiredExt] list and is therefore always loaded.';
01967                                                 }
01968                                                 $this->content.=$this->doc->spacer(10);
01969                                                 $this->content.=$this->doc->section('Active status:',$content,0,1);
01970 
01971                                                 if (t3lib_extMgm::isLoaded($extKey))    {
01972                                                         $updates=$this->updatesForm($extKey,$list[$extKey]);
01973                                                         if ($updates)   {
01974                                                                 $this->content.=$this->doc->spacer(10);
01975                                                                 $this->content.=$this->doc->section('Update needed:',$updates.'<br /><br />Notice: "Static data" may not <em>need</em> to be updated. You will only have to import static data each time you upgrade the extension.',0,1);
01976                                                         }
01977                                                 }
01978 
01979                                                 // Config:
01980                                                 if (@is_file($absPath.'ext_conf_template.txt')) {
01981                                                         $this->content.=$this->doc->spacer(10);
01982                                                         $this->content.=$this->doc->section('Configuration:','(<em>Notice: You may need to clear the cache after configuration of the extension. This is required if the extension adds TypoScript depending on these settings.</em>)<br /><br />',0,1);
01983                                                         $this->tsStyleConfigForm($extKey,$list[$extKey]);
01984                                                 }
01985 
01986                                                 // Show details:
01987                                                 $content = t3lib_BEfunc::cshItem('_MOD_tools_em', 'info', $GLOBALS['BACK_PATH'],'|<br/>');
01988                                                 $content.= $this->extInformationArray($extKey,$list[$extKey]);
01989 
01990                                                 $this->content.=$this->doc->spacer(10);
01991                                                 $this->content.=$this->doc->section('Details:',$content,0,1);
01992                                                 break;
01993                                         case 'upload':
01994                                                 $em = t3lib_div::_POST('em');
01995                                                 if($em['action'] == 'doUpload') {
01996                                                         $em['extKey'] = $extKey;
01997                                                         $em['extInfo'] = $list[$extKey];
01998                                                         $content = $this->uploadExtensionToTER($em);
01999                                                         $content .= $this->doc->spacer(10);
02000                                                                 // Must reload this, because EM_CONF information has been updated!
02001                                                         list($list,)=$this->getInstalledExtensions();
02002                                                 } else {
02003                                                                 // CSH:
02004                                                         $content = t3lib_BEfunc::cshItem('_MOD_tools_em', 'upload', $GLOBALS['BACK_PATH'],'|<br/>');
02005 
02006                                                                 // Upload:
02007                                                         if (substr($extKey,0,5)!='user_')       {
02008                                                                 $content.= $this->getRepositoryUploadForm($extKey,$list[$extKey]);
02009                                                                 $eC=0;
02010                                                         } else {
02011                                                                 $content.='The extensions has an extension key prefixed "user_" which indicates that it is a user-defined extension with no official unique identification. Therefore it cannot be uploaded.';
02012                                                                 $eC=2;
02013                                                         }
02014                                                         if (!$this->fe_user['username'])        {
02015                                                                 $content.= '<br /><br /><img src="'.$GLOBALS['BACK_PATH'].'gfx/icon_note.gif" width="18" height="16" align="top" alt="" />You have not configured a default username/password yet. <a href="index.php?SET[function]=3">Go to "Settings"</a> if you want to do that.<br />';
02016                                                         }
02017                                                 }
02018                                                 $this->content.=$this->doc->section('Upload extension to repository',$content,0,1,$eC);
02019                                                 break;
02020                                         case 'backup':
02021                                                 if($this->CMD['doDelete']) {
02022                                                         $content = $this->extDelete($extKey,$list[$extKey]);
02023                                                         $this->content.=$this->doc->section('Delete',$content,0,1);
02024                                                 } else {
02025                                                         $content = t3lib_BEfunc::cshItem('_MOD_tools_em', 'backup_delete', $GLOBALS['BACK_PATH'],'|<br/>');
02026                                                         $content.= $this->extBackup($extKey,$list[$extKey]);
02027                                                         $this->content.=$this->doc->section('Backup',$content,0,1);
02028 
02029                                                         $content = $this->extDelete($extKey,$list[$extKey]);
02030                                                         $this->content.=$this->doc->section('Delete',$content,0,1);
02031 
02032                                                         $content = $this->extUpdateEMCONF($extKey,$list[$extKey]);
02033                                                         $this->content.=$this->doc->section('Update EM_CONF',$content,0,1);
02034                                                 }
02035                                                 break;
02036                                         case 'dump':
02037                                                 $this->extDumpTables($extKey,$list[$extKey]);
02038                                                 break;
02039                                         case 'edit':
02040                                                 $content = t3lib_BEfunc::cshItem('_MOD_tools_em', 'editfiles', $GLOBALS['BACK_PATH'],'|<br/>');
02041                                                 $content.= $this->getFileListOfExtension($extKey,$list[$extKey]);
02042 
02043                                                 $this->content.=$this->doc->section('Extension files',$content,0,1);
02044                                                 break;
02045                                         case 'updateModule':
02046                                                 $this->content.=$this->doc->section('Update:',is_object($updateObj) ? $updateObj->main() : 'No update object',0,1);
02047                                                 break;
02048                                         default:
02049                                                 $this->extObjContent();
02050                                                 break;
02051                                 }
02052                         }
02053                 }
02054         }
02055 
02063         function requestInstallExtensions($extList)     {
02064 
02065                         // Return URL:
02066                 $returnUrl = t3lib_div::_GP('returnUrl');
02067                 $installOrImportExtension = t3lib_div::_POST('installOrImportExtension');
02068 
02069                         // Extension List:
02070                 $extArray = explode(',',$extList);
02071                 $outputRow = array();
02072                 $outputRow[] = '
02073                         <tr class="bgColor5 tableheader">
02074                                 <td>Install/Import:</td>
02075                                 <td>Extension Key:</td>
02076                         </tr>
02077                 ';
02078 
02079                 foreach($extArray as $extKey)   {
02080 
02081                                 // Check for the request:
02082                         if ($installOrImportExtension[$extKey]) {
02083                                 $this->installExtension($extKey);
02084                         }
02085 
02086                                 // Display:
02087                         if (!t3lib_extMgm::isLoaded($extKey))   {
02088                                 $outputRow[] = '
02089                                 <tr class="bgColor4">
02090                                         <td><input type="checkbox" name="'.htmlspecialchars('installOrImportExtension['.$extKey.']').'" value="1" checked="checked" /></td>
02091                                         <td>'.htmlspecialchars($extKey).'</td>
02092                                 </tr>
02093                                 ';
02094                         }
02095                 }
02096 
02097                 if (count($outputRow)>1 || !$returnUrl) {
02098                         $content = '
02099                         </form> <!-- ending page form ... -->
02100                         <form action="'.htmlspecialchars(t3lib_div::getIndpEnv('REQUEST_URI')).'" method="post">
02101                                 <table border="0" cellpadding="1" cellspacing="1">'.implode('',$outputRow).'</table>
02102                         <input type="submit" name="_" value="Import and Install selected" />
02103                         </form>
02104                         <form>  <!-- continuing page form... -->';
02105 
02106                         if ($returnUrl) {
02107                                 $content.= '
02108                                 <br/>
02109                                 <br/>
02110                                 <a href="'.htmlspecialchars($returnUrl).'">Return</a>
02111                                 ';
02112                         }
02113 
02114                         $this->content.= $this->doc->section('Import/Install Extensions:',$content,0,1);
02115                 } else {
02116                         header('Location: '.t3lib_div::locationHeaderUrl($returnUrl));
02117                 }
02118         }
02119 
02120 
02121 
02122 
02123 
02124 
02125 
02126 
02127         /***********************************
02128         *
02129         * Application Sub-functions (HTML parts)
02130         *
02131         **********************************/
02132 
02144         function updatesForm($extKey,$extInfo,$notSilent=0,$script='',$addFields='')    {
02145                 $script = $script ? $script : t3lib_div::linkThisScript();
02146                 $updates.= $this->checkDBupdates($extKey,$extInfo);
02147                 $uCache = $this->checkClearCache($extInfo);
02148                 if ($notSilent) $updates.= $uCache;
02149                 $updates.= $this->checkUploadFolder($extKey,$extInfo);
02150 
02151                 $absPath = $this->getExtPath($extKey,$extInfo['type']);
02152                 if ($notSilent && @is_file($absPath.'ext_conf_template.txt'))   {
02153                         $cForm = $this->tsStyleConfigForm($extKey,$extInfo,1,$script,$updates.$addFields.'<br />');
02154                 }
02155 
02156                 if ($updates || $cForm) {
02157                         if ($cForm)     {
02158                                 $updates = '</form>'.$cForm.'<form>';
02159                         } else {
02160                                 $updates = '</form><form action="'.htmlspecialchars($script).'" method="post">'.$updates.$addFields.'
02161                                         <br /><input type="submit" name="write" value="Make updates" />
02162                                 ';
02163                         }
02164                 }
02165                 return $updates;
02166         }
02167 
02175         function extDumpTables($extKey,$extInfo)        {
02176 
02177                 // Get dbInfo which holds the structure known from the tables.sql file
02178                 $techInfo = $this->makeDetailedExtensionAnalysis($extKey,$extInfo);
02179                 $absPath = $this->getExtPath($extKey,$extInfo['type']);
02180 
02181                 // Static tables:
02182                 if (is_array($techInfo['static']))      {
02183                         if ($this->CMD['writeSTATICdump'])      {       // Writing static dump:
02184                                 $writeFile = $absPath.'ext_tables_static+adt.sql';
02185                                 if (@is_file($writeFile))       {
02186                                         $dump_static = $this->dumpStaticTables(implode(',',$techInfo['static']));
02187                                         t3lib_div::writeFile($writeFile,$dump_static);
02188                                         $this->content.=$this->doc->section('Table and field structure required',t3lib_div::formatSize(strlen($dump_static)).'bytes written to '.substr($writeFile,strlen(PATH_site)),0,1);
02189                                 }
02190                         } else {        // Showing info about what tables to dump - and giving the link to execute it.
02191                                 $msg = 'Dumping table content for static tables:<br />';
02192                                 $msg.= '<br />'.implode('<br />',$techInfo['static']).'<br />';
02193 
02194                                 // ... then feed that to this function which will make new CREATE statements of the same fields but based on the current database content.
02195                                 $this->content.=$this->doc->section('Static tables',$msg.'<hr /><strong><a href="'.htmlspecialchars('index.php?CMD[showExt]='.$extKey.'&CMD[writeSTATICdump]=1').'">Write current static table contents to ext_tables_static+adt.sql now!</a></strong>',0,1);
02196                                 $this->content.=$this->doc->spacer(20);
02197                         }
02198                 }
02199 
02200                 // Table and field definitions:
02201                 if (is_array($techInfo['dump_tf']))     {
02202                         $dump_tf_array = $this->getTableAndFieldStructure($techInfo['dump_tf']);
02203                         $dump_tf = $this->dumpTableAndFieldStructure($dump_tf_array);
02204                         if ($this->CMD['writeTFdump'])  {
02205                                 $writeFile = $absPath.'ext_tables.sql';
02206                                 if (@is_file($writeFile))       {
02207                                         t3lib_div::writeFile($writeFile,$dump_tf);
02208                                         $this->content.=$this->doc->section('Table and field structure required',t3lib_div::formatSize(strlen($dump_tf)).'bytes written to '.substr($writeFile,strlen(PATH_site)),0,1);
02209                                 }
02210                         } else {
02211                                 $msg = 'Dumping current database structure for:<br />';
02212                                 if (is_array($techInfo['tables']))      {
02213                                         $msg.= '<br /><strong>Tables:</strong><br />'.implode('<br />',$techInfo['tables']).'<br />';
02214                                 }
02215                                 if (is_array($techInfo['fields']))      {
02216                                         $msg.= '<br /><strong>Solo-fields:</strong><br />'.implode('<br />',$techInfo['fields']).'<br />';
02217                                 }
02218 
02219                                 // ... then feed that to this function which will make new CREATE statements of the same fields but based on the current database content.
02220                                 $this->content.=$this->doc->section('Table and field structure required',$msg.'<hr /><strong><a href="'.htmlspecialchars('index.php?CMD[showExt]='.$extKey.'&CMD[writeTFdump]=1').'">Write this dump to ext_tables.sql now!</a></strong><hr />
02221                                 <pre>'.htmlspecialchars($dump_tf).'</pre>',0,1);
02222 
02223 
02224                                 $details = '                                                    This dump is based on two factors:<br />
02225                                 <ul>
02226                                 <li>1) All tablenames in ext_tables.sql which are <em>not</em> found in the "modify_tables" list in ext_emconf.php are dumped with the current database structure.</li>
02227                                 <li>2) For any tablenames which <em>are</em> listed in "modify_tables" all fields and keys found for the table in ext_tables.sql will be re-dumped with the fresh equalents from the database.</li>
02228                                 </ul>
02229                                 Bottomline is: Whole tables are dumped from database with no regard to which fields and keys are defined in ext_tables.sql. But for tables which are only modified, any NEW fields added to the database must in some form or the other exist in the ext_tables.sql file as well.<br />';
02230                                 $this->content.=$this->doc->section('',$details);
02231                         }
02232                 }
02233         }
02234 
02242         function getFileListOfExtension($extKey,$conf)  {
02243                 $content = '';
02244                 $extPath = $this->getExtPath($extKey,$conf['type']);
02245 
02246                 if ($extPath)   {
02247                         // Read files:
02248                         $fileArr = array();
02249                         $fileArr = t3lib_div::getAllFilesAndFoldersInPath($fileArr,$extPath);
02250 
02251                         // Start table:
02252                         $lines = array();
02253                         $totalSize = 0;
02254 
02255                         // Header:
02256                         $lines[] = '
02257                                 <tr class="bgColor5">
02258                                         <td>File:</td>
02259                                         <td>Size:</td>
02260                                         <td>Edit:</td>
02261                                 </tr>';
02262 
02263                         foreach($fileArr as $file)      {
02264                                 $fI = t3lib_div::split_fileref($file);
02265                                 $lines[] = '
02266                                 <tr class="bgColor4">
02267                                         <td><a href="'.htmlspecialchars('index.php?CMD[showExt]='.$extKey.'&CMD[downloadFile]='.rawurlencode($file)).'" title="Download...">'.substr($file,strlen($extPath)).'</a></td>
02268                                         <td>'.t3lib_div::formatSize(filesize($file)).'</td>
02269                                         <td>'.(!in_array($extKey,$this->requiredExt)&&t3lib_div::inList($this->editTextExtensions,($fI['fileext']?$fI['fileext']:$fI['filebody']))?'<a href="'.htmlspecialchars('index.php?CMD[showExt]='.$extKey.'&CMD[editFile]='.rawurlencode($file)).'">Edit file</a>':'').'</td>
02270                                 </tr>';
02271                                 $totalSize+=filesize($file);
02272                         }
02273 
02274                         $lines[] = '
02275                                 <tr class="bgColor6">
02276                                         <td><strong>Total:</strong></td>
02277                                         <td><strong>'.t3lib_div::formatSize($totalSize).'</strong></td>
02278                                         <td>&nbsp;</td>
02279                                 </tr>';
02280 
02281                         $content = '
02282                         Path: '.$extPath.'<br /><br />
02283                         <table border="0" cellpadding="1" cellspacing="2">'.implode('',$lines).'</table>';
02284                 }
02285 
02286                 return $content;
02287         }
02288 
02296         function extDelete($extKey,$extInfo)    {
02297                 $absPath = $this->getExtPath($extKey,$extInfo['type']);
02298                 if (t3lib_extMgm::isLoaded($extKey))    {
02299                         return 'This extension is currently installed (loaded and active) and so cannot be deleted!';
02300                 } elseif (!$this->deleteAsType($extInfo['type'])) {
02301                         return 'You cannot delete (and install/update) extensions in the '.$this->typeLabels[$extInfo['type']].' scope.';
02302                 } elseif (t3lib_div::inList('G,L',$extInfo['type'])) {
02303                         if ($this->CMD['doDelete'] && !strcmp($absPath,$this->CMD['absPath'])) {
02304                                 $res = $this->removeExtDirectory($absPath);
02305                                 if ($res) {
02306                                         return 'ERROR: Could not remove extension directory "'.$absPath.'". Had the following errors:<br /><br />'.
02307                                         nl2br($res);
02308                                 } else {
02309                                         return 'Removed extension in path "'.$absPath.'"!';
02310                                 }
02311                         } else {
02312                                 $onClick = "if (confirm('Are you sure you want to delete this extension from the server?')) {window.location.href='index.php?CMD[showExt]=".$extKey.'&CMD[doDelete]=1&CMD[absPath]='.rawurlencode($absPath)."';}";
02313                                 $content.= '<a href="#" onclick="'.htmlspecialchars($onClick).' return false;"><strong>DELETE EXTENSION FROM SERVER</strong> (in the "'.$this->typeLabels[$extInfo['type']].'" location "'.substr($absPath,strlen(PATH_site)).'")!</a>';
02314                                 $content.= '<br /><br />(Maybe you should make a backup first, see above.)';
02315                                 return $content;
02316                         }
02317                 } else return 'Extension is not a global or local extension and cannot be removed.';
02318         }
02319 
02327         function extUpdateEMCONF($extKey,$extInfo)      {
02328                 $absPath = $this->getExtPath($extKey,$extInfo['type']);
02329                 if ($this->CMD['doUpdateEMCONF']) {
02330                         return $this->updateLocalEM_CONF($extKey,$extInfo);
02331                 } else {
02332                         $onClick = "if (confirm('Are you sure you want to update EM_CONF?')) {window.location.href='index.php?CMD[showExt]=".$extKey."&CMD[doUpdateEMCONF]=1';}";
02333                         $content.= '<a href="#" onclick="'.htmlspecialchars($onClick).' return false;"><strong>Update extension EM_CONF file</strong> (in the "'.$this->typeLabels[$extInfo['type']].'" location "'.substr($absPath,strlen(PATH_site)).'")!</a>';
02334                         $content.= '<br /><br />If files are changed, added or removed to an extension this is normally detected and displayed so you know that this extension has been locally altered and may need to be uploaded or at least not overridden.<br />
02335                                                 Updating this file will first of all reset this registration.';
02336                         return $content;
02337                 }
02338         }
02339 
02347         function extBackup($extKey,$extInfo)    {
02348                 $uArr = $this->makeUploadArray($extKey,$extInfo);
02349                 if (is_array($uArr))    {
02350                         $backUpData = $this->terConnection->makeUploadDataFromArray($uArr);
02351                         $filename = 'T3X_'.$extKey.'-'.str_replace('.','_',$extInfo['EM_CONF']['version']).'-z-'.date('YmdHi').'.t3x';
02352                         if (intval($this->CMD['doBackup'])==1)  {
02353                                 header('Content-Type: application/octet-stream');
02354                                 header('Content-Disposition: attachment; filename='.$filename);
02355                                 echo $backUpData;
02356                                 exit;
02357                         } elseif ($this->CMD['dumpTables'])     {
02358                                 $filename='T3X_'.$extKey;
02359                                 $cTables = count(explode(',',$this->CMD['dumpTables']));
02360                                 if ($cTables>1) {
02361                                         $filename.='-'.$cTables.'tables';
02362                                 } else {
02363                                         $filename.='-'.$this->CMD['dumpTables'];
02364                                 }
02365                                 $filename.='+adt.sql';
02366 
02367                                 header('Content-Type: application/octet-stream');
02368                                 header('Content-Disposition: attachment; filename='.$filename);
02369                                 echo $this->dumpStaticTables($this->CMD['dumpTables']);
02370                                 exit;
02371                         } else {
02372                                 $techInfo = $this->makeDetailedExtensionAnalysis($extKey,$extInfo);
02373                                 $lines=array();
02374                                 $lines[]='<tr class="bgColor5"><td colspan="2"><strong>Make selection:</strong></td></tr>';
02375                                 $lines[]='<tr class="bgColor4"><td><strong>Extension files:</strong></td><td>'.
02376                                 '<a href="'.htmlspecialchars('index.php?CMD[doBackup]=1&CMD[showExt]='.$extKey).'">Download extension "'.$extKey.'" as a file</a><br />('.$filename.', '.t3lib_div::formatSize(strlen($backUpData)).', MD5: '.md5($backUpData).')<br /></td></tr>';
02377 
02378                                 if (is_array($techInfo['tables']))      {       $lines[]='<tr class="bgColor4"><td><strong>Data tables:</strong></td><td>'.$this->extBackup_dumpDataTablesLine($techInfo['tables'],$extKey).'</td></tr>';       }
02379                                 if (is_array($techInfo['static']))      {       $lines[]='<tr class="bgColor4"><td><strong>Static tables:</strong></td><td>'.$this->extBackup_dumpDataTablesLine($techInfo['static'],$extKey).'</td></tr>';     }
02380 
02381                                 $content = '<table border="0" cellpadding="2" cellspacing="2">'.implode('',$lines).'</table>';
02382                                 return $content;
02383                         }
02384                 } else die('Error...');
02385         }
02386 
02394         function extBackup_dumpDataTablesLine($tablesArray,$extKey)     {
02395                 $tables = array();
02396                 $tablesNA = array();
02397 
02398                 foreach($tablesArray as $tN)    {
02399                         $res = $GLOBALS['TYPO3_DB']->exec_SELECTquery('count(*)', $tN, '');
02400                         if (!$GLOBALS['TYPO3_DB']->sql_error()) {
02401                                 $row = $GLOBALS['TYPO3_DB']->sql_fetch_row($res);
02402                                 $tables[$tN]='<tr><td>&nbsp;</td><td><a href="'.htmlspecialchars('index.php?CMD[dumpTables]='.rawurlencode($tN).'&CMD[showExt]='.$extKey).'" title="Dump table \''.$tN.'\'">'.$tN.'</a></td><td>&nbsp;&nbsp;&nbsp;</td><td>'.$row[0].' records</td></tr>';
02403                         } else {
02404                                 $tablesNA[$tN]='<tr><td>&nbsp;</td><td>'.$tN.'</td><td>&nbsp;</td><td>Did not exist.</td></tr>';
02405                         }
02406                 }
02407                 $label = '<table border="0" cellpadding="0" cellspacing="0">'.implode('',array_merge($tables,$tablesNA)).'</table>';// Candidate for t3lib_div::array_merge() if integer-keys will some day make trouble...
02408                 if (count($tables))     {
02409                         $label = '<a href="'.htmlspecialchars('index.php?CMD[dumpTables]='.rawurlencode(implode(',',array_keys($tables))).'&CMD[showExt]='.$extKey).'" title="Dump all existing tables.">Download all data from:</a><br /><br />'.$label;
02410                 } else $label = 'Nothing to dump...<br /><br />'.$label;
02411                 return $label;
02412         }
02413 
02422         function extInformationArray($extKey,$extInfo,$remote=0)        {
02423                 $lines=array();
02424                 $lines[]='<tr class="bgColor5"><td colspan="2"><strong>General information:</strong></td>'.$this->helpCol('').'</tr>';
02425                 $lines[]='<tr class="bgColor4"><td>Title:</td><td>'.$extInfo['EM_CONF']['_icon'].$extInfo['EM_CONF']['title'].'</td>'.$this->helpCol('title').'</tr>';
02426                 $lines[]='<tr class="bgColor4"><td>Description:</td><td>'.nl2br(htmlspecialchars($extInfo['EM_CONF']['description'])).'</td>'.$this->helpCol('description').'</tr>';
02427                 $lines[]='<tr class="bgColor4"><td>Author:</td><td>'.$this->wrapEmail($extInfo['EM_CONF']['author'].($extInfo['EM_CONF']['author_email'] ? ' <'.$extInfo['EM_CONF']['author_email'].'>' : ''),$extInfo['EM_CONF']['author_email']).($extInfo['EM_CONF']['author_company']?', '.$extInfo['EM_CONF']['author_company']:'').
02428                 '</td>'.$this->helpCol('description').'</tr>';
02429 
02430                 $lines[]='<tr class="bgColor4"><td>Version:</td><td>'.$extInfo['EM_CONF']['version'].'</td>'.$this->helpCol('version').'</tr>';
02431                 $lines[]='<tr class="bgColor4"><td>Category:</td><td>'.$this->categories[$extInfo['EM_CONF']['category']].'</td>'.$this->helpCol('category').'</tr>';
02432                 $lines[]='<tr class="bgColor4"><td>State:</td><td>'.$this->states[$extInfo['EM_CONF']['state']].'</td>'.$this->helpCol('state').'</tr>';
02433                 $lines[]='<tr class="bgColor4"><td>Shy?</td><td>'.($extInfo['EM_CONF']['shy']?'Yes':'').'</td>'.$this->helpCol('shy').'</tr>';
02434                 $lines[]='<tr class="bgColor4"><td>Internal?</td><td>'.($extInfo['EM_CONF']['internal']?'Yes':'').'</td>'.$this->helpCol('internal').'</tr>';
02435 
02436                 $lines[]='<tr class="bgColor4"><td>Depends on:</td><td>'.$this->depToString($extInfo['EM_CONF']['constraints']).'</td>'.$this->helpCol('dependencies').'</tr>';
02437                 $lines[]='<tr class="bgColor4"><td>Conflicts with:</td><td>'.$this->depToString($extInfo['EM_CONF']['constraints'],'conflicts').'</td>'.$this->helpCol('dependencies').'</tr>';
02438                 $lines[]='<tr class="bgColor4"><td>Suggests:</td><td>'.$this->depToString($extInfo['EM_CONF']['constraints'],'suggests').'</td>'.$this->helpCol('dependencies').'</tr>';
02439                 if (!$remote)   {
02440                         $lines[]='<tr class="bgColor4"><td>Priority:</td><td>'.$extInfo['EM_CONF']['priority'].'</td>'.$this->helpCol('priority').'</tr>';
02441                         $lines[]='<tr class="bgColor4"><td>Clear cache?</td><td>'.($extInfo['EM_CONF']['clearCacheOnLoad']?'Yes':'').'</td>'.$this->helpCol('clearCacheOnLoad').'</tr>';
02442                         $lines[]='<tr class="bgColor4"><td>Includes modules:</td><td>'.$extInfo['EM_CONF']['module'].'</td>'.$this->helpCol('module').'</tr>';
02443                         $lines[]='<tr class="bgColor4"><td>Lock Type?</td><td>'.($extInfo['EM_CONF']['lockType']?$extInfo['EM_CONF']['lockType']:'').'</td>'.$this->helpCol('lockType').'</tr>';
02444                         $lines[]='<tr class="bgColor4"><td>Modifies tables:</td><td>'.$extInfo['EM_CONF']['modify_tables'].'</td>'.$this->helpCol('modify_tables').'</tr>';
02445 
02446                         // Installation status:
02447                         $techInfo = $this->makeDetailedExtensionAnalysis($extKey,$extInfo,1);
02448                         $lines[]='<tr><td>&nbsp;</td><td></td>'.$this->helpCol('').'</tr>';
02449                         $lines[]='<tr class="bgColor5"><td colspan="2"><strong>Installation status:</strong></td>'.$this->helpCol('').'</tr>';
02450                         $lines[]='<tr class="bgColor4"><td>Type of install:</td><td>'.$this->typeLabels[$extInfo['type']].' - <em>'.$this->typeDescr[$extInfo['type']].'</em></td>'.$this->helpCol('type').'</tr>';
02451                         $lines[]='<tr class="bgColor4"><td>Double installs?</td><td>'.$this->extInformationArray_dbInst($extInfo['doubleInstall'],$extInfo['type']).'</td>'.$this->helpCol('doubleInstall').'</tr>';
02452                         if (is_array($extInfo['files']))        {
02453                                 sort($extInfo['files']);
02454                                 $lines[]='<tr class="bgColor4"><td>Root files:</td><td>'.implode('<br />',$extInfo['files']).'</td>'.$this->helpCol('rootfiles').'</tr>';
02455                         }
02456 
02457                         if ($techInfo['tables']||$techInfo['static']||$techInfo['fields'])      {
02458                                 if (!$remote && t3lib_extMgm::isLoaded($extKey))        {
02459                                         $tableStatus = $GLOBALS['TBE_TEMPLATE']->rfw(($techInfo['tables_error']?'<strong>Table error!</strong><br />Probably one or more required fields/tables are missing in the database!':'').
02460                                         ($techInfo['static_error']?'<strong>Static table error!</strong><br />The static tables are missing or empty!':''));
02461                                 } else {
02462                                         $tableStatus = $techInfo['tables_error']||$techInfo['static_error'] ? 'The database will need to be updated when this extension is installed.' : 'All required tables are already in the database!';
02463                                 }
02464                         }
02465 
02466                         $lines[]='<tr class="bgColor4"><td>Database requirements:</td><td>'.$this->extInformationArray_dbReq($techInfo,1).'</td>'.$this->helpCol('dbReq').'</tr>';
02467                         $lines[]='<tr class="bgColor4"><td>Database status:</td><td>'.$tableStatus.'</td>'.$this->helpCol('dbStatus').'</tr>';
02468                         $lines[]='<tr class="bgColor4"><td>Flags:</td><td>'.(is_array($techInfo['flags'])?implode('<br />',$techInfo['flags']):'').'</td>'.$this->helpCol('flags').'</tr>';
02469                         $lines[]='<tr class="bgColor4"><td>Config template?</td><td>'.($techInfo['conf']?'Yes':'').'</td>'.$this->helpCol('conf').'</tr>';
02470                         $lines[]='<tr class="bgColor4"><td>TypoScript files:</td><td>'.(is_array($techInfo['TSfiles'])?implode('<br />',$techInfo['TSfiles']):'').'</td>'.$this->helpCol('TSfiles').'</tr>';
02471                         $lines[]='<tr class="bgColor4"><td>Language files:</td><td>'.(is_array($techInfo['locallang'])?implode('<br />',$techInfo['locallang']):'').'</td>'.$this->helpCol('locallang').'</tr>';
02472                         $lines[]='<tr class="bgColor4"><td>Upload folder:</td><td>'.($techInfo['uploadfolder']?$techInfo['uploadfolder']:'').'</td>'.$this->helpCol('uploadfolder').'</tr>';
02473                         $lines[]='<tr class="bgColor4"><td>Create directories:</td><td>'.(is_array($techInfo['createDirs'])?implode('<br />',$techInfo['createDirs']):'').'</td>'.$this->helpCol('createDirs').'</tr>';
02474                         $lines[]='<tr class="bgColor4"><td>Module names:</td><td>'.(is_array($techInfo['moduleNames'])?implode('<br />',$techInfo['moduleNames']):'').'</td>'.$this->helpCol('moduleNames').'</tr>';
02475                         $lines[]='<tr class="bgColor4"><td>Class names:</td><td>'.(is_array($techInfo['classes'])?implode('<br />',$techInfo['classes']):'').'</td>'.$this->helpCol('classNames').'</tr>';
02476                         $lines[]='<tr class="bgColor4"><td>Code warnings:<br />(developer-relevant)</td><td>'.(is_array($techInfo['errors'])?$GLOBALS['TBE_TEMPLATE']->rfw(implode('<br />',$techInfo['errors'])):'').'</td>'.$this->helpCol('errors').'</tr>';
02477                         $lines[]='<tr class="bgColor4"><td>Naming annoyances:<br />(developer-relevant)</td><td>'.(is_array($techInfo['NSerrors']) ? (!t3lib_div::inList($this->nameSpaceExceptions,$extKey)?t3lib_div::view_array($techInfo['NSerrors']):$GLOBALS['TBE_TEMPLATE']->dfw('[exception]')) : '').'</td>'.$this->helpCol('NSerrors').'</tr>';
02478 
02479                         $currentMd5Array = $this->serverExtensionMD5Array($extKey,$extInfo);
02480                         $affectedFiles='';
02481 
02482                         $msgLines=array();
02483                         if (strcmp($extInfo['EM_CONF']['_md5_values_when_last_written'],serialize($currentMd5Array)))   {
02484                                 $msgLines[] = $GLOBALS['TBE_TEMPLATE']->rfw('<br /><strong>A difference between the originally installed version and the current was detected!</strong>');
02485                                 $affectedFiles = $this->findMD5ArrayDiff($currentMd5Array,unserialize($extInfo['EM_CONF']['_md5_values_when_last_written']));
02486                                 if (count($affectedFiles))      $msgLines[] = '<br /><strong>Modified files:</strong><br />'.$GLOBALS['TBE_TEMPLATE']->rfw(implode('<br />',$affectedFiles));
02487                         }
02488                         $lines[]='<tr class="bgColor4"><td>Files changed?</td><td>'.implode('<br />',$msgLines).'</td>'.$this->helpCol('filesChanged').'</tr>';
02489                 }
02490 
02491                 return '<table border="0" cellpadding="1" cellspacing="2">
02492                                         '.implode('
02493                                         ',$lines).'
02494                                 </table>';
02495         }
02496 
02504         function extInformationArray_dbReq($techInfo,$tableHeader=0)    {
02505                 return nl2br(trim((is_array($techInfo['tables'])?($tableHeader?"\n\n<strong>Tables:</strong>\n":'').implode(chr(10),$techInfo['tables']):'').
02506                 (is_array($techInfo['static'])?"\n\n<strong>Static tables:</strong>\n".implode(chr(10),$techInfo['static']):'').
02507                 (is_array($techInfo['fields'])?"\n\n<strong>Additional fields:</strong>\n".implode('<hr />',$techInfo['fields']):'')));
02508         }
02509 
02517         function extInformationArray_dbInst($dbInst,$current)   {
02518                 if (strlen($dbInst)>1)  {
02519                         $others = array();
02520                         for($a=0;$a<strlen($dbInst);$a++)       {
02521                                 if (substr($dbInst,$a,1)!=$current)     {
02522                                         $others[]='"'.$this->typeLabels[substr($dbInst,$a,1)].'"';
02523                                 }
02524                         }
02525                         return $GLOBALS['TBE_TEMPLATE']->rfw('A '.implode(' and ',$others).' extension with this key is also available on the server, but cannot be loaded because the "'.$this->typeLabels[$current].'" version takes precedence.');
02526                 } else return '';
02527         }
02528 
02536         function getRepositoryUploadForm($extKey,$extInfo)      {
02537                 $content.='
02538                         <input type="hidden" name="CMD[showExt]" value="'.$extKey.'" />
02539                         <input type="hidden" name="em[action]" value="doUpload" />
02540                         <table border="0" cellpadding="2" cellspacing="1">
02541                                 <tr class="bgColor4">
02542                                         <td>Repository Username:</td>
02543                                         <td><input'.$this->doc->formWidth(20).' type="text" name="em[user][fe_u]" value="'.$this->fe_user['username'].'" /></td>
02544                                 </tr>
02545                                 <tr class="bgColor4">
02546                                         <td>Repository Password:</td>
02547                                         <td><input'.$this->doc->formWidth(20).' type="password" name="em[user][fe_p]" value="'.$this->fe_user['password'].'" /></td>
02548                                 </tr>
02549                                 <tr class="bgColor4">
02550                                         <td>Changelog for upload:</td>
02551                                         <td><textarea'.$this->doc->formWidth(30,1).' rows="5" name="em[upload][comment]"></textarea></td>
02552                                 </tr>
02553                                 <tr class="bgColor4">
02554                                         <td>Upload command:</td>
02555                                         <td nowrap="nowrap">
02556                                                 <input type="radio" name="em[upload][mode]" value="new_dev" checked="checked" /> New development version (latest x.x.<strong>'.$GLOBALS['TBE_TEMPLATE']->rfw('x+1').'</strong>)<br />
02557                                                 <input type="radio" name="em[upload][mode]" value="latest" /> Override <em>this</em> development version ('.$extInfo['EM_CONF']['version'].')<br />
02558                                                 <input type="radio" name="em[upload][mode]" value="new_sub" /> New sub version (latest x.<strong>'.$GLOBALS['TBE_TEMPLATE']->rfw('x+1').'</strong>.0)<br />
02559                                                 <input type="radio" name="em[upload][mode]" value="new_main" /> New main version (latest <strong>'.$GLOBALS['TBE_TEMPLATE']->rfw('x+1').'</strong>.0.0)<br />
02560                                                 <input type="radio" name="em[upload][mode]" value="custom" /> This version: <input type="text" name="em[upload][version]" /><br />
02561                                         </td>
02562                                 </tr>
02563                                 <tr class="bgColor4">
02564                                         <td>&nbsp;</td>
02565                                         <td><input type="submit" name="submit" value="Upload extension" />
02566                                         </td>
02567                                 </tr>
02568                         </table>
02569                         ';
02570 
02571                 return $content;
02572         }
02573 
02574 
02575 
02576 
02577 
02578 
02579 
02580 
02581 
02582 
02583         /***********************************
02584         *
02585         * Extension list rendering
02586         *
02587         **********************************/
02588 
02597         function extensionListRowHeader($trAttrib,$cells,$import=0)     {
02598                 $cells[] = '<td></td>';
02599                 $cells[] = '<td>Title:</td>';
02600 
02601                 if (!$this->MOD_SETTINGS['display_details'])    {
02602                         $cells[] = '<td>Description:</td>';
02603                         $cells[] = '<td>Author:</td>';
02604                 } elseif ($this->MOD_SETTINGS['display_details']==2)    {
02605                         $cells[] = '<td>Priority:</td>';
02606                         $cells[] = '<td>Mod.Tables:</td>';
02607                         $cells[] = '<td>Modules:</td>';
02608                         $cells[] = '<td>Cl.Cache?</td>';
02609                         $cells[] = '<td>Internal?</td>';
02610                         $cells[] = '<td>Shy?</td>';
02611                 } elseif ($this->MOD_SETTINGS['display_details']==3)    {
02612                         $cells[] = '<td>Tables/Fields:</td>';
02613                         $cells[] = '<td>TS-files:</td>';
02614                         $cells[] = '<td>Affects:</td>';
02615                         $cells[] = '<td>Modules:</td>';
02616                         $cells[] = '<td>Config?</td>';
02617                         $cells[] = '<td>Code warnings:</td>';
02618                 } elseif ($this->MOD_SETTINGS['display_details']==4)    {
02619                         $cells[] = '<td>locallang:</td>';
02620                         $cells[] = '<td>Classes:</td>';
02621                         $cells[] = '<td>Code warnings:</td>';
02622                         $cells[] = '<td>Nameing annoyances:</td>';
02623                 } elseif ($this->MOD_SETTINGS['display_details']==5)    {
02624                         $cells[] = '<td>Changed files:</td>';
02625                 } else {
02626                         $cells[] = '<td>Extension key:</td>';
02627                         $cells[] = '<td>Version:</td>';
02628                         if (!$import) {
02629                                 $cells[] = '<td>DL:</td>';
02630                                 $cells[] = '<td>Doc:</td>';
02631                                 $cells[] = '<td>Type:</td>';
02632                         } else {
02633                                 $cells[] = '<td class="bgColor6"'.$this->labelInfo('Current version of the extension on this server. If colored red there is a newer version in repository! Then you should upgrade.').'>Cur. Ver:</td>';
02634                                 $cells[] = '<td class="bgColor6"'.$this->labelInfo('Current type of installation of the extension on this server.').'>Cur. Type:</td>';
02635                                 $cells[] = '<td'.$this->labelInfo('Number of downloads, all versions/this version').'>DL:</td>';
02636                         }
02637                         $cells[] = '<td>State:</td>';
02638                 }
02639                 return '
02640                         <tr'.$trAttrib.'>
02641                                 '.implode('
02642                                 ',$cells).'
02643                         </tr>';
02644         }
02645 
02658         function extensionListRow($extKey,$extInfo,$cells,$bgColorClass='',$inst_list=array(),$import=0,$altLinkUrl='') {
02659 
02660                         // Icon:
02661                 $imgInfo = @getImageSize($this->getExtPath($extKey,$extInfo['type']).'/ext_icon.gif');
02662                 if (is_array($imgInfo)) {
02663                         $cells[] = '<td><img src="'.$GLOBALS['BACK_PATH'].$this->typeRelPaths[$extInfo['type']].$extKey.'/ext_icon.gif'.'" '.$imgInfo[3].' alt="" /></td>';
02664                 } elseif ($extInfo['_ICON']) {
02665                         $cells[] = '<td>'.$extInfo['_ICON'].'</td>';
02666                 } else {
02667                         $cells[] = '<td><img src="clear.gif" width="1" height="1" alt="" /></td>';
02668                 }
02669 
02670                         // Extension title:
02671                 $cells[] = '<td nowrap="nowrap"><a href="'.htmlspecialchars($altLinkUrl?$altLinkUrl:'index.php?CMD[showExt]='.$extKey.'&SET[singleDetails]=info').'" title="'.$extKey.'"'/*.($extInfo['EM_CONF']['shy'] ? ' style="color:#666;" ' : '')*/.'>'.t3lib_div::fixed_lgd($extInfo['EM_CONF']['title']?$extInfo['EM_CONF']['title']:'<em>'.$extKey.'</em>',40).'</a></td>';
02672 
02673                         // Based on which display mode you will see more or less details:
02674                 if (!$this->MOD_SETTINGS['display_details'])    {
02675                         $cells[] = '<td>'.htmlspecialchars(t3lib_div::fixed_lgd($extInfo['EM_CONF']['description'],400)).'<br /><img src="clear.gif" width="300" height="1" alt="" /></td>';
02676                         $cells[] = '<td nowrap="nowrap">'.($extInfo['EM_CONF']['author_email'] ? '<a href="mailto:'.htmlspecialchars($extInfo['EM_CONF']['author_email']).'">' : '').htmlspecialchars($extInfo['EM_CONF']['author']).($extInfo['EM_CONF']['author_email'] ? '</a>' : '').($extInfo['EM_CONF']['author_company'] ? '<br />'.htmlspecialchars($extInfo['EM_CONF']['author_company']) : '').'</td>';
02677                 } elseif ($this->MOD_SETTINGS['display_details']==2)    {
02678                         $cells[] = '<td nowrap="nowrap">'.$extInfo['EM_CONF']['priority'].'</td>';
02679                         $cells[] = '<td nowrap="nowrap">'.implode('<br />',t3lib_div::trimExplode(',',$extInfo['EM_CONF']['modify_tables'],1)).'</td>';
02680                         $cells[] = '<td nowrap="nowrap">'.$extInfo['EM_CONF']['module'].'</td>';
02681                         $cells[] = '<td nowrap="nowrap">'.($extInfo['EM_CONF']['clearCacheOnLoad'] ? 'Yes' : '').'</td>';
02682                         $cells[] = '<td nowrap="nowrap">'.($extInfo['EM_CONF']['internal'] ? 'Yes' : '').'</td>';
02683                         $cells[] = '<td nowrap="nowrap">'.($extInfo['EM_CONF']['shy'] ? 'Yes' : '').'</td>';
02684                 } elseif ($this->MOD_SETTINGS['display_details']==3)    {
02685                         $techInfo = $this->makeDetailedExtensionAnalysis($extKey,$extInfo);
02686 
02687                         $cells[] = '<td>'.$this->extInformationArray_dbReq($techInfo).
02688                         '</td>';
02689                         $cells[] = '<td nowrap="nowrap">'.(is_array($techInfo['TSfiles']) ? implode('<br />',$techInfo['TSfiles']) : '').'</td>';
02690                         $cells[] = '<td nowrap="nowrap">'.(is_array($techInfo['flags']) ? implode('<br />',$techInfo['flags']) : '').'</td>';
02691                         $cells[] = '<td nowrap="nowrap">'.(is_array($techInfo['moduleNames']) ? implode('<br />',$techInfo['moduleNames']) : '').'</td>';
02692                         $cells[] = '<td nowrap="nowrap">'.($techInfo['conf'] ? 'Yes' : '').'</td>';
02693                         $cells[] = '<td>'.
02694                         $GLOBALS['TBE_TEMPLATE']->rfw((t3lib_extMgm::isLoaded($extKey)&&$techInfo['tables_error']?'<strong>Table error!</strong><br />Probably one or more required fields/tables are missing in the database!':'').
02695                         (t3lib_extMgm::isLoaded($extKey)&&$techInfo['static_error']?'<strong>Static table error!</strong><br />The static tables are missing or empty!':'')).
02696                         '</td>';
02697                 } elseif ($this->MOD_SETTINGS['display_details']==4)    {
02698                         $techInfo=$this->makeDetailedExtensionAnalysis($extKey,$extInfo,1);
02699 
02700                         $cells[] = '<td>'.(is_array($techInfo['locallang']) ? implode('<br />',$techInfo['locallang']) : '').'</td>';
02701                         $cells[] = '<td>'.(is_array($techInfo['classes']) ? implode('<br />',$techInfo['classes']) : '').'</td>';
02702                         $cells[] = '<td>'.(is_array($techInfo['errors']) ? $GLOBALS['TBE_TEMPLATE']->rfw(implode('<hr />',$techInfo['errors'])) : '').'</td>';
02703                         $cells[] = '<td>'.(is_array($techInfo['NSerrors']) ? (!t3lib_div::inList($this->nameSpaceExceptions,$extKey) ? t3lib_div::view_array($techInfo['NSerrors']) : $GLOBALS['TBE_TEMPLATE']->dfw('[exception]')) :'').'</td>';
02704                 } elseif ($this->MOD_SETTINGS['display_details']==5)    {
02705                         $currentMd5Array = $this->serverExtensionMD5Array($extKey,$extInfo);
02706                         $affectedFiles = '';
02707                         $msgLines = array();
02708                         $msgLines[] = 'Files: '.count($currentMd5Array);
02709                         if (strcmp($extInfo['EM_CONF']['_md5_values_when_last_written'],serialize($currentMd5Array)))   {
02710                                 $msgLines[] = $GLOBALS['TBE_TEMPLATE']->rfw('<br /><strong>A difference between the originally installed version and the current was detected!</strong>');
02711                                 $affectedFiles = $this->findMD5ArrayDiff($currentMd5Array,unserialize($extInfo['EM_CONF']['_md5_values_when_last_written']));
02712                                 if (count($affectedFiles))      $msgLines[] = '<br /><strong>Modified files:</strong><br />'.$GLOBALS['TBE_TEMPLATE']->rfw(implode('<br />',$affectedFiles));
02713                         }
02714                         $cells[] = '<td>'.implode('<br />',$msgLines).'</td>';
02715                 } else {
02716                                 // Default view:
02717                         $verDiff = $inst_list[$extKey] && $this->versionDifference($extInfo['EM_CONF']['version'],$inst_list[$extKey]['EM_CONF']['version'],$this->versionDiffFactor);
02718 
02719                         $cells[] = '<td nowrap="nowrap"><em>'.$extKey.'</em></td>';
02720                         $cells[] = '<td nowrap="nowrap">'.($verDiff ? '<strong>'.$GLOBALS['TBE_TEMPLATE']->rfw(htmlspecialchars($extInfo['EM_CONF']['version'])).'</strong>' : $extInfo['EM_CONF']['version']).'</td>';
02721                         if (!$import) {         // Listing extenson on LOCAL server:
02722                                         // Extension Download:
02723                                 $cells[] = '<td nowrap="nowrap"><a href="'.htmlspecialchars('index.php?CMD[doBackup]=1&SET[singleDetails]=backup&CMD[showExt]='.$extKey).'"><img src="download.png" width="13" height="12" title="Download" alt="" /></a></td>';
02724 
02725                                         // Manual download
02726                                 $fileP = PATH_site.$this->typePaths[$extInfo['type']].$extKey.'/doc/manual.sxw';
02727                                 $cells[] = '<td nowrap="nowrap">'.
02728                                 ($this->typePaths[$extInfo['type']] && @is_file($fileP)?'<a href="'.htmlspecialchars(t3lib_div::resolveBackPath($this->doc->backPath.'../'.$this->typePaths[$extInfo['type']].$extKey.'/doc/manual.sxw')).'" target="_blank"><img src="oodoc.gif" width="13" height="16" title="Local Open Office Manual" alt="" /></a>':'').
02729                                 '</td>';
02730                                 $cells[] = '<td nowrap="nowrap">'.$this->typeLabels[$extInfo['type']].(strlen($extInfo['doubleInstall'])>1?'<strong> '.$GLOBALS['TBE_TEMPLATE']->rfw($extInfo['doubleInstall']).'</strong>':'').'</td>';
02731                         } else {        // Listing extensions from REMOTE repository:
02732                                 $inst_curVer = $inst_list[$extKey]['EM_CONF']['version'];
02733                                 if (isset($inst_list[$extKey])) {
02734                                         if ($verDiff)   $inst_curVer = '<strong>'.$GLOBALS['TBE_TEMPLATE']->rfw($inst_curVer).'</strong>';
02735                                 }
02736                                 $cells[] = '<td nowrap="nowrap">'.$inst_curVer.'</td>';
02737                                 $cells[] = '<td nowrap="nowrap">'.$this->typeLabels[$inst_list[$extKey]['type']].(strlen($inst_list[$extKey]['doubleInstall'])>1?'<strong> '.$GLOBALS['TBE_TEMPLATE']->rfw($inst_list[$extKey]['doubleInstall']).'</strong>':'').'</td>';
02738                                 $cells[] = '<td nowrap="nowrap">'.($extInfo['downloadcounter_all']?$extInfo['downloadcounter_all']:'&nbsp;&nbsp;').'/'.($extInfo['downloadcounter']?$extInfo['downloadcounter']:'&nbsp;').'</td>';
02739                         }
02740                         $cells[] = '<td nowrap="nowrap" class="extstate" style="background-color:'.$this->stateColors[$extInfo['EM_CONF']['state']].';">'.$this->states[$extInfo['EM_CONF']['state']].'</td>';
02741                 }
02742 
02743                 if($this->xmlhandler->getReviewState($extKey,$extInfo['EM_CONF']['version'])<1) {
02744                         $bgclass = ' class="unsupported-ext"';
02745                 } else {
02746                         $bgclass = ' class="'.($bgColorClass?$bgColorClass:'bgColor4').'"';
02747                 }
02748 
02749                 return '
02750                         <tr'.$bgclass.'>
02751                                 '.implode('
02752                                 ',$cells).'
02753                         </tr>';
02754         }
02755 
02756 
02757 
02758 
02759 
02760 
02761         /************************************
02762         *
02763         * Output helper functions
02764         *
02765         ************************************/
02766 
02774         function wrapEmail($str,$email) {
02775                 if ($email)     {
02776                         $str = '<a href="mailto:'.htmlspecialchars($email).'">'.htmlspecialchars($str).'</a>';
02777                 }
02778                 return $str;
02779         }
02780 
02787         function helpCol($key)  {
02788                 global $BE_USER;
02789                 if ($BE_USER->uc['edit_showFieldHelp']) {
02790                         $hT = trim(t3lib_BEfunc::helpText($this->descrTable,'emconf_'.$key,$this->doc->backPath));
02791                         return '<td>'.($hT?$hT:t3lib_BEfunc::helpTextIcon($this->descrTable,'emconf_'.$key,$this->doc->backPath)).'</td>';
02792                 } else {
02793                         return '';
02794                 }
02795         }
02796 
02803         function labelInfo($str)        {
02804                 return ' title="'.htmlspecialchars($str).'" style="cursor:help;"';
02805         }
02806 
02815         function extensionTitleIconHeader($extKey,$extInfo,$align='top')        {
02816                 $imgInfo = @getImageSize($this->getExtPath($extKey,$extInfo['type']).'/ext_icon.gif');
02817                 $out = '';
02818                 if (is_array($imgInfo)) {
02819                         $out.= '<img src="'.$GLOBALS['BACK_PATH'].$this->typeRelPaths[$extInfo['type']].$extKey.'/ext_icon.gif" '.$imgInfo[3].' align="'.$align.'" alt="" />';
02820                 }
02821                 $out.= $extInfo['EM_CONF']['title'] ? htmlspecialchars(t3lib_div::fixed_lgd($extInfo['EM_CONF']['title'],40)) : '<em>'.$extKey.'</em>';
02822                 return $out;
02823         }
02824 
02830         function removeButton() {
02831                 return '<img src="uninstall.gif" width="16" height="16" title="Remove extension" align="top" alt="" />';
02832         }
02833 
02839         function installButton()        {
02840                 return '<img src="install.gif" width="16" height="16" title="Install extension..." align="top" alt="" />';
02841         }
02842 
02848         function noImportMsg()  {
02849                 return '<img src="'.$this->doc->backPath.'gfx/icon_warning2.gif" width="18" height="16" align="top" alt="" /><strong>Import to both local and global path is disabled in TYPO3_CONF_VARS!</strong>';
02850         }
02851 
02861         function depToString($dep,$type='depends') {
02862                 if(is_array($dep)) {
02863                         unset($dep[$type]['php']);
02864                         unset($dep[$type]['typo3']);
02865                         $s = (count($dep[$type])) ? implode(',', array_keys($dep[$type])) : '';
02866                         return $s;
02867                 }
02868                 return '';
02869         }
02870 
02880         function stringToDep($dep) {
02881                 $constraint = array();
02882                 if(is_string($dep) && strlen($dep)) {
02883                         $dep = explode(',',$dep);
02884                         foreach($dep as $v) {
02885                                 $constraint[$v] = '';
02886                         }
02887                 }
02888                 return $constraint;
02889         }
02890 
02891 
02892 
02893 
02894 
02895 
02896 
02897 
02898         /********************************
02899         *
02900         * Read information about all available extensions
02901         *
02902         *******************************/
02903 
02910         function getInstalledExtensions()       {
02911                 $list = array();
02912                 $cat = $this->defaultCategories;
02913 
02914                 $path = PATH_site.TYPO3_mainDir.'sysext/';
02915                 $this->getInstExtList($path,$list,$cat,'S');
02916 
02917                 $path = PATH_site.TYPO3_mainDir.'ext/';
02918                 $this->getInstExtList($path,$list,$cat,'G');
02919 
02920                 $path = PATH_site.'typo3conf/ext/';
02921                 $this->getInstExtList($path,$list,$cat,'L');
02922 
02923                 return array($list,$cat);
02924         }
02925 
02937         function getInstExtList($path,&$list,&$cat,$type)       {
02938 
02939                 if (@is_dir($path))     {
02940                         $extList = t3lib_div::get_dirs($path);
02941                         if (is_array($extList)) {
02942                                 foreach($extList as $extKey)    {
02943                                         if (@is_file($path.$extKey.'/ext_emconf.php'))  {
02944                                                 $emConf = $this->includeEMCONF($path.$extKey.'/ext_emconf.php', $extKey);
02945                                                 if (is_array($emConf))  {
02946                                                         if (is_array($list[$extKey]))   {
02947                                                                 $list[$extKey]=array('doubleInstall'=>$list[$extKey]['doubleInstall']);
02948                                                         }
02949                                                         $list[$extKey]['doubleInstall'].= $type;
02950                                                         $list[$extKey]['type'] = $type;
02951                                                         $list[$extKey]['EM_CONF'] = $emConf;
02952                                                         $list[$extKey]['files'] = t3lib_div::getFilesInDir($path.$extKey);
02953 
02954                                                         $this->setCat($cat,$list[$extKey], $extKey);
02955                                                 }
02956                                         }
02957                                 }
02958                         }
02959                 }
02960         }
02961 
02968         function fixEMCONF($emConf) {
02969                 if(!isset($emConf['constraints']) || !isset($emConf['constraints']['depends']) || !isset($emConf['constraints']['conflicts']) || !isset($emConf['constraints']['suggests'])) {
02970                         if(!isset($emConf['constraints']) || !isset($emConf['constraints']['depends'])) {
02971                                 $emConf['constraints']['depends'] = $this->stringToDep($emConf['dependencies']);
02972                                 if(strlen($emConf['PHP_version'])) {
02973                                         $versionRange = $this->splitVersionRange($emConf['PHP_version']);
02974                                         if(version_compare($versionRange[0],'3.0.0','<')) $versionRange[0] = '3.0.0';
02975                                         if(version_compare($versionRange[1],'3.0.0','<')) $versionRange[1] = '';
02976                                         $emConf['constraints']['depends']['php'] = implode('-',$versionRange);
02977                                 }
02978                                 if(strlen($emConf['TYPO3_version'])) {
02979                                         $versionRange = $this->splitVersionRange($emConf['TYPO3_version']);
02980                                         if(version_compare($versionRange[0],'3.5.0','<')) $versionRange[0] = '3.5.0';
02981                                         if(version_compare($versionRange[1],'3.5.0','<')) $versionRange[1] = '';
02982                                         $emConf['constraints']['depends']['typo3'] = implode('-',$versionRange);
02983                                 }
02984                         }
02985                         if(!isset($emConf['constraints']) || !isset($emConf['constraints']['conflicts'])) {
02986                                 $emConf['constraints']['conflicts'] = $this->stringToDep($emConf['conflicts']);
02987                         }
02988                         if(!isset($emConf['constraints']) || !isset($emConf['constraints']['suggests'])) {
02989                                 $emConf['constraints']['suggests'] = array();
02990                         }
02991                 } elseif (isset($emConf['constraints']) && isset($emConf['dependencies'])) {
02992                         $emConf['suggests'] = isset($emConf['suggests']) ? $emConf['suggests'] : array();
02993                         $emConf['dependencies'] = $this->depToString($emConf['constraints']);
02994                         $emConf['conflicts'] = $this->depToString($emConf['constraints'], 'conflicts');
02995                 }
02996                 unset($emConf['private']);
02997                 unset($emConf['download_password']);
02998                 unset($emConf['TYPO3_version']);
02999                 unset($emConf['PHP_version']);
03000 
03001                 return $emConf;
03002         }
03003 
03013         function splitVersionRange($ver) {
03014                 $versionRange = array();
03015                 if(strstr($ver, '-')) $versionRange = explode('-', $ver, 2);
03016                 else {
03017                         $versionRange[0] = $ver;
03018                         $versionRange[1] = '';
03019                 }
03020 
03021                 return $versionRange;
03022         }
03023 
03029         function prepareImportExtList() {
03030                 $list = array();
03031                 $cat = $this->defaultCategories;
03032                 $filepath = $this->getMirrorURL();
03033 
03034                 reset($this->xmlhandler->extensionsXML);
03035                 while (list($extKey, $data) = each($this->xmlhandler->extensionsXML)) {
03036                         $GLOBALS['LANG']->csConvObj->convArray($data,'utf-8',$GLOBALS['LANG']->charSet); // is there a better place for conversion?
03037                         $list[$extKey]['type'] = '_';
03038                         $version = array_keys($data['versions']);
03039                         $list[$extKey]['_ICON'] = '<img alt="" src="'.$filepath.$extKey{0}.'/'.$extKey{1}.'/'.$extKey.'_'.end($version).'.gif" />';
03040                         $list[$extKey]['downloadcounter'] = $data['downloadcounter'];
03041 
03042                         foreach(array_keys($data['versions']) as $version) {
03043                                 $list[$extKey]['versions'][$version]['downloadcounter'] = $data['versions'][$version]['downloadcounter'];
03044 
03045                                 $list[$extKey]['versions'][$version]['EM_CONF'] = array(
03046                                 'version' => $version,
03047                                 'title' => $data['versions'][$version]['title'],
03048                                 'description' => $data['versions'][$version]['description'],
03049                                 'category' => $data['versions'][$version]['category'],
03050                                 'constraints' => $data['versions'][$version]['dependencies'],
03051                                 'state' => $data['versions'][$version]['state'],
03052                                 'reviewstate' => $data['versions'][$version]['reviewstate'],
03053                                 'lastuploaddate' => $data['versions'][$version]['lastuploaddate'],
03054                                 'author' => $data['versions'][$version]['authorname'],
03055                                 'author_email' => $data['versions'][$version]['authoremail'],
03056                                 'author_company' => $data['versions'][$version]['authorcompany'],
03057                                 );
03058                         }
03059                         $this->setCat($cat, $list[$extKey]['versions'][$version], $extKey);
03060                 }
03061 
03062                 return array($list,$cat);
03063         }
03064 
03073         function setCat(&$cat,$listArrayPart,$extKey)   {
03074 
03075                 // Getting extension title:
03076                 $extTitle = $listArrayPart['EM_CONF']['title'];
03077 
03078                 // Category index:
03079                 $index = $listArrayPart['EM_CONF']['category'];
03080                 $cat['cat'][$index][$extKey] = $extTitle;
03081 
03082                 // Author index:
03083                 $index = $listArrayPart['EM_CONF']['author'].($listArrayPart['EM_CONF']['author_company']?', '.$listArrayPart['EM_CONF']['author_company']:'');
03084                 $cat['author_company'][$index][$extKey] = $extTitle;
03085 
03086                 // State index:
03087                 $index = $listArrayPart['EM_CONF']['state'];
03088                 $cat['state'][$index][$extKey] = $extTitle;
03089 
03090                 // Type index:
03091                 $index = $listArrayPart['type'];
03092                 $cat['type'][$index][$extKey] = $extTitle;
03093 
03094                 // Return categories:
03095                 return $cat;
03096         }
03097 
03098 
03099 
03100 
03101 
03102 
03103 
03104 
03105 
03106 
03107         /*******************************
03108         *
03109         * Extension analyzing (detailed information)
03110         *
03111         ******************************/
03112 
03123         function makeDetailedExtensionAnalysis($extKey,$extInfo,$validity=0)    {
03124 
03125                 // Get absolute path of the extension
03126                 $absPath = $this->getExtPath($extKey,$extInfo['type']);
03127 
03128                 $infoArray = array();
03129 
03130                 $table_class_prefix = substr($extKey,0,5)=='user_' ? 'user_' : 'tx_'.str_replace('_','',$extKey).'_';
03131                 $module_prefix = substr($extKey,0,5)=='user_' ? 'u' : 'tx'.str_replace('_','',$extKey);
03132 
03133                 // Database status:
03134                 $dbInfo = $this->checkDBupdates($extKey,$extInfo,1);
03135 
03136                 // Database structure required:
03137                 if (is_array($dbInfo['structure']['tables_fields']))    {
03138                         $modify_tables = t3lib_div::trimExplode(',',$extInfo['EM_CONF']['modify_tables'],1);
03139                         $infoArray['dump_tf'] = array();
03140 
03141                         foreach($dbInfo['structure']['tables_fields'] as $tN => $d)     {
03142                                 if (in_array($tN,$modify_tables))       {
03143                                         $infoArray['fields'][] = $tN.': <i>'.
03144                                         (is_array($d['fields']) ? implode(', ',array_keys($d['fields'])) : '').
03145                                         (is_array($d['keys']) ? ' + '.count($d['keys']).' keys' : '').
03146                                         '</i>';
03147                                         if (is_array($d['fields']))     {
03148                                                 reset($d['fields']);
03149                                                 while(list($fN) = each($d['fields']))   {
03150                                                         $infoArray['dump_tf'][] = $tN.'.'.$fN;
03151                                                         if (!t3lib_div::isFirstPartOfStr($fN,$table_class_prefix))      {
03152                                                                 $infoArray['NSerrors']['fields'][$fN] = $fN;
03153                                                         } else {
03154                                                                 $infoArray['NSok']['fields'][$fN] = $fN;
03155                                                         }
03156                                                 }
03157                                         }
03158                                         if (is_array($d['keys']))       {
03159                                                 reset($d['keys']);
03160                                                 while(list($fN)=each($d['keys']))       {
03161                                                         $infoArray['dump_tf'][] = $tN.'.KEY:'.$fN;
03162                                                 }
03163                                         }
03164                                 } else {
03165                                         $infoArray['dump_tf'][] = $tN;
03166                                         $infoArray['tables'][] = $tN;
03167                                         if (!t3lib_div::isFirstPartOfStr($tN,$table_class_prefix))      {
03168                                                 $infoArray['NSerrors']['tables'][$tN] = $tN;
03169                                         } else $infoArray['NSok']['tables'][$tN] = $tN;
03170                                 }
03171                         }
03172                         if (count($dbInfo['structure']['diff']['diff']) || count($dbInfo['structure']['diff']['extra']))        {
03173                                 $msg = array();
03174                                 if (count($dbInfo['structure']['diff']['diff']))        $msg[] = 'missing';
03175                                 if (count($dbInfo['structure']['diff']['extra']))       $msg[] = 'of wrong type';
03176                                 $infoArray['tables_error'] = 1;
03177                                 if (t3lib_extMgm::isLoaded($extKey))    $infoArray['errors'][] = 'Some tables or fields are '.implode(' and ',$msg).'!';
03178                         }
03179                 }
03180 
03181                 // Static tables?
03182                 if (is_array($dbInfo['static']))        {
03183                         $infoArray['static'] = array_keys($dbInfo['static']);
03184 
03185                         foreach($dbInfo['static'] as $tN => $d) {
03186                                 if (!$d['exists'])      {
03187                                         $infoArray['static_error'] = 1;
03188                                         if (t3lib_extMgm::isLoaded($extKey))    $infoArray['errors'][] = 'Static table(s) missing!';
03189                                         if (!t3lib_div::isFirstPartOfStr($tN,$table_class_prefix))      {
03190                                                 $infoArray['NSerrors']['tables'][$tN] = $tN;
03191                                         } else $infoArray['NSok']['tables'][$tN] = $tN;
03192                                 }
03193                         }
03194                 }
03195 
03196                 // Backend Module-check:
03197                 $knownModuleList = t3lib_div::trimExplode(',',$extInfo['EM_CONF']['module'],1);
03198                 foreach($knownModuleList as $mod)       {
03199                         if (@is_dir($absPath.$mod))     {
03200                                 if (@is_file($absPath.$mod.'/conf.php'))        {
03201                                         $confFileInfo = $this->modConfFileAnalysis($absPath.$mod.'/conf.php');
03202                                         if (is_array($confFileInfo['TYPO3_MOD_PATH']))  {
03203                                                 $shouldBePath = $this->typeRelPaths[$extInfo['type']].$extKey.'/'.$mod.'/';
03204                                                 if (strcmp($confFileInfo['TYPO3_MOD_PATH'][1][1],$shouldBePath))        {
03205                                                         $infoArray['errors'][] = 'Configured TYPO3_MOD_PATH "'.$confFileInfo['TYPO3_MOD_PATH'][1][1].'" different from "'.$shouldBePath.'"';
03206                                                 }
03207                                         } else $infoArray['errors'][] = 'No definition of TYPO3_MOD_PATH constant found inside!';
03208                                         if (is_array($confFileInfo['MCONF_name']))      {
03209                                                 $mName = $confFileInfo['MCONF_name'][1][1];
03210                                                 $mNameParts = explode('_',$mName);
03211                                                 $infoArray['moduleNames'][] = $mName;
03212                                                 if (!t3lib_div::isFirstPartOfStr($mNameParts[0],$module_prefix) &&
03213                                                 (!$mNameParts[1] || !t3lib_div::isFirstPartOfStr($mNameParts[1],$module_prefix)))       {
03214                                                         $infoArray['NSerrors']['modname'][] = $mName;
03215                                                 } else $infoArray['NSok']['modname'][] = $mName;
03216                                         } else $infoArray['errors'][] = 'No definition of MCONF[name] variable found inside!';
03217                                 } else  $infoArray['errors'][] = 'Backend module conf file "'.$mod.'/conf.php" should exist but does not!';
03218                         } else $infoArray['errors'][] = 'Backend module folder "'.$mod.'/" should exist but does not!';
03219                 }
03220                 $dirs = t3lib_div::get_dirs($absPath);
03221                 if (is_array($dirs))    {
03222                         reset($dirs);
03223                         while(list(,$mod) = each($dirs))        {
03224                                 if (!in_array($mod,$knownModuleList) && @is_file($absPath.$mod.'/conf.php'))    {
03225                                         $confFileInfo = $this->modConfFileAnalysis($absPath.$mod.'/conf.php');
03226                                         if (is_array($confFileInfo))    {
03227                                                 $infoArray['errors'][] = 'It seems like there is a backend module in "'.$mod.'/conf.php" which is not configured in ext_emconf.php';
03228                                         }
03229                                 }
03230                         }
03231                 }
03232 
03233                 // ext_tables.php:
03234                 if (@is_file($absPath.'ext_tables.php'))        {
03235                         $content = t3lib_div::getUrl($absPath.'ext_tables.php');
03236                         if (stristr($content,'t3lib_extMgm::addModule'))        $infoArray['flags'][] = 'Module';
03237                         if (stristr($content,'t3lib_extMgm::insertModuleFunction'))     $infoArray['flags'][] = 'Module+';
03238                         if (stristr($content,'t3lib_div::loadTCA'))     $infoArray['flags'][] = 'loadTCA';
03239                         if (stristr($content,'$TCA['))  $infoArray['flags'][] = 'TCA';
03240                         if (stristr($content,'t3lib_extMgm::addPlugin'))        $infoArray['flags'][] = 'Plugin';
03241                 }
03242 
03243                 // ext_localconf.php:
03244                 if (@is_file($absPath.'ext_localconf.php'))     {
03245                         $content = t3lib_div::getUrl($absPath.'ext_localconf.php');
03246                         if (stristr($content,'t3lib_extMgm::addPItoST43'))      $infoArray['flags'][]='Plugin/ST43';
03247                         if (stristr($content,'t3lib_extMgm::addPageTSConfig'))  $infoArray['flags'][]='Page-TSconfig';
03248                         if (stristr($content,'t3lib_extMgm::addUserTSConfig'))  $infoArray['flags'][]='User-TSconfig';
03249                         if (stristr($content,'t3lib_extMgm::addTypoScriptSetup'))       $infoArray['flags'][]='TS/Setup';
03250                         if (stristr($content,'t3lib_extMgm::addTypoScriptConstants'))   $infoArray['flags'][]='TS/Constants';
03251                 }
03252 
03253                 if (@is_file($absPath.'ext_typoscript_constants.txt'))  {
03254                         $infoArray['TSfiles'][] = 'Constants';
03255                 }
03256                 if (@is_file($absPath.'ext_typoscript_setup.txt'))      {
03257                         $infoArray['TSfiles'][] = 'Setup';
03258                 }
03259                 if (@is_file($absPath.'ext_conf_template.txt')) {
03260                         $infoArray['conf'] = 1;
03261                 }
03262 
03263                 // Classes:
03264                 if ($validity)  {
03265                         $filesInside = $this->getClassIndexLocallangFiles($absPath,$table_class_prefix,$extKey);
03266                         if (is_array($filesInside['errors']))   $infoArray['errors'] = array_merge((array)$infoArray['errors'],$filesInside['errors']);
03267                         if (is_array($filesInside['NSerrors'])) $infoArray['NSerrors'] = array_merge((array)$infoArray['NSerrors'],$filesInside['NSerrors']);
03268                         if (is_array($filesInside['NSok']))     $infoArray['NSok'] = array_merge((array)$infoArray['NSok'],$filesInside['NSok']);
03269                         $infoArray['locallang'] = $filesInside['locallang'];
03270                         $infoArray['classes'] = $filesInside['classes'];
03271                 }
03272 
03273                 // Upload folders
03274                 if ($extInfo['EM_CONF']['uploadfolder'])        {
03275                         $infoArray['uploadfolder'] = $this->ulFolder($extKey);
03276                         if (!@is_dir(PATH_site.$infoArray['uploadfolder']))     {
03277                                 $infoArray['errors'][] = 'Error: Upload folder "'.$infoArray['uploadfolder'].'" did not exist!';
03278                                 $infoArray['uploadfolder'] = '';
03279                         }
03280                 }
03281 
03282                 // Create directories:
03283                 if ($extInfo['EM_CONF']['createDirs'])  {
03284                         $infoArray['createDirs'] = array_unique(t3lib_div::trimExplode(',',$extInfo['EM_CONF']['createDirs'],1));
03285                         foreach($infoArray['createDirs'] as $crDir)     {
03286                                 if (!@is_dir(PATH_site.$crDir)) {
03287                                         $infoArray['errors'][]='Error: Upload folder "'.$crDir.'" did not exist!';
03288                                 }
03289                         }
03290                 }
03291 
03292                 // Return result array:
03293                 return $infoArray;
03294         }
03295 
03305         function getClassIndexLocallangFiles($absPath,$table_class_prefix,$extKey)      {
03306                 $filesInside = t3lib_div::removePrefixPathFromList(t3lib_div::getAllFilesAndFoldersInPath(array(),$absPath,'php,inc'),$absPath);
03307                 $out = array();
03308 
03309                 foreach($filesInside as $fileName)      {
03310                         if (substr($fileName,0,4)!='ext_' && substr($fileName,0,6)!='tests/')   {       // ignore supposed-to-be unit tests as well
03311                                 $baseName = basename($fileName);
03312                                 if (substr($baseName,0,9)=='locallang' && substr($baseName,-4)=='.php') {
03313                                         $out['locallang'][] = $fileName;
03314                                 } elseif ($baseName!='conf.php')        {
03315                                         if (filesize($absPath.$fileName)<500*1024)      {
03316                                                 $fContent = t3lib_div::getUrl($absPath.$fileName);
03317                                                 unset($reg);
03318                                                 if (preg_match('/\n[[:space:]]*class[[:space:]]*([[:alnum:]_]+)([[:alnum:][:space:]_]*)/',$fContent,$reg))      {
03319 
03320                                                         // Find classes:
03321                                                         $lines = explode(chr(10),$fContent);
03322                                                         foreach($lines as $l)   {
03323                                                                 $line = trim($l);
03324                                                                 unset($reg);
03325                                                                 if (preg_match('/^class[[:space:]]*([[:alnum:]_]+)([[:alnum:][:space:]_]*)/',$line,$reg))       {
03326                                                                         $out['classes'][] = $reg[1];
03327                                                                         $out['files'][$fileName]['classes'][] = $reg[1];
03328                                                                         if ($reg[1]!=='ext_update' && substr($reg[1],0,3)!='ux_' && !t3lib_div::isFirstPartOfStr($reg[1],$table_class_prefix) && strcmp(substr($table_class_prefix,0,-1),$reg[1]))      {
03329                                                                                 $out['NSerrors']['classname'][] = $reg[1];
03330                                                                         } else $out['NSok']['classname'][] = $reg[1];
03331                                                                 }
03332                                                         }
03333                                                         // If class file prefixed 'class.'....
03334                                                         if (substr($baseName,0,6)=='class.')    {
03335                                                                 $fI = pathinfo($baseName);
03336                                                                 $testName=substr($baseName,6,-(1+strlen($fI['extension'])));
03337                                                                 if ($testName!=='ext_update' && substr($testName,0,3)!='ux_' && !t3lib_div::isFirstPartOfStr($testName,$table_class_prefix) && strcmp(substr($table_class_prefix,0,-1),$testName))      {
03338                                                                         $out['NSerrors']['classfilename'][] = $baseName;
03339                                                                 } else {
03340                                                                         $out['NSok']['classfilename'][] = $baseName;
03341                                                                         if (is_array($out['files'][$fileName]['classes']) && $this->first_in_array($testName,$out['files'][$fileName]['classes'],1))    {
03342                                                                                 $out['msg'][] = 'Class filename "'.$fileName.'" did contain the class "'.$testName.'" just as it should.';
03343                                                                         } else $out['errors'][] = 'Class filename "'.$fileName.'" did NOT contain the class "'.$testName.'"!';
03344                                                                 }
03345                                                         }
03346                                                         //
03347                                                         $XclassParts = split('if \(defined\([\'"]TYPO3_MODE[\'"]\) && \$TYPO3_CONF_VARS\[TYPO3_MODE\]\[[\'"]XCLASS[\'"]\]',$fContent,2);
03348                                                         if (count($XclassParts)==2)     {
03349                                                                 unset($reg);
03350                                                                 preg_match('/^\[[\'"]([[:alnum:]_\/\.]*)[\'"]\]/',$XclassParts[1],$reg);
03351                                                                 if ($reg[1]) {
03352                                                                         $cmpF = 'ext/'.$extKey.'/'.$fileName;
03353                                                                         if (!strcmp($reg[1],$cmpF))     {
03354                                                                                 if (preg_match('/_once[[:space:]]*\(\$TYPO3_.ONF_VARS\[TYPO3_MODE\]\[[\'"]XCLASS[\'"]\]\[[\'"]'.preg_quote($cmpF,'/').'[\'"]\]\);/', $XclassParts[1]))  {
03355                                                                                         $out['msg'][] = 'XCLASS OK in '.$fileName;
03356                                                                                 } else $out['errors'][] = 'Couldn\'t find the include_once statement for XCLASS!';
03357                                                                         } else $out['errors'][] = 'The XCLASS filename-key "'.$reg[1].'" was different from "'.$cmpF.'" which it should have been!';
03358                                                                 } else $out['errors'][] = 'No XCLASS filename-key found in file "'.$fileName.'". Maybe a regex coding error here...';
03359                                                         } elseif (!$this->first_in_array('ux_',$out['files'][$fileName]['classes'])) $out['errors'][] = 'No XCLASS inclusion code found in file "'.$fileName.'"';
03360                                                 }
03361                                         }
03362                                 }
03363                         }
03364                 }
03365                 return $out;
03366         }
03367 
03375         function modConfFileAnalysis($confFilePath)     {
03376                 $lines = explode(chr(10),t3lib_div::getUrl($confFilePath));
03377                 $confFileInfo = array();
03378                 $confFileInfo['lines'] = $lines;
03379 
03380                 foreach($lines as $k => $l)     {
03381                         $line = trim($l);
03382 
03383                         unset($reg);
03384                         if (preg_match('/^define[[:space:]]*\([[:space:]]*["\']TYPO3_MOD_PATH["\'][[:space:]]*,[[:space:]]*["\']([[:alnum:]_\/\.]+)["\'][[:space:]]*\)[[:space:]]*;/',$line,$reg))      {
03385                                 $confFileInfo['TYPO3_MOD_PATH'] = array($k,$reg);
03386                         }
03387 
03388                         unset($reg);
03389                         if (preg_match('/^\$MCONF\[["\']?name["\']?\][[:space:]]*=[[:space:]]*["\']([[:alnum:]_]+)["\'];/',$line,$reg)) {
03390                                 $confFileInfo['MCONF_name'] = array($k,$reg);
03391                         }
03392                 }
03393                 return $confFileInfo;
03394         }
03395 
03403         function serverExtensionMD5Array($extKey,$conf) {
03404 
03405                 // Creates upload-array - including filelist.
03406                 $mUA = $this->makeUploadArray($extKey,$conf);
03407 
03408                 $md5Array = array();
03409                 if (is_array($mUA['FILES']))    {
03410 
03411                         // Traverse files.
03412                         foreach($mUA['FILES'] as $fN => $d)     {
03413                                 if ($fN!='ext_emconf.php')      {
03414                                         $md5Array[$fN] = substr($d['content_md5'],0,4);
03415                                 }
03416                         }
03417                 } else debug($mUA);
03418                 return $md5Array;
03419         }
03420 
03428         function findMD5ArrayDiff($current,$past)       {
03429                 if (!is_array($current))        $current = array();
03430                 if (!is_array($past))           $past = array();
03431                 $filesInCommon = array_intersect($current,$past);
03432                 $diff1 =  array_keys(array_diff($past,$filesInCommon));
03433                 $diff2 =  array_keys(array_diff($current,$filesInCommon));
03434                 $affectedFiles = array_unique(array_merge($diff1,$diff2));
03435                 return $affectedFiles;
03436         }
03437 
03438 
03439 
03440 
03441 
03442 
03443 
03444 
03445 
03446 
03447         /***********************************
03448         *
03449         * File system operations
03450         *
03451         **********************************/
03452 
03460         function createDirsInPath($dirs,$extDirPath)    {
03461                 if (is_array($dirs))    {
03462                         foreach($dirs as $dir)  {
03463                                 $error = t3lib_div::mkdir_deep($extDirPath,$dir);
03464                                 if ($error)     return $error;
03465                         }
03466                 }
03467 
03468                 return false;
03469         }
03470 
03478         function removeExtDirectory($removePath,$removeContentOnly=0)   {
03479                 $errors = array();
03480                 if (@is_dir($removePath) && substr($removePath,-1)=='/' && (
03481                 t3lib_div::isFirstPartOfStr($removePath,PATH_site.$this->typePaths['G']) ||
03482                 t3lib_div::isFirstPartOfStr($removePath,PATH_site.$this->typePaths['L']) ||
03483                 (t3lib_div::isFirstPartOfStr($removePath,PATH_site.$this->typePaths['S']) && $this->systemInstall) ||
03484                 t3lib_div::isFirstPartOfStr($removePath,PATH_site.'fileadmin/_temp_/'))         // Playing-around directory...
03485                 ) {
03486 
03487                         // All files in extension directory:
03488                         $fileArr = t3lib_div::getAllFilesAndFoldersInPath(array(),$removePath,'',1);
03489                         if (is_array($fileArr)) {
03490 
03491                                 // Remove files in dirs:
03492                                 foreach($fileArr as $removeFile)        {
03493                                         if (!@is_dir($removeFile))      {
03494                                                 if (@is_file($removeFile) && t3lib_div::isFirstPartOfStr($removeFile,$removePath) && strcmp($removeFile,$removePath))   {       // ... we are very paranoid, so we check what cannot go wrong: that the file is in fact within the prefix path!
03495                                                         @unlink($removeFile);
03496                                                         clearstatcache();
03497                                                         if (@is_file($removeFile))      {
03498                                                                 $errors[] = 'Error: "'.$removeFile.'" could not be deleted!';
03499                                                         }
03500                                                 } else $errors[] = 'Error: "'.$removeFile.'" was either not a file, or it was equal to the removed directory or simply outside the removed directory "'.$removePath.'"!';
03501                                         }
03502                                 }
03503 
03504                                 // Remove directories:
03505                                 $remDirs = $this->extractDirsFromFileList(t3lib_div::removePrefixPathFromList($fileArr,$removePath));
03506                                 $remDirs = array_reverse($remDirs);     // Must delete outer directories first...
03507                                 foreach($remDirs as $removeRelDir)      {
03508                                         $removeDir = $removePath.$removeRelDir;
03509                                         if (@is_dir($removeDir))        {
03510                                                 rmdir($removeDir);
03511                                                 clearstatcache();
03512                                                 if (@is_dir($removeDir))        {
03513                                                         $errors[] = 'Error: "'.$removeDir.'" could not be removed (are there files left?)';
03514                                                 }
03515                                         } else $errors[] = 'Error: "'.$removeDir.'" was not a directory!';
03516                                 }
03517 
03518                                 // If extension dir should also be removed:
03519                                 if (!$removeContentOnly)        {
03520                                         rmdir($removePath);
03521                                         clearstatcache();
03522                                         if (@is_dir($removePath))       {
03523                                                 $errors[] = 'Error: Extension directory "'.$removePath.'" could not be removed (are there files or folders left?)';
03524                                         }
03525                                 }
03526                         } else $errors[] = 'Error: '.$fileArr;
03527                 } else $errors[] = 'Error: Unallowed path to remove: '.$removePath;
03528 
03529                 // Return errors if any:
03530                 return implode(chr(10),$errors);
03531         }
03532 
03541         function clearAndMakeExtensionDir($importedData,$type,$dontDelete=0)    {
03542                 if (!$importedData['extKey'])   return 'FATAL ERROR: Extension key was not set for some VERY strange reason. Nothing done...';
03543 
03544                 // Setting install path (L, G, S or fileadmin/_temp_/)
03545                 $path = '';
03546                 switch((string)$type)   {
03547                         case 'G':
03548                         case 'L':
03549                                 $path = PATH_site.$this->typePaths[$type];
03550                                 $suffix = '';
03551 
03552                                 // Creates the typo3conf/ext/ directory if it does NOT already exist:
03553                                 if ((string)$type=='L' && !@is_dir($path))      {
03554                                         t3lib_div::mkdir($path);
03555                                 }
03556                                 break;
03557                         default:
03558                                 if ($this->systemInstall && (string)$type=='S') {
03559                                         $path = PATH_site.$this->typePaths[$type];
03560                                         $suffix = '';
03561                                 } else {
03562                                         $path = PATH_site.'fileadmin/_temp_/';
03563                                         $suffix = '_'.date('dmy-His');
03564                                 }
03565                                 break;
03566                 }
03567 
03568                 // If the install path is OK...
03569                 if ($path && @is_dir($path))    {
03570 
03571                         // Set extension directory:
03572                         $extDirPath = $path.$importedData['extKey'].$suffix.'/';
03573 
03574                         // Install dir was found, remove it then:
03575                         if (@is_dir($extDirPath))       {
03576                                 if($dontDelete) return array($extDirPath);
03577                                 $res = $this->removeExtDirectory($extDirPath);
03578                                 if ($res) {
03579                                         return 'ERROR: Could not remove extension directory "'.$extDirPath.'". Reasons:<br /><br />'.nl2br($res);
03580                                 }
03581                         }
03582 
03583                         // We go create...
03584                         t3lib_div::mkdir($extDirPath);
03585                         if (!is_dir($extDirPath))       return 'ERROR: Could not create extension directory "'.$extDirPath.'"';
03586                         return array($extDirPath);
03587                 } else return 'ERROR: The extension install path "'.$path.'" was not a directory.';
03588         }
03589 
03595         function removeCacheFiles()     {
03596                 return t3lib_extMgm::removeCacheFiles();
03597         }
03598 
03605         function extractDirsFromFileList($files)        {
03606                 $dirs = array();
03607 
03608                 if (is_array($files))   {
03609                         // Traverse files / directories array:
03610                         foreach($files as $file)        {
03611                                 if (substr($file,-1)=='/')      {
03612                                         $dirs[$file] = $file;
03613                                 } else {
03614                                         $pI = pathinfo($file);
03615                                         if (strcmp($pI['dirname'],'') && strcmp($pI['dirname'],'.'))    {
03616                                                 $dirs[$pI['dirname'].'/'] = $pI['dirname'].'/';
03617                                         }
03618                                 }
03619                         }
03620                 }
03621                 return $dirs;
03622         }
03623 
03631         function getExtPath($extKey,$type)      {
03632                 $typeP = $this->typePaths[$type];
03633                 if ($typeP)     {
03634                         $path = PATH_site.$typeP.$extKey.'/';
03635                         return @is_dir($path) ? $path : '';
03636                 } else {
03637                         return '';
03638                 }
03639         }
03640 
03641 
03642 
03643 
03644 
03645 
03646 
03647 
03648 
03649 
03650         /*******************************
03651         *
03652         * Writing to "conf.php" and "localconf.php" files
03653         *
03654         ******************************/
03655 
03665         function writeTYPO3_MOD_PATH($confFilePath,$type,$mP)   {
03666                 $lines = explode(chr(10),t3lib_div::getUrl($confFilePath));
03667                 $confFileInfo = array();
03668                 $confFileInfo['lines'] = $lines;
03669 
03670                 $flag_M = 0;
03671                 $flag_B = 0;
03672 
03673                 foreach($lines as $k => $l)     {
03674                         $line = trim($l);
03675 
03676                         unset($reg);
03677                         if (preg_match('/^define[[:space:]]*\([[:space:]]*["\']TYPO3_MOD_PATH["\'][[:space:]]*,[[:space:]]*["\']([[:alnum:]_\/\.]+)["\'][[:space:]]*\)[[:space:]]*;/',$line,$reg))      {
03678                                 $lines[$k] = str_replace($reg[0], 'define(\'TYPO3_MOD_PATH\', \''.$this->typeRelPaths[$type].$mP.'\');', $lines[$k]);
03679                                 $flag_M = $k+1;
03680                         }
03681 
03682                         unset($reg);
03683                         if (preg_match('/^\$BACK_PATH[[:space:]]*=[[:space:]]*["\']([[:alnum:]_\/\.]+)["\'][[:space:]]*;/',$line,$reg)) {
03684                                 $lines[$k] = str_replace($reg[0], '$BACK_PATH=\''.$this->typeBackPaths[$type].'\';', $lines[$k]);
03685                                 $flag_B = $k+1;
03686                         }
03687                 }
03688 
03689                 if ($flag_B && $flag_M) {
03690                         t3lib_div::writeFile($confFilePath,implode(chr(10),$lines));
03691                         return 'TYPO3_MOD_PATH and $BACK_PATH was updated in "'.substr($confFilePath,strlen(PATH_site)).'"';
03692                 } else return 'Error: Either TYPO3_MOD_PATH or $BACK_PATH was not found in the "'.$confFilePath.'" file. You must manually configure that!';
03693         }
03694 
03702         function writeNewExtensionList($newExtList)     {
03703                 global $TYPO3_CONF_VARS;
03704 
03705                 // Instance of install tool
03706                 $instObj = new t3lib_install;
03707                 $instObj->allowUpdateLocalConf =1;
03708                 $instObj->updateIdentity = 'TYPO3 Extension Manager';
03709 
03710                 // Get lines from localconf file
03711                 $lines = $instObj->writeToLocalconf_control();
03712                 $instObj->setValueInLocalconfFile($lines, '$TYPO3_CONF_VARS[\'EXT\'][\'extList\']', $newExtList);
03713                 $instObj->writeToLocalconf_control($lines);
03714 
03715                 $TYPO3_CONF_VARS['EXT']['extList'] = $newExtList;
03716                 $this->removeCacheFiles();
03717         }
03718 
03727         function writeTsStyleConfig($extKey,$arr)       {
03728 
03729                 // Instance of install tool
03730                 $instObj = new t3lib_install;
03731                 $instObj->allowUpdateLocalConf =1;
03732                 $instObj->updateIdentity = 'TYPO3 Extension Manager';
03733 
03734                 // Get lines from localconf file
03735                 $lines = $instObj->writeToLocalconf_control();
03736                 $instObj->setValueInLocalconfFile($lines, '$TYPO3_CONF_VARS[\'EXT\'][\'extConf\'][\''.$extKey.'\']', serialize($arr));  // This will be saved only if there are no linebreaks in it !
03737                 $instObj->writeToLocalconf_control($lines);
03738 
03739                 $this->removeCacheFiles();
03740         }
03741 
03749         function updateLocalEM_CONF($extKey,$extInfo)   {
03750                 $extInfo['EM_CONF']['_md5_values_when_last_written'] = serialize($this->serverExtensionMD5Array($extKey,$extInfo));
03751                 $emConfFileContent = $this->construct_ext_emconf_file($extKey,$extInfo['EM_CONF']);
03752 
03753                 if($emConfFileContent)  {
03754                         $absPath = $this->getExtPath($extKey,$extInfo['type']);
03755                         $emConfFileName = $absPath.'ext_emconf.php';
03756 
03757                         if(@is_file($emConfFileName))   {
03758                                 if(t3lib_div::writeFile($emConfFileName,$emConfFileContent) === true) {
03759                                         return '"'.substr($emConfFileName,strlen($absPath)).'" was updated with a cleaned up EM_CONF array.';
03760                                 } else {
03761                                         return '<strong>Error: "'.$emConfFileName.'" was not writable!</strong>';
03762                                 }
03763                         } else return('<strong>Error: No file "'.$emConfFileName.'" found. DON\'T PANIC!</strong>');
03764                 } else {
03765                         return 'No content to write to "'.substr($emConfFileName,strlen($absPath)).'"!';
03766                 }
03767         }
03768 
03769 
03770 
03771 
03772 
03773 
03774 
03775 
03776 
03777 
03778         /*******************************************
03779         *
03780         * Compiling upload information, emconf-file etc.
03781         *
03782         *******************************************/
03783 
03791         function construct_ext_emconf_file($extKey,$EM_CONF)    {
03792 
03793                         // clean version number:
03794                 $vDat = $this->renderVersion($EM_CONF['version']);
03795                 $EM_CONF['version']=$vDat['version'];
03796 
03797                 return '<?php
03798 
03799 ########################################################################
03800 # Extension Manager/Repository config file for ext: "'.$extKey.'"
03801 #
03802 # Auto generated '.date('d-m-Y H:i').'
03803 #
03804 # Manual updates:
03805 # Only the data in the array - anything else is removed by next write.
03806 # "version" and "dependencies" must not be touched!
03807 ########################################################################
03808 
03809 $EM_CONF[$_EXTKEY] = '.$this->arrayToCode($EM_CONF, 0).';
03810 
03811 ?>';
03812         }
03813 
03822         function arrayToCode($array, $level=0) {
03823                 $lines = 'array('.chr(10);
03824                 $level++;
03825                 foreach($array as $k => $v)     {
03826                         if(strlen($k) && is_array($v)) {
03827                                 $lines .= str_repeat(chr(9),$level)."'".$k."' => ".$this->arrayToCode($v, $level);
03828                         } elseif(strlen($k)) {
03829                                 $lines .= str_repeat(chr(9),$level)."'".$k."' => ".(t3lib_div::testInt($v) ? intval($v) : "'".t3lib_div::slashJS(trim($v),1)."'").','.chr(10);
03830                         }
03831                 }
03832 
03833                 $lines .= str_repeat(chr(9),$level-1).')'.($level-1==0 ? '':','.chr(10));
03834                 return $lines;
03835         }
03836 
03844         function makeUploadArray($extKey,$conf) {
03845                 $extPath = $this->getExtPath($extKey,$conf['type']);
03846 
03847                 if ($extPath)   {
03848 
03849                         // Get files for extension:
03850                         $fileArr = array();
03851                         $fileArr = t3lib_div::getAllFilesAndFoldersInPath($fileArr,$extPath);
03852 
03853                         // Calculate the total size of those files:
03854                         $totalSize = 0;
03855                         foreach($fileArr as $file)      {
03856                                 $totalSize+=filesize($file);
03857                         }
03858 
03859                         // If the total size is less than the upper limit, proceed:
03860                         if ($totalSize < $this->maxUploadSize)  {
03861 
03862                                 // Initialize output array:
03863                                 $uploadArray = array();
03864                                 $uploadArray['extKey'] = $extKey;
03865                                 $uploadArray['EM_CONF'] = $conf['EM_CONF'];
03866                                 $uploadArray['misc']['codelines'] = 0;
03867                                 $uploadArray['misc']['codebytes'] = 0;
03868 
03869                                 $uploadArray['techInfo'] = $this->makeDetailedExtensionAnalysis($extKey,$conf,1);
03870 
03871                                 // Read all files:
03872                                 foreach($fileArr as $file)      {
03873                                         $relFileName = substr($file,strlen($extPath));
03874                                         $fI = pathinfo($relFileName);
03875                                         if ($relFileName!='ext_emconf.php')     {               // This file should be dynamically written...
03876                                                 $uploadArray['FILES'][$relFileName] = array(
03877                                                 'name' => $relFileName,
03878                                                 'size' => filesize($file),
03879                                                 'mtime' => filemtime($file),
03880                                                 'is_executable' => (TYPO3_OS=='WIN' ? 0 : is_executable($file)),
03881                                                 'content' => t3lib_div::getUrl($file)
03882                                                 );
03883                                                 if (t3lib_div::inList('php,inc',strtolower($fI['extension'])))  {
03884                                                         $uploadArray['FILES'][$relFileName]['codelines']=count(explode(chr(10),$uploadArray['FILES'][$relFileName]['content']));
03885                                                         $uploadArray['misc']['codelines']+=$uploadArray['FILES'][$relFileName]['codelines'];
03886                                                         $uploadArray['misc']['codebytes']+=$uploadArray['FILES'][$relFileName]['size'];
03887 
03888                                                         // locallang*.php files:
03889                                                         if (substr($fI['basename'],0,9)=='locallang' && strstr($uploadArray['FILES'][$relFileName]['content'],'$LOCAL_LANG'))   {
03890                                                                 $uploadArray['FILES'][$relFileName]['LOCAL_LANG']=$this->getSerializedLocalLang($file,$uploadArray['FILES'][$relFileName]['content']);
03891                                                         }
03892                                                 }
03893                                                 $uploadArray['FILES'][$relFileName]['content_md5'] = md5($uploadArray['FILES'][$relFileName]['content']);
03894                                         }
03895                                 }
03896 
03897                                 // Return upload-array:
03898                                 return $uploadArray;
03899                         } else return 'Error: Total size of uncompressed upload ('.$totalSize.') exceeds '.t3lib_div::formatSize($this->maxUploadSize);
03900                 } else {
03901                         return 'Error: Extension path for extension "'.$extKey.'" not found';
03902                 }
03903         }
03904 
03913         function getSerializedLocalLang($file,$content) {
03914                 $returnParts = explode('$LOCAL_LANG',$content,2);
03915 
03916                 include($file);
03917                 if (is_array($LOCAL_LANG))      {
03918                         $returnParts[1] = serialize($LOCAL_LANG);
03919                         return $returnParts;
03920                 } else {
03921                         return array();
03922                 }
03923         }
03924 
03925 
03926 
03927 
03928 
03929 
03930 
03931 
03932 
03933 
03934         /********************************
03935         *
03936         * Managing dependencies, conflicts, priorities, load order of extension keys
03937         *
03938         *******************************/
03939 
03949         function addExtToList($extKey,$instExtInfo)     {
03950                 global $TYPO3_LOADED_EXT;
03951 
03952                         // ext_emconf.php information:
03953                 $conf = $instExtInfo[$extKey]['EM_CONF'];
03954 
03955                         // Get list of installed extensions and add this one.
03956                 $listArr = array_keys($TYPO3_LOADED_EXT);
03957                 if ($conf['priority']=='top')   {
03958                         array_unshift($listArr,$extKey);
03959                 } else {
03960                         $listArr[]=$extKey;
03961                 }
03962 
03963                         // Manage other circumstances:
03964                 $listArr = $this->managesPriorities($listArr,$instExtInfo);
03965                 $listArr = $this->removeRequiredExtFromListArr($listArr);
03966 
03967                         // Implode unique list of extensions to load and return:
03968                 $list = implode(',',array_unique($listArr));
03969                 return $list;
03970         }
03971 
03980         function checkDependencies($extKey, $conf, $instExtInfo) {
03981                 $content = '';
03982                 $depError = false;
03983                 $msg = array();
03984                 $depsolver = t3lib_div::_POST('depsolver');
03985 
03986                 foreach($conf['constraints']['depends'] as $depK => $depV)      {
03987                         if($depsolver['ignore'][$depK]) {
03988                                 $msg[] = '<br />Dependency on '.$depK.' ignored as requested.
03989                                 <input type="hidden" value="1" name="depsolver[ignore]['.$depK.']" />';
03990                                 continue;
03991                         }
03992                         if($depK == 'php') {
03993                                 if(!$depV) continue;
03994                                 $versionRange = $this->splitVersionRange($depV);
03995                                 $phpv = strstr(PHP_VERSION,'-') ? substr(PHP_VERSION,0,strpos(PHP_VERSION,'-')) : PHP_VERSION; // Linux distributors like to add suffixes, like in 5.1.2-1. Those must be ignored!
03996                                 if($versionRange[0] && version_compare($phpv,$versionRange[0],'<')) {
03997                                         $msg[] = '<br />The running PHP version ('.$phpv.') is lower than required ('.$versionRange[0].')';
03998                                         $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;<input type="checkbox" value="1" name="depsolver[ignore]['.$depK.']" /> Ignore this version requirement';
03999                                         $depError = true;
04000                                         continue;
04001                                 } elseif($versionRange[1] && version_compare($phpv,$versionRange[1],'>')) {
04002                                         $msg[] = '<br />The running PHP version ('.$phpv.') is higher than allowed ('.$versionRange[1].')';
04003                                         $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;<input type="checkbox" value="1" name="depsolver[ignore]['.$depK.']" /> Ignore this version requirement';
04004                                         $depError = true;
04005                                         continue;
04006                                 }
04007                         } elseif($depK == 'typo3') {
04008                                 if(!$depV) continue;
04009                                 $versionRange = $this->splitVersionRange($depV);
04010                                 if($versionRange[0] && version_compare(TYPO3_version,$versionRange[0],'<')) {
04011                                         $msg[] = '<br />The running TYPO3 version ('.TYPO3_version.') is lower than required ('.$versionRange[0].')';
04012                                         $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;<input type="checkbox" value="1" name="depsolver[ignore]['.$depK.']" /> Ignore this version requirement';
04013                                         $depError = true;
04014                                         continue;
04015                                 } elseif($versionRange[1] && version_compare(TYPO3_version,$versionRange[1],'>')) {
04016                                         $msg[] = '<br />The running TYPO3 version ('.TYPO3_version.') is higher than allowed ('.$versionRange[1].')';
04017                                         $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;<input type="checkbox" value="1" name="depsolver[ignore]['.$depK.']" /> Ignore this version requirement';
04018                                         $depError = true;
04019                                         continue;
04020                                 }
04021                         } elseif (strlen($depK) && !t3lib_extMgm::isLoaded($depK))      { // strlen check for braindead empty dependencies coming from extensions...
04022                                 if(!isset($instExtInfo[$depK])) {
04023                                         $msg[] = '<br />Extension "'.$depK.'" was not available in the system. Please import it from the TYPO3 Extension Repository.';
04024                                         $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;<img src="'.$GLOBALS['BACK_PATH'].'gfx/import.gif" width="12" height="12" title="Import this extension to \'local\' dir typo3conf/ext/ from online repository." alt="" />&nbsp;<a href="index.php?CMD[importExt]='.$depK.'&CMD[loc]=L&CMD[standAlone]=1" target="_blank">Import now (opens a new window)</a>';
04025                                         $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;<input type="checkbox" value="1" name="depsolver[ignore]['.$depK.']" /> Ignore this extension requirement';
04026                                 } else {
04027                                         $msg[] = '<br />Extension "'.$depK.'" ('.$instExtInfo[$depK]['EM_CONF']['title'].') was not installed. Please install it first.';
04028                                         $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;'.$this->installButton().'&nbsp;<a href="'.htmlspecialchars('index.php?CMD[showExt]='.$depK.'&CMD[load]=1&CMD[clrCmd]=1&CMD[standAlone]=1&SET[singleDetails]=info').'" target="_blank">Install now (opens a new window)</a>';
04029                                         $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;<input type="checkbox" value="1" name="depsolver[ignore]['.$depK.']" /> Ignore this extension requirement';
04030                                 }
04031                                 $depError = true;
04032                         } else {
04033                                 $versionRange = $this->splitVersionRange($depV);
04034                                 if($versionRange[0] && version_compare($instExtInfo[$depK]['EM_CONF']['version'],$versionRange[0],'<')) {
04035                                         $msg[] = '<br />The running version of extension "'.$depK.'" ('.$instExtInfo[$depK]['EM_CONF']['version'].') is lower than required ('.$versionRange[0].')';
04036                                         $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;<input type="checkbox" value="1" name="depsolver[ignore]['.$depK.']" /> Ignore this version requirement';
04037                                         $depError = true;
04038                                         continue;
04039                                 } elseif($versionRange[1] && version_compare($instExtInfo[$depK]['EM_CONF']['version'],$versionRange[1],'>')) {
04040                                         $msg[] = '<br />The running version of extension "'.$depK.'" ('.$instExtInfo[$depK]['EM_CONF']['version'].') is higher than allowed ('.$versionRange[1].')';
04041                                         $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;<input type="checkbox" value="1" name="depsolver[ignore]['.$depK.']" /> Ignore this version requirement';
04042                                         $depError = true;
04043                                         continue;
04044                                 }
04045                         }
04046                 }
04047                 if($depError) {
04048                         $content .= $this->doc->section('Dependency Error',implode('<br />',$msg),0,1,2);
04049                 }
04050 
04051                         // Check conflicts with other extensions:
04052                 $conflictError = false;
04053                 $msg = array();
04054                 foreach((array)$conf['constraints']['conflicts'] as $conflictK => $conflictV)   {
04055                         if($depsolver['ignore'][$conflictK]) {
04056                                 $msg[] = '<br />Conflict with '.$conflictK.' ignored as requested.
04057                                 <input type="hidden" value="1" name="depsolver[ignore]['.$conflictK.']" />';
04058                                 continue;
04059                         }
04060                         if (t3lib_extMgm::isLoaded($conflictK)) {
04061                                 $msg[] = 'The extensions "'.$extKey.'" and "'.$conflictK.'" ('.$instExtInfo[$conflictK]['EM_CONF']['title'].') will conflict with each other. Please remove "'.$conflictK.'" if you want to install "'.$extKey.'".';
04062                                 $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;'.$this->removeButton().'&nbsp;<a href="'.htmlspecialchars('index.php?CMD[showExt]='.$conflictK.'&CMD[remove]=1&CMD[clrCmd]=1&CMD[standAlone]=1&SET[singleDetails]=info').'" target="_blank">Remove now (opens a new window)</a>';
04063                                 $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;<input type="checkbox" value="1" name="depsolver[ignore]['.$conflictK.']" /> Ignore this conflict error';
04064                                 $conflictError = true;
04065                         }
04066                 }
04067                 if($conflictError) {
04068                         $content .= $this->doc->section('Conflict Error',implode('<br />',$msg),0,1,2);
04069                 }
04070 
04071                         // Check suggests on other extensions:
04072                 if(is_array($conf['constraints']['suggests'])) {
04073                         $suggestion = false;
04074                         $msg = array();
04075                         foreach($conf['constraints']['suggests'] as $suggestK => $suggestV)     {
04076                                 if($depsolver['ignore'][$suggestK]) {
04077                                         $msg[] = '<br />Suggestion of '.$suggestK.' acknowledged.
04078                                 <input type="hidden" value="1" name="depsolver[ignore]['.$suggestK.']" />';
04079                                         continue;
04080                                 }
04081                                 if (!t3lib_extMgm::isLoaded($suggestK)) {
04082                                         if (!isset($instExtInfo[$suggestK]))    {
04083                                                 $msg[] = 'Extension "'.$suggestK.'" was not available in the system. You may want to import it from the TYPO3 Extension Repository.';
04084                                                 $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;<img src="'.$GLOBALS['BACK_PATH'].'gfx/import.gif" width="12" height="12" title="Import this extension to \'local\' dir typo3conf/ext/ from online repository." alt="" />&nbsp;<a href="index.php?CMD[importExt]='.$depK.'&CMD[loc]=L&CMD[standAlone]=1" target="_blank">Import now (opens a new window)</a>';
04085                                                 $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;<input type="checkbox" value="1" name="depsolver[ignore]['.$suggestK.']" /> Ignore this suggestion';
04086                                         } else {
04087                                                 $msg[] = 'Extension "'.$suggestK.'" ('.$instExtInfo[$suggestK]['EM_CONF']['title'].') was not installed. You may want to install it.';
04088                                                 $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;'.$this->installButton().'&nbsp;<a href="'.htmlspecialchars('index.php?CMD[showExt]='.$suggestK.'&CMD[load]=1&CMD[clrCmd]=1&CMD[standAlone]=1&SET[singleDetails]=info').'" target="_blank">Install now (opens a new window)</a>';
04089                                                 $msg[] = '&nbsp;&nbsp;&nbsp;&nbsp;<input type="checkbox" value="1" name="depsolver[ignore]['.$suggestK.']" /> Ignore this suggestion';
04090                                         }
04091                                         $suggestion = true;
04092                                 }
04093                         }
04094                         if($suggestion) {
04095                                 $content .= $this->doc->section('Extensions suggested by extension "'.$extKey.'"',implode('<br />',$msg),0,1,1);
04096                         }
04097                 }
04098 
04099                 if($depError || $conflictError || $suggestion) {
04100                         foreach($this->CMD as $k => $v) {
04101                                 $content .= '<input type="hidden" name="CMD['.$k.']" value="'.$v.'" />';
04102                         }
04103                         $content .= '<br /><br /><input type="submit" value="Try again" />';
04104 
04105                         return array('returnCode' => false, 'html' => $content);
04106                 }
04107 
04108                 return array('returnCode' => true);
04109         }
04110 
04120         function removeExtFromList($extKey,$instExtInfo)        {
04121                 global $TYPO3_LOADED_EXT;
04122 
04123                         // Initialize:
04124                 $depList = array();
04125                 $listArr = array_keys($TYPO3_LOADED_EXT);
04126 
04127                         // Traverse all installed extensions to check if any of them have this extension as dependency since if that is the case it will not work out!
04128                 foreach($listArr as $k => $ext) {
04129                         if ($instExtInfo[$ext]['EM_CONF']['dependencies'])      {
04130                                 $dep = t3lib_div::trimExplode(',',$instExtInfo[$ext]['EM_CONF']['dependencies'],1);
04131                                 if (in_array($extKey,$dep))     {
04132                                         $depList[] = $ext;
04133                                 }
04134                         }
04135                         if (!strcmp($ext,$extKey))      unset($listArr[$k]);
04136                 }
04137 
04138                         // Returns either error or the new list
04139                 if (count($depList))    {
04140                         $msg = 'The extension(s) "'.implode(', ',$depList).'" depends on the extension you are trying to remove. The operation was not completed.';
04141                         $this->content.=$this->doc->section('Dependency Error',$msg,0,1,2);
04142                         return -1;
04143                 } else {
04144                         $listArr = $this->removeRequiredExtFromListArr($listArr);
04145                         $list = implode(',',array_unique($listArr));
04146                         return $list;
04147                 }
04148         }
04149 
04157         function removeRequiredExtFromListArr($listArr) {
04158                 foreach($listArr as $k => $ext) {
04159                         if (in_array($ext,$this->requiredExt) || !strcmp($ext,'_CACHEFILE'))    unset($listArr[$k]);
04160                 }
04161                 return $listArr;
04162         }
04163 
04172         function managesPriorities($listArr,$instExtInfo)       {
04173 
04174                         // Initialize:
04175                 $levels = array(
04176                         'top' => array(),
04177                         'middle' => array(),
04178                         'bottom' => array(),
04179                 );
04180 
04181                         // Traverse list of extensions:
04182                 foreach($listArr as $ext)       {
04183                         $prio = trim($instExtInfo[$ext]['EM_CONF']['priority']);
04184                         switch((string)$prio)   {
04185                                 case 'top':
04186                                 case 'bottom':
04187                                         $levels[$prio][] = $ext;
04188                                         break;
04189                                 default:
04190                                         $levels['middle'][] = $ext;
04191                                         break;
04192                         }
04193                 }
04194                 return array_merge(
04195                         $levels['top'],
04196                         $levels['middle'],
04197                         $levels['bottom']
04198                 );
04199         }
04200 
04201 
04202 
04203 
04204 
04205 
04206 
04207 
04208 
04209 
04210         /*******************************
04211         *
04212         * System Update functions (based on extension requirements)
04213         *
04214         ******************************/
04215 
04224         function checkClearCache($extInfo)      {
04225                 if ($extInfo['EM_CONF']['clearCacheOnLoad'])    {
04226                         if (t3lib_div::_POST('_clear_all_cache'))       {               // Action: Clearing the cache
04227                                 $tce = t3lib_div::makeInstance('t3lib_TCEmain');
04228                                 $tce->stripslashes_values = 0;
04229                                 $tce->start(Array(),Array());
04230                                 $tce->clear_cacheCmd('all');
04231                         } else {        // Show checkbox for clearing cache:
04232                                 $content.= '
04233                                         <br />
04234                                         <h3>Clear cache</h3>
04235                                         <p>This extension requests the cache to be cleared when it is installed/removed.<br />
04236                                                 Clear all cache: <input type="checkbox" name="_clear_all_cache" checked="checked" value="1" /><br />
04237                                                 </p>
04238                                 ';
04239                         }
04240                 }
04241                 return $content;
04242         }
04243 
04251         function checkUploadFolder($extKey,$extInfo)    {
04252 
04253                         // Checking for upload folder:
04254                 $uploadFolder = PATH_site.$this->ulFolder($extKey);
04255                 if ($extInfo['EM_CONF']['uploadfolder'] && !@is_dir($uploadFolder))     {
04256                         if (t3lib_div::_POST('_uploadfolder'))  {       // CREATE dir:
04257                                 t3lib_div::mkdir($uploadFolder);
04258                                 $indexContent = '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN">
04259 <HTML>
04260 <HEAD>
04261         <TITLE></TITLE>
04262 <META http-equiv=Refresh Content="0; Url=../../">
04263 </HEAD>
04264 </HTML>';
04265                                 t3lib_div::writeFile($uploadFolder.'index.html',$indexContent);
04266                         } else {        // Show checkbox / HTML for creation:
04267                                 $content.='
04268                                         <br /><h3>Create upload folder</h3>
04269                                         <p>The extension requires the upload folder "'.$this->ulFolder($extKey).'" to exist.<br />
04270                                 Create directory "'.$this->ulFolder($extKey).'": <input type="checkbox" name="_uploadfolder" checked="checked" value="1" /><br />
04271                                 </p>
04272                                 ';
04273                         }
04274                 }
04275 
04276                         // Additional directories that should be created:
04277                 if ($extInfo['EM_CONF']['createDirs'])  {
04278                         $createDirs = array_unique(t3lib_div::trimExplode(',',$extInfo['EM_CONF']['createDirs'],1));
04279 
04280                         foreach($createDirs as $crDir)  {
04281                                 if (!@is_dir(PATH_site.$crDir)) {
04282                                         if (t3lib_div::_POST('_createDir_'.md5($crDir)))        {       // CREATE dir:
04283 
04284                                                         // Initialize:
04285                                                 $crDirStart = '';
04286                                                 $dirs_in_path = explode('/',preg_replace('/\/$/','',$crDir));
04287 
04288                                                         // Traverse each part of the dir path and create it one-by-one:
04289                                                 foreach($dirs_in_path as $dirP) {
04290                                                         if (strcmp($dirP,''))   {
04291                                                                 $crDirStart.= $dirP.'/';
04292                                                                 if (!@is_dir(PATH_site.$crDirStart))    {
04293                                                                         t3lib_div::mkdir(PATH_site.$crDirStart);
04294                                                                         $finalDir = PATH_site.$crDirStart;
04295                                                                 }
04296                                                         } else {
04297                                                                 die('ERROR: The path "'.PATH_site.$crDir.'" could not be created.');
04298                                                         }
04299                                                 }
04300                                                 if ($finalDir)  {
04301                                                         $indexContent = '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN">
04302 <HTML>
04303 <HEAD>
04304         <TITLE></TITLE>
04305 <META http-equiv=Refresh Content="0; Url=/">
04306 </HEAD>
04307 </HTML>';
04308                                                         t3lib_div::writeFile($finalDir.'index.html',$indexContent);
04309                                                 }
04310                                         } else {        // Show checkbox / HTML for creation:
04311                                                 $content.='
04312                                                         <br />
04313                                                         <h3>Create folder</h3>
04314                                                         <p>The extension requires the folder "'.$crDir.'" to exist.<br />
04315                                                 Create directory "'.$crDir.'": <input type="checkbox" name="_createDir_'.md5($crDir).'" checked="checked" value="1" /><br />
04316                                                 </p>
04317                                                 ';
04318                                         }
04319                                 }
04320                         }
04321                 }
04322 
04323                 return $content;
04324         }
04325 
04336         function checkDBupdates($extKey,$extInfo,$infoOnly=0)   {
04337 
04338                         // Initializing Install Tool object:
04339                 $instObj = new t3lib_install;
04340                 $instObj->INSTALL = t3lib_div::_GP('TYPO3_INSTALL');
04341                 $dbStatus = array();
04342 
04343                         // Updating tables and fields?
04344                 if (is_array($extInfo['files']) && in_array('ext_tables.sql',$extInfo['files']))        {
04345                         $fileContent = t3lib_div::getUrl($this->getExtPath($extKey,$extInfo['type']).'ext_tables.sql');
04346 
04347                         $FDfile = $instObj->getFieldDefinitions_sqlContent($fileContent);
04348                         if (count($FDfile))     {
04349                                 $FDdb = $instObj->getFieldDefinitions_database(TYPO3_db);
04350                                 $diff = $instObj->getDatabaseExtra($FDfile, $FDdb);
04351                                 $update_statements = $instObj->getUpdateSuggestions($diff);
04352 
04353                                 $dbStatus['structure']['tables_fields'] = $FDfile;
04354                                 $dbStatus['structure']['diff'] = $diff;
04355 
04356                                         // Updating database...
04357                                 if (!$infoOnly && is_array($instObj->INSTALL['database_update']))       {
04358                                         $instObj->performUpdateQueries($update_statements['add'],$instObj->INSTALL['database_update']);
04359                                         $instObj->performUpdateQueries($update_statements['change'],$instObj->INSTALL['database_update']);
04360                                         $instObj->performUpdateQueries($update_statements['create_table'],$instObj->INSTALL['database_update']);
04361                                 } else {
04362                                         $content.=$instObj->generateUpdateDatabaseForm_checkboxes($update_statements['add'],'Add fields');
04363                                         $content.=$instObj->generateUpdateDatabaseForm_checkboxes($update_statements['change'],'Changing fields',1,0,$update_statements['change_currentValue']);
04364                                         $content.=$instObj->generateUpdateDatabaseForm_checkboxes($update_statements['create_table'],'Add tables');
04365                                 }
04366                         }
04367                 }
04368 
04369                         // Importing static tables?
04370                 if (is_array($extInfo['files']) && in_array('ext_tables_static+adt.sql',$extInfo['files']))     {
04371                         $fileContent = t3lib_div::getUrl($this->getExtPath($extKey,$extInfo['type']).'ext_tables_static+adt.sql');
04372 
04373                         $statements = $instObj->getStatementArray($fileContent,1);
04374                         list($statements_table, $insertCount) = $instObj->getCreateTables($statements,1);
04375 
04376                                 // Execute import of static table content:
04377                         if (!$infoOnly && is_array($instObj->INSTALL['database_import']))       {
04378 
04379                                         // Traverse the tables
04380                                 foreach($instObj->INSTALL['database_import'] as $table => $md5str)      {
04381                                         if ($md5str == md5($statements_table[$table]))  {
04382                                                 $GLOBALS['TYPO3_DB']->admin_query('DROP TABLE IF EXISTS '.$table);
04383                                                 $GLOBALS['TYPO3_DB']->admin_query($statements_table[$table]);
04384 
04385                                                 if ($insertCount[$table])       {
04386                                                         $statements_insert = $instObj->getTableInsertStatements($statements, $table);
04387 
04388                                                         foreach($statements_insert as $v)       {
04389                                                                 $GLOBALS['TYPO3_DB']->admin_query($v);
04390                                                         }
04391                                                 }
04392                                         }
04393                                 }
04394                         } else {
04395                                 $whichTables = $instObj->getListOfTables();
04396                                 if (count($statements_table))   {
04397                                         $out = '';
04398                                         foreach($statements_table as $table => $definition)     {
04399                                                 $exist = isset($whichTables[$table]);
04400 
04401                                                 $dbStatus['static'][$table]['exists'] = $exist;
04402                                                 $dbStatus['static'][$table]['count'] = $insertCount[$table];
04403 
04404                                                 $out.= '<tr>
04405                                                         <td><input type="checkbox" name="TYPO3_INSTALL[database_import]['.$table.']" checked="checked" value="'.md5($definition).'" /></td>
04406                                                         <td><strong>'.$table.'</strong></td>
04407                                                         <td><img src="clear.gif" width="10" height="1" alt="" /></td>
04408                                                         <td nowrap="nowrap">'.($insertCount[$table]?'Rows: '.$insertCount[$table]:'').'</td>
04409                                                         <td><img src="clear.gif" width="10" height="1" alt="" /></td>
04410                                                         <td nowrap="nowrap">'.($exist?'<img src="'.$GLOBALS['BACK_PATH'].'gfx/icon_warning.gif" width="18" height="16" align="top" alt="" />Table exists!':'').'</td>
04411                                                         </tr>';
04412                                         }
04413                                         $content.= '
04414                                                 <br />
04415                                                 <h3>Import static data</h3>
04416                                                 <table border="0" cellpadding="0" cellspacing="0">'.$out.'</table>';
04417                                 }
04418                         }
04419                 }
04420 
04421                         // Return array of information if $infoOnly, otherwise content.
04422                 return $infoOnly ? $dbStatus : $content;
04423         }
04424 
04433         function forceDBupdates($extKey, $extInfo)      {
04434                 $instObj = new t3lib_install;
04435 
04436                         // Updating tables and fields?
04437                 if (is_array($extInfo['files']) && in_array('ext_tables.sql',$extInfo['files']))        {
04438                         $fileContent = t3lib_div::getUrl($this->getExtPath($extKey,$extInfo['type']).'ext_tables.sql');
04439 
04440                         $FDfile = $instObj->getFieldDefinitions_sqlContent($fileContent);
04441                         if (count($FDfile))     {
04442                                 $FDdb = $instObj->getFieldDefinitions_database(TYPO3_db);
04443                                 $diff = $instObj->getDatabaseExtra($FDfile, $FDdb);
04444                                 $update_statements = $instObj->getUpdateSuggestions($diff);
04445 
04446                                 foreach((array)$update_statements['add'] as $string)    {
04447                                         $GLOBALS['TYPO3_DB']->admin_query($string);
04448                                 }
04449                                 foreach((array)$update_statements['change'] as $string) {
04450                                         $GLOBALS['TYPO3_DB']->admin_query($string);
04451                                 }
04452                                 foreach((array)$update_statements['create_table'] as $string)   {
04453                                         $GLOBALS['TYPO3_DB']->admin_query($string);
04454                                 }
04455                         }
04456                 }
04457 
04458                         // Importing static tables?
04459                 if (is_array($extInfo['files']) && in_array('ext_tables_static+adt.sql',$extInfo['files']))     {
04460                         $fileContent = t3lib_div::getUrl($this->getExtPath($extKey,$extInfo['type']).'ext_tables_static+adt.sql');
04461 
04462                         $statements = $instObj->getStatementArray($fileContent,1);
04463                         list($statements_table, $insertCount) = $instObj->getCreateTables($statements,1);
04464 
04465                                 // Traverse the tables
04466                         foreach($statements_table as $table => $query)  {
04467                                 $GLOBALS['TYPO3_DB']->admin_query('DROP TABLE IF EXISTS '.$table);
04468                                 $GLOBALS['TYPO3_DB']->admin_query($query);
04469 
04470                                 if ($insertCount[$table])       {
04471                                         $statements_insert = $instObj->getTableInsertStatements($statements, $table);
04472 
04473                                         foreach($statements_insert as $v)       {
04474                                                 $GLOBALS['TYPO3_DB']->admin_query($v);
04475                                         }
04476                                 }
04477                         }
04478                 }
04479         }
04480 
04491         function tsStyleConfigForm($extKey,$extInfo,$output=0,$script='',$addFields='') {
04492                 global $TYPO3_CONF_VARS;
04493 
04494                         // Initialize:
04495                 $absPath = $this->getExtPath($extKey,$extInfo['type']);
04496                 $relPath = $this->typeRelPaths[$extInfo['type']].$extKey.'/';
04497 
04498                         // Look for template file for form:
04499                 if (@is_file($absPath.'ext_conf_template.txt')) {
04500 
04501                                 // Load tsStyleConfig class and parse configuration template:
04502                         $tsStyleConfig = t3lib_div::makeInstance('t3lib_tsStyleConfig');
04503                         $tsStyleConfig->doNotSortCategoriesBeforeMakingForm = TRUE;
04504                         $theConstants = $tsStyleConfig->ext_initTSstyleConfig(
04505                         t3lib_div::getUrl($absPath.'ext_conf_template.txt'),
04506                         $relPath,
04507                         $absPath,
04508                         $GLOBALS['BACK_PATH']
04509                         );
04510 
04511                                 // Load the list of resources.
04512                         $tsStyleConfig->ext_loadResources($absPath.'res/');
04513 
04514                                 // Load current value:
04515                         $arr = unserialize($TYPO3_CONF_VARS['EXT']['extConf'][$extKey]);
04516                         $arr = is_array($arr) ? $arr : array();
04517 
04518                                 // Call processing function for constants config and data before write and form rendering:
04519                         if (is_array($TYPO3_CONF_VARS['SC_OPTIONS']['typo3/mod/tools/em/index.php']['tsStyleConfigForm']))      {
04520                                 $_params = array('fields' => &$theConstants, 'data' => &$arr, 'extKey' => $extKey);
04521                                 foreach($TYPO3_CONF_VARS['SC_OPTIONS']['typo3/mod/tools/em/index.php']['tsStyleConfigForm'] as $_funcRef)       {
04522                                         t3lib_div::callUserFunction($_funcRef,$_params,$this);
04523                                 }
04524                                 unset($_params);
04525                         }
04526 
04527                                 // If saving operation is done:
04528                         if (t3lib_div::_POST('submit')) {
04529                                 $tsStyleConfig->ext_procesInput(t3lib_div::_POST(),array(),$theConstants,array());
04530                                 $arr = $tsStyleConfig->ext_mergeIncomingWithExisting($arr);
04531                                 $this->writeTsStyleConfig($extKey,$arr);
04532                         }
04533 
04534                                 // Setting value array
04535                         $tsStyleConfig->ext_setValueArray($theConstants,$arr);
04536 
04537                                 // Getting session data:
04538                         $MOD_MENU = array();
04539                         $MOD_MENU['constant_editor_cat'] = $tsStyleConfig->ext_getCategoriesForModMenu();
04540                         $MOD_SETTINGS = t3lib_BEfunc::getModuleData($MOD_MENU, t3lib_div::_GP('SET'), 'xMod_test');
04541 
04542                                 // Resetting the menu (stop)
04543                         if (count($MOD_MENU)>1) {
04544                                 $menu = 'Category: '.t3lib_BEfunc::getFuncMenu(0,'SET[constant_editor_cat]',$MOD_SETTINGS['constant_editor_cat'],$MOD_MENU['constant_editor_cat'],'','&CMD[showExt]='.$extKey);
04545                                 $this->content.=$this->doc->section('','<span class="nobr">'.$menu.'</span>');
04546                                 $this->content.=$this->doc->spacer(10);
04547                         }
04548 
04549                                 // Category and constant editor config:
04550                         $form = '
04551                                 <table border="0" cellpadding="0" cellspacing="0" width="600">
04552                                         <tr>
04553                                                 <td>'.$tsStyleConfig->ext_getForm($MOD_SETTINGS['constant_editor_cat'],$theConstants,$script,$addFields).'</td>
04554                                         </tr>
04555                                 </table>';
04556                         if ($output)    {
04557                                 return $form;
04558                         } else {
04559                                 $this->content.=$this->doc->section('','</form>'.$form.'<form>');
04560                         }
04561                 }
04562         }
04563 
04564 
04565 
04566 
04567 
04568 
04569 
04570 
04571 
04572 
04573         /*******************************
04574         *
04575         * Dumping database (MySQL compliant)
04576         *
04577         ******************************/
04578 
04586         function dumpTableAndFieldStructure($arr)       {
04587                 $tables = array();
04588 
04589                 if (count($arr))        {
04590 
04591                         // Get file header comment:
04592                         $tables[] = $this->dumpHeader();
04593 
04594                         // Traverse tables, write each table/field definition:
04595                         foreach($arr as $table => $fieldKeyInfo)        {
04596                                 $tables[] = $this->dumpTableHeader($table,$fieldKeyInfo);
04597                         }
04598                 }
04599 
04600                 // Return result:
04601                 return implode(chr(10).chr(10).chr(10),$tables);
04602         }
04603 
04611         function dumpStaticTables($tableList)   {
04612                 $instObj = new t3lib_install;
04613                 $dbFields = $instObj->getFieldDefinitions_database(TYPO3_db);
04614 
04615                 $out = '';
04616                 $parts = t3lib_div::trimExplode(',',$tableList,1);
04617 
04618                 // Traverse the table list and dump each:
04619                 foreach($parts as $table)       {
04620                         if (is_array($dbFields[$table]['fields']))      {
04621                                 $dHeader = $this->dumpHeader();
04622                                 $header = $this->dumpTableHeader($table,$dbFields[$table],1);
04623                                 $insertStatements = $this->dumpTableContent($table,$dbFields[$table]['fields']);
04624 
04625                                 $out.= $dHeader.chr(10).chr(10).chr(10).
04626                                 $header.chr(10).chr(10).chr(10).
04627                                 $insertStatements.chr(10).chr(10).chr(10);
04628                         } else {
04629                                 die('Fatal error: Table for dump not found in database...');
04630                         }
04631                 }
04632                 return $out;
04633         }
04634 
04640         function dumpHeader()   {
04641                 return trim('
04642 # TYPO3 Extension Manager dump 1.1
04643 #
04644 # Host: '.TYPO3_db_host.'    Database: '.TYPO3_db.'
04645 #--------------------------------------------------------
04646 ');
04647         }
04648 
04657         function dumpTableHeader($table,$fieldKeyInfo,$dropTableIfExists=0)     {
04658                 $lines = array();
04659                 $dump = '';
04660 
04661                 // Create field definitions
04662                 if (is_array($fieldKeyInfo['fields']))  {
04663                         foreach($fieldKeyInfo['fields'] as $fieldN => $data)    {
04664                                 $lines[]='  '.$fieldN.' '.$data;
04665                         }
04666                 }
04667 
04668                 // Create index key definitions
04669                 if (is_array($fieldKeyInfo['keys']))    {
04670                         foreach($fieldKeyInfo['keys'] as $fieldN => $data)      {
04671                                 $lines[]='  '.$data;
04672                         }
04673                 }
04674 
04675                 // Compile final output:
04676                 if (count($lines))      {
04677                         $dump = trim('
04678 #
04679 # Table structure for table "'.$table.'"
04680 #
04681 '.($dropTableIfExists ? 'DROP TABLE IF EXISTS '.$table.';
04682 ' : '').'CREATE TABLE '.$table.' (
04683 '.implode(','.chr(10),$lines).'
04684 );'
04685 );
04686                 }
04687 
04688                 return $dump;
04689         }
04690 
04699         function dumpTableContent($table,$fieldStructure)       {
04700 
04701                 // Substitution of certain characters (borrowed from phpMySQL):
04702                 $search = array('\\', '\'', "\x00", "\x0a", "\x0d", "\x1a");
04703                 $replace = array('\\\\', '\\\'', '\0', '\n', '\r', '\Z');
04704 
04705                 $lines = array();
04706 
04707                 // Select all rows from the table:
04708                 $result = $GLOBALS['TYPO3_DB']->exec_SELECTquery('*', $table, '');
04709 
04710                 // Traverse the selected rows and dump each row as a line in the file:
04711                 while ($row = $GLOBALS['TYPO3_DB']->sql_fetch_assoc($result)) {
04712                         $values = array();
04713                         reset($fieldStructure);
04714                         while(list($field) = each($fieldStructure))     {
04715                                 $values[] = isset($row[$field]) ? "'".str_replace($search, $replace, $row[$field])."'" : 'NULL';
04716                         }
04717                         $lines[] = 'INSERT INTO '.$table.' VALUES ('.implode(', ',$values).');';
04718                 }
04719 
04720                 // Free DB result:
04721                 $GLOBALS['TYPO3_DB']->sql_free_result($result);
04722 
04723                 // Implode lines and return:
04724                 return implode(chr(10),$lines);
04725         }
04726 
04734         function getTableAndFieldStructure($parts)      {
04735                 // Instance of install tool
04736                 $instObj = new t3lib_install;
04737                 $dbFields = $instObj->getFieldDefinitions_database(TYPO3_db);
04738 
04739 
04740                 $outTables = array();
04741                 foreach($parts as $table)       {
04742                         $tP = explode('.',$table);
04743                         if ($tP[0] && isset($dbFields[$tP[0]])) {
04744                                 if ($tP[1])     {
04745                                         $kfP = explode('KEY:',$tP[1],2);
04746                                         if (count($kfP)==2 && !$kfP[0]) {       // key:
04747                                                 if (isset($dbFields[$tP[0]]['keys'][$kfP[1]]))  $outTables[$tP[0]]['keys'][$kfP[1]] = $dbFields[$tP[0]]['keys'][$kfP[1]];
04748                                         } else {
04749                                                 if (isset($dbFields[$tP[0]]['fields'][$tP[1]])) $outTables[$tP[0]]['fields'][$tP[1]] = $dbFields[$tP[0]]['fields'][$tP[1]];
04750                                         }
04751                                 } else {
04752                                         $outTables[$tP[0]] = $dbFields[$tP[0]];
04753                                 }
04754                         }
04755                 }
04756 
04757                 return $outTables;
04758         }
04759 
04760 
04761 
04762 
04763 
04764 
04765 
04766 
04767 
04768 
04769         /*******************************
04770         *
04771         * TER Communication functions
04772         *
04773         ******************************/
04774 
04775 
04776 
04784         function uploadExtensionToTER($em)      {
04785                 $msg = '';
04786                 $response = $this->terConnection->uploadToTER($em);
04787 
04788                 if(!is_array($response)) return $response;
04789 
04790                 if($response['resultCode']==TX_TER_RESULT_EXTENSIONSUCCESSFULLYUPLOADED) {
04791                         $em['extInfo']['EM_CONF']['version'] = $response['version'];
04792                         $response['resultMessages'][] = 'The extension is now version: '.$response['version'];
04793                         $response['resultMessages'][] = $this->updateLocalEM_CONF($em['extKey'],$em['extInfo']);
04794                 }
04795 
04796                 $msg = '<ul><li>'.implode('</li><li>',$response['resultMessages']).'</li></ul>';
04797                 return $msg;
04798         }
04799 
04800 
04801 
04802 
04803 
04804 
04805 
04806 
04807 
04808 
04809         /************************************
04810         *
04811         * Various helper functions
04812         *
04813         ************************************/
04814 
04822         function listOrderTitle($listOrder,$key)        {
04823                 switch($listOrder)      {
04824                         case 'cat':
04825                                 return isset($this->categories[$key])?$this->categories[$key]:'<em>['.$key.']</em>';
04826                                 break;
04827                         case 'author_company':
04828                                 return $key;
04829                                 break;
04830                         case 'state':
04831                                 return $this->states[$key];
04832                                 break;
04833                         case 'type':
04834                                 return $this->typeDescr[$key];
04835                                 break;
04836                 }
04837         }
04838 
04847         function makeVersion($v,$mode)  {
04848                 $vDat = $this->renderVersion($v);
04849                 return $vDat['version_'.$mode];
04850         }
04851 
04859         function renderVersion($v,$raise='')    {
04860                 $parts = t3lib_div::intExplode('.',$v.'..');
04861                 $parts[0] = t3lib_div::intInRange($parts[0],0,999);
04862                 $parts[1] = t3lib_div::intInRange($parts[1],0,999);
04863                 $parts[2] = t3lib_div::intInRange($parts[2],0,999);
04864 
04865                 switch((string)$raise)  {
04866                         case 'main':
04867                                 $parts[0]++;
04868                                 $parts[1]=0;
04869                                 $parts[2]=0;
04870                                 break;
04871                         case 'sub':
04872                                 $parts[1]++;
04873                                 $parts[2]=0;
04874                                 break;
04875                         case 'dev':
04876                                 $parts[2]++;
04877                                 break;
04878                 }
04879 
04880                 $res = array();
04881                 $res['version'] = $parts[0].'.'.$parts[1].'.'.$parts[2];
04882                 $res['version_int'] = intval(str_pad($parts[0],3,'0',STR_PAD_LEFT).str_pad($parts[1],3,'0',STR_PAD_LEFT).str_pad($parts[2],3,'0',STR_PAD_LEFT));
04883                 $res['version_main'] = $parts[0];
04884                 $res['version_sub'] = $parts[1];
04885                 $res['version_dev'] = $parts[2];
04886 
04887                 return $res;
04888         }
04889 
04896         function ulFolder($extKey)      {
04897                 return 'uploads/tx_'.str_replace('_','',$extKey).'/';
04898         }
04899 
04905         function importAtAll()  {
04906                 return ($GLOBALS['TYPO3_CONF_VARS']['EXT']['allowGlobalInstall'] || $GLOBALS['TYPO3_CONF_VARS']['EXT']['allowLocalInstall']);
04907         }
04908 
04916         function importAsType($type,$lockType='')       {
04917                 switch($type)   {
04918                         case 'G':
04919                                 return $GLOBALS['TYPO3_CONF_VARS']['EXT']['allowGlobalInstall'] && (!$lockType || !strcmp($lockType,$type));
04920                                 break;
04921                         case 'L':
04922                                 return $GLOBALS['TYPO3_CONF_VARS']['EXT']['allowLocalInstall'] && (!$lockType || !strcmp($lockType,$type));
04923                                 break;
04924                         case 'S':
04925                                 return $this->systemInstall;
04926                                 break;
04927                         default:
04928                                 return false;
04929                 }
04930         }
04931 
04938         function deleteAsType($type)    {
04939                 switch($type)   {
04940                         case 'G':
04941                                 return $GLOBALS['TYPO3_CONF_VARS']['EXT']['allowGlobalInstall'];
04942                                 break;
04943                         case 'L':
04944                                 return $GLOBALS['TYPO3_CONF_VARS']['EXT']['allowLocalInstall'];
04945                                 break;
04946                         default:
04947                                 return false;
04948                 }
04949         }
04950 
04959         function versionDifference($v1,$v2,$div=1)      {
04960                 return floor($this->makeVersion($v1,'int')/$div) > floor($this->makeVersion($v2,'int')/$div);
04961         }
04962 
04971         function first_in_array($str,$array,$caseInsensitive=FALSE)     {
04972                 if ($caseInsensitive)   $str = strtolower($str);
04973                 if (is_array($array))   {
04974                         foreach($array as $cl)  {
04975                                 if ($caseInsensitive)   $cl = strtolower($cl);
04976                                 if (t3lib_div::isFirstPartOfStr($cl,$str))      return true;
04977                         }
04978                 }
04979                 return false;
04980         }
04981 
04989         function includeEMCONF($path,$_EXTKEY)  {
04990                 @include($path);
04991                 if(is_array($EM_CONF[$_EXTKEY])) {
04992                         return $this->fixEMCONF($EM_CONF[$_EXTKEY]);
04993                 }
04994                 return false;
04995         }
04996 
05004         function searchExtension($extKey,$row) {
05005                 if ($this->lookUpStr)   {
05006                         return (
05007                         stristr($extKey,$this->lookUpStr) ||
05008                         stristr($row['EM_CONF']['title'],$this->lookUpStr) ||
05009                         stristr($row['EM_CONF']['description'],$this->lookUpStr) ||
05010                         stristr($row['EM_CONF']['author'],$this->lookUpStr) ||
05011                         stristr($row['EM_CONF']['author_company'],$this->lookUpStr)
05012                         );
05013                 } else return true;
05014         }
05015 }
05016 
05017 // Include extension?
05018 if (defined('TYPO3_MODE') && $TYPO3_CONF_VARS[TYPO3_MODE]['XCLASS']['typo3/mod/tools/em/index.php'])    {
05019         include_once($TYPO3_CONF_VARS[TYPO3_MODE]['XCLASS']['typo3/mod/tools/em/index.php']);
05020 }
05021 
05022 ?>


Généré par L'expert TYPO3 avec  doxygen 1.4.6