oxconfig.php

Go to the documentation of this file.
00001 <?php
00002 
00003 define( 'MAX_64BIT_INTEGER', '18446744073709551615' );
00004 
00009 class oxConfig extends oxSuperCfg
00010 {
00011     // this column of params are defined in config.inc.php file,
00012     // so for backwards compat. names starts without underscore
00013 
00019     protected $dbHost = null;
00020 
00026     protected $dbName = null;
00027 
00033     protected $dbUser = null;
00034 
00040     protected $dbPwd  = null;
00041 
00047     protected $dbType = null;
00048 
00054     protected $sShopURL = null;
00055 
00061     protected $sSSLShopURL = null;
00062 
00068     protected $sAdminSSLURL = null;
00069 
00075     protected $sShopDir = null;
00076 
00082     protected $sCompileDir = null;
00083 
00098     protected $iDebug = 0;
00099 
00105     protected $sAdminEmail = null;
00106 
00112     protected $blSessionUseCookies = null;
00113 
00119     //protected $iMaxArticles = 6000;
00120 
00130     protected $blNativeImages = true;
00131 
00137     protected $aMultiShopTables = array( 'oxarticles', 'oxdiscount', 'oxcategories', 'oxattribute',
00138                                          'oxlinks', 'oxvoucherseries', 'oxmanufacturers',
00139                                          'oxnews', 'oxselectlist', 'oxwrapping',
00140                                          'oxdeliveryset', 'oxdelivery', 'oxvendor', 'oxobject2category');
00141 
00147     private static $_instance = null;
00148 
00154     private $_oStart = null;
00155 
00156 
00162     protected $_oActShop       = null;
00163 
00171     protected $_oActView       = null;
00172 
00178     protected $_aGlobalParams = array();
00179 
00185     protected $_aConfigParams = array();
00186 
00192     protected $_iLanguageId = null;
00193 
00199     protected $_iShopId = null;
00200 
00201 
00207     protected $_sOutDir = 'out';
00208 
00214     protected $_sImageDir = 'img';
00215 
00221     protected $_sPictureDir = 'pictures';
00222 
00228     protected $_sMasterPictureDir = 'master';
00229 
00235     protected $_sTemplateDir = 'tpl';
00236 
00242     protected $_sResourceDir = 'src';
00243 
00249     protected $_blIsSsl = null;
00250 
00256     protected $_aAbsDynImageDir = array();
00257 
00263     protected $_oActCurrencyObject = null;
00264 
00272     public function getConfigParam( $sName )
00273     {
00274         if ( isset( $this->$sName ) ) {
00275             return $this->$sName;
00276         } elseif ( isset ( $this->_aConfigParams[$sName] ) ) {
00277             return $this->_aConfigParams[$sName];
00278         }
00279     }
00280 
00289     public function setConfigParam( $sName, $sValue )
00290     {
00291         if ( isset( $this->$sName ) ) {
00292             $this->$sName = $sValue;
00293         } else {
00294             $this->_aConfigParams[$sName] = $sValue;
00295         }
00296     }
00297 
00303     public function init()
00304     {
00305         include getShopBasePath().'config.inc.php';
00306         include getShopBasePath().'core/oxconfk.php';
00307 
00308         //adding trailing slashes
00309         $oFileUtils = oxUtilsFile::getInstance();
00310         $this->sShopDir     = $oFileUtils->normalizeDir($this->sShopDir);
00311         $this->sCompileDir  = $oFileUtils->normalizeDir($this->sCompileDir);
00312         $this->sShopURL     = $oFileUtils->normalizeDir($this->sShopURL);
00313         $this->sSSLShopURL  = $oFileUtils->normalizeDir($this->sSSLShopURL);
00314         $this->sAdminSSLURL = $oFileUtils->normalizeDir($this->sAdminSSLURL);
00315 
00316 
00317         // some important defaults
00318         if( !$this->getConfigParam( 'sDefaultLang' ) )
00319             $this->setConfigParam( 'sDefaultLang', 0 );
00320 
00321         $blLogChangesInAdmin = $this->getConfigParam( 'blLogChangesInAdmin' );
00322         if( !isset( $blLogChangesInAdmin ) )
00323             $this->setConfigParam( 'blLogChangesInAdmin', false );
00324 
00325         $blCheckTemplates = $this->getConfigParam( 'blCheckTemplates' );
00326         if( !isset( $blCheckTemplates ) )
00327             $this->setConfigParam( 'blCheckTemplates', false );
00328 
00329         $blAllowArticlesubclass = $this->getConfigParam( 'blAllowArticlesubclass' );
00330         if( !isset( $blAllowArticlesubclass ) )
00331             $this->setConfigParam( 'blAllowArticlesubclass', false );
00332 
00333         $iAdminListSize = $this->getConfigParam( 'iAdminListSize' );
00334         if( !isset( $iAdminListSize ) )
00335             $this->setConfigParam( 'iAdminListSize', 9 );
00336 
00337         // #1173M  for EE - not all pic are deleted
00338         $iPicCount = $this->getConfigParam( 'iPicCount' );
00339         if( !isset( $iPicCount ) )
00340             $this->setConfigParam( 'iPicCount', 7 );
00341 
00342         $iZoomPicCount = $this->getConfigParam( 'iZoomPicCount' );
00343         if( !isset( $iZoomPicCount ) )
00344             $this->setConfigParam( 'iZoomPicCount', 4 );
00345 
00346         //max shop id default value
00347         $iMaxShopId = $this->getConfigParam( 'iMaxShopId' );
00348         if( !isset( $iMaxShopId ) )
00349             $this->setConfigParam( 'iMaxShopId', 64 );
00350 
00351         // disabling caching according to DODGER #655 : disable Caching as it doesnt work good enought
00352         $this->setConfigParam( 'blTemplateCaching', false );
00353 
00354         //setting ADODB timeout
00355         global  $ADODB_SESS_LIFE;
00356         $ADODB_SESS_LIFE  = 1;
00357 
00358 
00359             /*
00360         $iSessionTimeout = null;
00361         if ( $this->isAdmin())
00362             $iSessionTimeout = $this->getConfigParam( 'iSessionTimeoutAdmin' );
00363         if ( !$this->isAdmin() || !$iSessionTimeout )
00364             $iSessionTimeout = $this->getConfigParam( 'iSessionTimeout' );
00365         if (!$iSessionTimeout)
00366             $iSessionTimeout = 60;*/
00367 
00368         // ADODB cachelifetime
00369         $iDBCacheLifeTime = $this->getConfigParam( 'iDBCacheLifeTime' );
00370         if( !isset( $iDBCacheLifeTime ) )
00371             $this->setConfigParam( 'iDBCacheLifeTime', 3600 ); // 1 hour
00372 
00373         $sCoreDir = $this->getConfigParam( 'sShopDir' );
00374         $this->setConfigParam( 'sCoreDir', $sCoreDir.'/core/' );
00375 
00376         try {
00377             //starting up the session
00378             $this->getSession()->start();
00379 
00380             $sShopID = $this->getShopId();
00381 
00382             // load now
00383             $this->_loadVarsFromDb( $sShopID );
00384 
00385 
00386         } catch ( oxConnectionException $oEx ) {
00387             $oEx->debugOut();
00388             if ( defined( 'OXID_PHP_UNIT' ) ) {
00389                 return false;
00390             } elseif ( 0 != $this->iDebug ) {
00391                 oxUtils::getInstance()->showMessageAndExit( $oEx->getString() );
00392             } else {
00393                 header( "HTTP/1.1 500 Internal Server Error");
00394                 header( "Location: offline.html");
00395                 header( "Connection: close");
00396             }
00397         } catch ( oxCookieException $oEx ) {
00398             // redirect to start page and display the error
00399             oxUtilsView::getInstance()->addErrorToDisplay( $oEx );
00400             oxUtils::getInstance()->redirect( $this->getShopHomeURL() .'cl=start', true, 302 );
00401         }
00402 
00403         //application initialization
00404         $this->_oStart = new oxStart();
00405         $this->_oStart->appInit();
00406     }
00407 
00413     public static function getInstance()
00414     {
00415 
00416         if ( defined( 'OXID_PHP_UNIT' ) ) {
00417             if ( isset( modConfig::$unitMOD ) && is_object( modConfig::$unitMOD ) ) {
00418                 return modConfig::$unitMOD;
00419             }
00420         }
00421 
00422         if ( !self::$_instance instanceof oxConfig ) {
00423                 //exceptions from here go directly to global exception handler
00424                 //if no init is possible whole application has to die!
00425                 self::$_instance = new oxConfig();
00426                 self::$_instance->init();
00427         }
00428         return self::$_instance;
00429     }
00430 
00439     protected function _loadVarsFromDb( $sShopID, $aOnlyVars = null )
00440     {
00441 
00442         $sQ = "select oxvarname, oxvartype, DECODE( oxvarvalue, '".$this->getConfigParam( 'sConfigKey' )."') as oxvarvalue from oxconfig where oxshopid = '$sShopID'";
00443         // dodger, allow loading from some vars only from baseshop
00444         if ( $aOnlyVars !== null ) {
00445             $blSep = false;
00446             $sIn  = '';
00447             foreach ( $aOnlyVars as $sField ) {
00448                 if ( $blSep ) {
00449                     $sIn .= ', ';
00450                 }
00451                 $sIn .= '"'.$sField.'"';
00452                 $blSep = true;
00453             }
00454             $sQ .= ' and oxvarname in ( '.$sIn.' ) ';
00455         }
00456 
00457         $oRs = oxDb::getDb()->execute( $sQ );
00458         if ( $oRs != false && $oRs->recordCount() > 0 ) {
00459             while ( !$oRs->EOF ) {
00460                 $sVarName = $oRs->fields[0];
00461                 $sVarType = $oRs->fields[1];
00462                 $sVarVal  = $oRs->fields[2];
00463 
00464                 //in sShopURL and sSSLShopURL cases we skip (for admin or when URL values are not set)
00465                 if ( ( $sVarName == 'sShopURL' || $sVarName == 'sSSLShopURL' ) &&
00466                     ( !$sVarVal || $this->isAdmin() === true ) ) {
00467                     $oRs->moveNext();
00468                     continue;
00469                 }
00470 
00471                 switch ( $sVarType ) {
00472                     case 'arr':
00473                     case 'aarr':
00474                         $this->setConfigParam( $sVarName, unserialize( $sVarVal ) );
00475                         break;
00476                     case 'bool':
00477                         $this->setConfigParam( $sVarName, ( $sVarVal == 'true' || $sVarVal == '1' ) );
00478                         break;
00479                     default:
00480                         $this->setConfigParam( $sVarName, $sVarVal );
00481                         break;
00482                 }
00483 
00484                 $oRs->moveNext();
00485             }
00486         }
00487 
00488     }
00489 
00495     public function pageClose()
00496     {
00497         return $this->_oStart->pageClose();
00498     }
00499 
00513     public static function getParameter(  $sName, $blRaw = false )
00514     {
00515         if ( defined( 'OXID_PHP_UNIT' ) ) {
00516             if ( isset( modConfig::$unitMOD ) && is_object( modConfig::$unitMOD ) ) {
00517                 try{
00518                     return modConfig::getParameter(  $sName, $blRaw );
00519                 } catch( Exception $e ) {
00520                     // if exception is thrown, use default
00521                 }
00522             }
00523         }
00524 
00525         $sValue = null;
00526         if ( isset( $_SERVER['REQUEST_METHOD'] ) && $_SERVER['REQUEST_METHOD'] == 'POST' && isset( $_POST[$sName] ) ) {
00527             $sValue = $_POST[$sName];
00528         } elseif ( isset( $_SERVER['REQUEST_METHOD'] ) && $_SERVER['REQUEST_METHOD'] == 'GET' && isset( $_GET[$sName] ) ) {
00529             $sValue = $_GET[$sName];
00530             //<deprecated>
00531         } elseif ( oxSession::hasVar( $sName ) ) {
00532             $sValue = oxSession::getVar( $sName );
00533             //</deprecated>
00534         } else {
00535             $sValue = null;
00536         }
00537 
00538         // TODO: remove this after special charts concept implementation
00539         $blIsAdmin = oxConfig::getInstance()->isAdmin() && oxSession::getVar("blIsAdmin");
00540         if ( $sValue != null && !$blIsAdmin && (!$blRaw || is_array($blRaw))) {
00541             self::checkSpecialChars( $sValue, $blRaw );
00542         }
00543 
00544         return $sValue;
00545     }
00546 
00554     public function getUploadedFile($sParamName)
00555     {
00556         return $_FILES[$sParamName];
00557     }
00558 
00567     public function setGlobalParameter( $sName, $sValue )
00568     {
00569         $this->_aGlobalParams[$sName] = $sValue;
00570     }
00571 
00579     public function getGlobalParameter( $sName )
00580     {
00581         if ( isset( $this->_aGlobalParams[$sName] ) ) {
00582             return $this->_aGlobalParams[$sName];
00583         } else {
00584             return null;
00585         }
00586     }
00587 
00597     public static function checkSpecialChars( & $sValue, $aRaw = null )
00598     {
00599         if ( is_object( $sValue ) ) {
00600             return $sValue;
00601         }
00602 
00603         if ( is_array( $sValue ) ) {
00604             $newValue = array();
00605             foreach ( $sValue as $sKey => $sVal ) {
00606                 $sValidKey = $sKey;
00607                 if ( !$aRaw || !in_array($sKey, $aRaw) ) {
00608                     self::checkSpecialChars( $sValidKey );
00609                     self::checkSpecialChars( $sVal );
00610                     if ($sValidKey != $sKey) {
00611                         unset ($sValue[$sKey]);
00612                     }
00613                 }
00614                 $newValue[$sValidKey] = $sVal;
00615             }
00616             $sValue = $newValue;
00617         } else {
00618             $sValue = str_replace( array( '&',     '<',    '>',    '"',      "'",      chr(0), '\\' ),
00619                                    array( '&amp;', '&lt;', '&gt;', '&quot;', '&#039;', '',     '&#092;' ),
00620                                    $sValue );
00621         }
00622         return $sValue;
00623     }
00624 
00630     public function getShopId()
00631     {
00632         if ( $this->_iShopId !== null )
00633             return $this->_iShopId;
00634 
00635             $this->_iShopId = $this->getBaseShopId();
00636 
00637 
00638         oxSession::setVar( 'actshop', $this->_iShopId );
00639         return $this->_iShopId;
00640     }
00641 
00642 
00650     public function setShopId( $sShopId )
00651     {
00652         oxSession::setVar( 'actshop', $sShopId );
00653         $this->_iShopId = $sShopId;
00654     }
00655 
00656 
00662     public function isSsl()
00663     {
00664         if ( is_null( $this->_blIsSsl ) ) {
00665 
00666             $myUtilsServer   = oxUtilsServer::getInstance();
00667             $aServerVars     = $myUtilsServer->getServerVar();
00668             $aHttpsServerVar = $myUtilsServer->getServerVar( 'HTTPS' );
00669 
00670             $this->_blIsSsl = false;
00671             if (isset( $aHttpsServerVar ) && ($aHttpsServerVar === 'on' || $aHttpsServerVar == '1' )) {
00672                 // "1&1" hoster provides "1"
00673                 $this->_blIsSsl = ($this->getConfigParam('sSSLShopURL') || $this->getConfigParam('sMallSSLShopURL'));
00674                 if ($this->isAdmin() && !$this->_blIsSsl) {
00675                     $this->_blIsSsl = $this->getConfigParam('sAdminSSLURL');
00676                 }
00677             }
00678 
00679             //additional special handling for profihost customers
00680             if ( isset( $aServerVars['HTTP_X_FORWARDED_SERVER'] ) &&
00681                  ( strpos( $aServerVars['HTTP_X_FORWARDED_SERVER'], 'ssl' ) !== false ||
00682                  strpos( $aServerVars['HTTP_X_FORWARDED_SERVER'], 'secure-online-shopping.de' ) !== false ) ) {
00683                 $this->_blIsSsl = true;
00684             }
00685         }
00686 
00687         return $this->_blIsSsl;
00688     }
00689 
00697     public function isCurrentUrl( $sURL )
00698     {
00699         if ( !$sURL ) {
00700             return false;
00701         }
00702 
00703         $oUtilsServer = oxUtilsServer::getInstance();
00704         $sHost = $oUtilsServer->getServerVar( 'HTTP_HOST' );
00705         $sScriptName = $oUtilsServer->getServerVar( 'SCRIPT_NAME' );
00706 
00707         $sCurrentHost = preg_replace( '/\/\w*\.php.*/', '', $sHost . $sScriptName );
00708 
00709         //remove double slashes all the way
00710         $sCurrentHost = str_replace( '/', '', $sCurrentHost );
00711         $sURL = str_replace( '/', '', $sURL );
00712 
00713         //so far comparing for the host is enought for us
00714         if ( getStr()->strpos( $sURL, $sCurrentHost ) !== false ) {
00715             return true;
00716         }
00717 
00718         return false;
00719     }
00720 
00729     public function getShopUrl( $iLang = null, $blAdmin = null )
00730     {
00731         $blAdmin = isset( $blAdmin ) ? $blAdmin : $this->isAdmin();
00732         if ( $blAdmin ) {
00733             return $this->getConfigParam( 'sShopURL' );
00734         }
00735 
00736         // #680 per language another URL
00737         $iLang = isset( $iLang ) ? $iLang : oxLang::getInstance()->getBaseLanguage();
00738         $aLanguageURLs = $this->getConfigParam( 'aLanguageURLs' );
00739         if ( isset( $iLang ) && isset( $aLanguageURLs[$iLang] ) && !empty( $aLanguageURLs[$iLang] ) ) {
00740             $aLanguageURLs[$iLang] = oxUtils::getInstance()->checkUrlEndingSlash( $aLanguageURLs[$iLang] );
00741             return $aLanguageURLs[$iLang];
00742         }
00743 
00744         //normal section
00745         $sMallShopURL = $this->getConfigParam( 'sMallShopURL' );
00746         if ( $sMallShopURL ) {
00747             $sMallShopURL = oxUtils::getInstance()->checkUrlEndingSlash( $sMallShopURL );
00748             return $sMallShopURL;
00749         }
00750 
00751         return $this->getConfigParam( 'sShopURL' );
00752     }
00753 
00761     public function getSslShopUrl( $iLang = null )
00762     {
00763         // #680 per language another URL
00764         $iLang = isset( $iLang ) ? $iLang : oxLang::getInstance()->getBaseLanguage();
00765         $aLanguageSSLURLs = $this->getConfigParam( 'aLanguageSSLURLs' );
00766         if ( isset( $iLang ) && isset( $aLanguageSSLURLs[$iLang] ) && !empty( $aLanguageSSLURLs[$iLang] ) ) {
00767             $aLanguageSSLURLs[$iLang] = oxUtils::getInstance()->checkUrlEndingSlash( $aLanguageSSLURLs[$iLang] );
00768             return $aLanguageSSLURLs[$iLang];
00769         }
00770 
00771         //mall mode
00772         if ( ( $sMallSSLShopURL = $this->getConfigParam( 'sMallSSLShopURL' ) ) ) {
00773             $sMallSSLShopURL = oxUtils::getInstance()->checkUrlEndingSlash( $sMallSSLShopURL );
00774             return $sMallSSLShopURL;
00775         }
00776 
00777         if ( ( $sMallShopURL = $this->getConfigParam( 'sMallShopURL' ) ) ) {
00778             $sMallShopURL = oxUtils::getInstance()->checkUrlEndingSlash( $sMallShopURL );
00779             return $sMallShopURL;
00780         }
00781 
00782         //normal section
00783         if ( ( $sSSLShopURL = $this->getConfigParam( 'sSSLShopURL' ) ) ) {
00784             return $sSSLShopURL;
00785         }
00786 
00787         return $this->getShopUrl( $iLang );
00788     }
00789 
00795     public function getCoreUtilsUrl()
00796     {
00797         return $this->getCurrentShopUrl().'core/utils/';
00798     }
00799 
00808     public function getCurrentShopUrl($blAdmin = null)
00809     {
00810         if ($blAdmin===null) {
00811             $blAdmin = $this->isAdmin();
00812         }
00813         if ($blAdmin) {
00814             if ($this->isSsl()) {
00815 
00816                 $sUrl = $this->getConfigParam( 'sAdminSSLURL' );
00817                 if ( !$sUrl ) {
00818                     return $this->getSslShopUrl() . $this->getConfigParam( 'sAdminDir' ) . '/';
00819                 }
00820                 return $sUrl;
00821             } else {
00822                 return $this->getShopUrl() . $this->getConfigParam( 'sAdminDir' ) . '/';
00823             }
00824         } else {
00825             return $this->isSsl() ? $this->getSslShopUrl() : $this->getShopUrl();
00826         }
00827     }
00828 
00836     public function getShopCurrentUrl( $iLang = null )
00837     {
00838         if ( $this->isSsl() ) {
00839             $sURL = $this->getSSLShopURL( $iLang );
00840         } else {
00841             $sURL = $this->getShopURL( $iLang );
00842         }
00843 
00844         return oxUtilsUrl::getInstance()->processUrl( $sURL.'index.php', false );
00845     }
00846 
00855     public function getShopHomeUrl( $iLang = null, $blAdmin = null )
00856     {
00857         return oxUtilsUrl::getInstance()->processUrl($this->getShopUrl( $iLang, $blAdmin).'index.php', false );
00858     }
00859 
00865     public function getShopSecureHomeUrl()
00866     {
00867         return  oxUtilsUrl::getInstance()->processUrl( $this->getSslShopUrl().'index.php', false );
00868     }
00869 
00875     public function getShopCurrency()
00876     {
00877         return (int) oxConfig::getParameter( 'currency' );
00878     }
00879 
00885     public function getActShopCurrencyObject()
00886     {
00887         //caching currency as it does not change through the script
00888         //but not for unit tests as ther it changes always
00889         if ( !defined( 'OXID_PHP_UNIT' ) ) {
00890             if (!is_null($this->_oActCurrencyObject)) {
00891                 return $this->_oActCurrencyObject;
00892             }
00893         }
00894 
00895         $iCur = oxConfig::getParameter( 'cur' );
00896         if ( !isset( $iCur ) ) {
00897             $iCur = $this->getShopCurrency();
00898         }
00899 
00900         $aCurrencies = $this->getCurrencyArray();
00901         if ( !isset( $aCurrencies[$iCur] ) ) {
00902             return $this->_oActCurrencyObject = reset( $aCurrencies ); // reset() returns the first element
00903         }
00904 
00905         return $this->_oActCurrencyObject = $aCurrencies[$iCur];
00906     }
00907 
00915     public function setActShopCurrency( $iCur )
00916     {
00917         $aCurrencies = $this->getCurrencyArray();
00918         if ( isset( $aCurrencies[$iCur] ) ) {
00919             oxSession::setVar( 'currency', $iCur );
00920             $this->_oActCurrencyObject = null;
00921         }
00922     }
00923 
00924 
00934     public function getNoSslImageDir( $blAdmin = false )
00935     {
00936         return $this->getImageUrl( $blAdmin, false );
00937     }
00938 
00946     public function getAbsAdminImageDir()
00947     {
00948         return $this->getImageDir( true );
00949 
00950     }
00951 
00966     /* is not used
00967     public function formatOutDir($sFile, $iLang = null, $blAdmin = false, $blNoThemes = false, $iShop = null)
00968     {
00969         //resolving theme and shop dir
00970         $sThemeDir  = ($blNoThemes || $blAdmin) ? "" : $this->getConfigParam( 'sTheme' );
00971 
00972         if (is_null($iShop))
00973             $iShop = $this->getShopId();
00974 
00975         $aShopDirs = array();
00976 
00977 
00978         if ($sThemeDir)
00979             $aShopDirs[] = "$sThemeDir/1/";
00980         else
00981             $aShopDirs[] = $this->getBaseShopId() . "/";
00982 
00983         //admin dir
00984         if ( $blAdmin ) {
00985             $aShopDirs = array('admin/');
00986         }
00987 
00988         if ($sFile) {
00989             //language dir
00990             if (is_null($iLang))
00991                 $iLang = oxLang::getInstance()->getBaseLanguage();
00992 
00993             $aLangs    = oxLang::getInstance()->getLanguageArray();
00994             //specific language dir and top dir
00995             $aLangDirs = array();
00996             if (isset($aLangs[$iLang]))
00997                 $aLangDirs[] = strtolower($aLangs[$iLang]->abbr . "/");
00998             $aLangDirs[] = "";
00999 
01000 
01001             //finally checking dir
01002             foreach ($aShopDirs as $sShopDir) {
01003                 foreach ($aLangDirs as $sLangDir) {
01004                     $sOut = "out/" . $sShopDir . $sLangDir . $sFile;
01005                     if (file_exists($this->getConfigParam('sShopDir'). $sOut))
01006                         return $sOut;
01007                 }
01008             }
01009         }
01010 
01011         //not language specific default dir
01012         foreach ($aShopDirs as $sShopDir) {
01013             $sOut = "out/" . $sShopDir;
01014             if (file_exists($this->getConfigParam('sShopDir'). $sOut))
01015                 return $sOut;
01016         }
01017     }*/
01018 
01026     public function getOutDir( $blAbsolute = true)
01027     {
01028         if ($blAbsolute) {
01029             return $this->getConfigParam('sShopDir').$this->_sOutDir.'/';
01030         } else {
01031             return $this->_sOutDir.'/';
01032         }
01033     }
01034 
01044     public function getOutUrl( $blSSL = null , $blAdmin = null, $blNativeImg = false )
01045     {
01046         $blSSL    = is_null($blSSL)?$this->isSsl():$blSSL;
01047         $blAdmin  = is_null($blAdmin)?$this->isAdmin():$blAdmin;
01048 
01049         if ( $blSSL ) {
01050             if ($blNativeImg && !$blAdmin) {
01051                 $sUrl = $this->getSslShopUrl();
01052             } else {
01053                 $sUrl = $this->getConfigParam('sSSLShopURL');
01054                 if (!$sUrl && $blAdmin) {
01055                     $sUrl = $this->getConfigParam('sAdminSSLURL').'../';
01056                 }
01057             }
01058         } else {
01059             $sUrl = ($blNativeImg && !$blAdmin )?$this->getShopUrl():$this->getConfigParam( 'sShopURL' );
01060         }
01061 
01062         return $sUrl.$this->_sOutDir.'/';
01063     }
01064 
01079     public function getDir($sFile, $sDir, $blAdmin, $iLang = null, $iShop = null, $sTheme = null, $blAbsolute = true, $blIgnoreCust = false )
01080     {
01081         if ( is_null($sTheme) ) {
01082             $sTheme = $this->getConfigParam( 'sTheme' );
01083         }
01084 
01085         if ( $blAdmin ) {
01086             $sTheme = 'admin';
01087         }
01088 
01089         $sBase    = $this->getOutDir( $blAbsolute );
01090         $sAbsBase = $this->getOutDir();
01091 
01092         $sLang = '-';
01093         // FALSE means skip language folder check
01094         if ( $iLang !== false ) {
01095             $oLang = oxLang::getInstance();
01096 
01097             if ( is_null( $iLang ) ) {
01098                 $iLang = $oLang->getEditLanguage();
01099             }
01100 
01101             $sLang = $oLang->getLanguageAbbr( $iLang );
01102         }
01103 
01104         if ( is_null($iShop) ) {
01105             $iShop = $this->getShopId();
01106         }
01107 
01108         //Load from
01109         $sPath = "{$sTheme}/{$iShop}/{$sLang}/{$sDir}/{$sFile}";
01110         $sCacheKey = $sPath . "_{$blIgnoreCust}{$blAbsolute}";
01111 
01112         if ( ( $sReturn = oxutils::getInstance()->fromStaticCache( $sCacheKey ) ) !== null ) {
01113             return $sReturn;
01114         }
01115 
01116         $sReturn = false;
01117 
01118         // Check for custom template
01119         $sCustomTheme = $this->getConfigParam( 'sCustomTheme' );
01120         if ( !$blAdmin && !$blIgnoreCust && $sCustomTheme && $sCustomTheme != $sTheme) {
01121             $sReturn = $this->getDir( $sFile, $sDir, $blAdmin, $iLang, $iShop, $sCustomTheme, $blAbsolute );
01122         }
01123 
01124         //test lang level ..
01125         if ( !$sReturn && !$blAdmin && is_readable( $sAbsBase.$sPath ) ) {
01126             $sReturn = $sBase . $sPath;
01127         }
01128 
01129         //test shop level ..
01130         $sPath = "$sTheme/$iShop/$sDir/$sFile";
01131         if ( !$sReturn && !$blAdmin && is_readable( $sAbsBase.$sPath ) ) {
01132             $sReturn = $sBase . $sPath;
01133         }
01134 
01135 
01136         //test theme language level ..
01137         $sPath = "$sTheme/$sLang/$sDir/$sFile";
01138         if ( !$sReturn && $iLang !== false && is_readable( $sAbsBase.$sPath ) ) {
01139             $sReturn = $sBase . $sPath;
01140         }
01141 
01142         //test theme level ..
01143         $sPath = "$sTheme/$sDir/$sFile";
01144         if ( !$sReturn && is_readable( $sAbsBase.$sPath ) ) {
01145             $sReturn = $sBase . $sPath;
01146         }
01147 
01148         //test out language level ..
01149         $sPath = "$sLang/$sDir/$sFile";
01150         if ( !$sReturn &&  $iLang !== false && is_readable( $sAbsBase.$sPath ) ) {
01151             $sReturn = $sBase . $sPath;
01152         }
01153 
01154         //test out level ..
01155         $sPath = "$sDir/$sFile";
01156         if ( !$sReturn && is_readable( $sAbsBase.$sPath ) ) {
01157             $sReturn = $sBase . $sPath;
01158         }
01159 
01160         if ( !$sReturn ) {
01161             // TODO: implement logic to log missing paths
01162         }
01163 
01164         // to cache
01165         oxutils::getInstance()->toStaticCache( $sCacheKey, $sReturn );
01166 
01167         return $sReturn;
01168     }
01169 
01184     public function getUrl($sFile, $sDir , $blAdmin = null, $blSSL = null, $blNativeImg = false, $iLang = null , $iShop = null , $sTheme = null )
01185     {
01186         $sUrl = str_replace(
01187                                 $this->getOutDir(),
01188                                 $this->getOutUrl($blSSL, $blAdmin, $blNativeImg),
01189                                 $this->getDir( $sFile, $sDir, $blAdmin, $iLang, $iShop, $sTheme )
01190                             );
01191         return $sUrl;
01192     }
01193 
01202     public function getImagePath( $sFile, $blAdmin = false )
01203     {
01204         return $this->getDir( $sFile, $this->_sImageDir, $blAdmin );
01205     }
01206 
01216     public function getImageUrl( $blAdmin = false, $blSSL = null, $blNativeImg = null )
01217     {
01218         $blNativeImg = is_null($blNativeImg)?$this->getConfigParam( 'blNativeImages' ):$blNativeImg;
01219         return $this->getUrl( null, $this->_sImageDir, $blAdmin, $blSSL, $blNativeImg );
01220     }
01221 
01229     public function getImageDir( $blAdmin = false )
01230     {
01231         return $this->getDir( null, $this->_sImageDir, $blAdmin );
01232     }
01233 
01242     public function getPicturePath($sFile, $blAdmin = false )
01243     {
01244         return $this->getDir( $sFile, $this->_sPictureDir, $blAdmin );
01245     }
01246 
01254     public function getMasterPictureDir( $blAdmin = false )
01255     {
01256         return $this->getDir( null, $this->_sPictureDir . "/" . $this->_sMasterPictureDir, $blAdmin );
01257     }
01258 
01267     public function getMasterPicturePath( $sFile, $blAdmin = false )
01268     {
01269         return $this->getDir( $sFile, $this->_sPictureDir . "/" . $this->_sMasterPictureDir, $blAdmin );
01270     }
01271 
01284     public function getPictureUrl( $sFile, $blAdmin = false, $blSSL = null, $iLang = null, $iShopId = null, $sDefPic = "0/nopic.jpg" )
01285     {
01286         if ( $sAltUrl = $this->getConfigParam( 'sAltImageDir' ) ) {
01287 
01288             if ( $this->isSsl() && $blSSL && $sSslAltUrl = $this->getConfigParam( 'sSSLAltImageDir' ) ) {
01289                 $sAltUrl = $sSslAltUrl;
01290             }
01291 
01292             if ( !is_null( $sFile ) ) {
01293                 $sAltUrl .= $sFile;
01294             }
01295 
01296             return $sAltUrl;
01297         }
01298 
01299         $blNativeImg = $this->getConfigParam( 'blNativeImages' );
01300 
01301         $sUrl = $this->getUrl( $sFile, $this->_sPictureDir, $blAdmin, $blSSL, $blNativeImg, $iLang, $iShopId );
01302         if ( $sFile && $this->getConfigParam( 'blFormerTplSupport' ) && !$blAdmin ) {
01303             $sUrl = str_replace( $this->getPictureUrl( null, $blAdmin, $blSSL, $iLang, $iShopId ), '', $sUrl );
01304         }
01305 
01306         //anything is better than empty name, because <img src=""> calls shop once more = x2 SLOW.
01307         if ( !$sUrl ) {
01308             $sUrl = $this->getUrl( $sDefPic, $this->_sPictureDir, $blAdmin, $blSSL, $blNativeImg, $iLang, $iShopId );
01309         }
01310         return $sUrl;
01311     }
01312 
01325     public function getIconUrl( $sFile, $blAdmin = false , $blSSL = null , $iLang = null, $iShopId = null, $sDefPic = "icon/nopic_ico.jpg" )
01326     {
01327         return $this->getPictureUrl( $sFile, $blAdmin, $blSSL, $iLang, $iShopId, $sDefPic );
01328     }
01329 
01337     public function getPictureDir( $blAdmin )
01338     {
01339         return $this->getDir( null, $this->_sPictureDir, $blAdmin );
01340     }
01341 
01350     public function getTemplatePath( $sFile, $blAdmin )
01351     {
01352         return $this->getDir( $sFile, $this->_sTemplateDir, $blAdmin );
01353     }
01354 
01362     public function getTemplateDir( $blAdmin = false )
01363     {
01364         return $this->getDir( null, $this->_sTemplateDir, $blAdmin );
01365     }
01366 
01377     public function getTemplateUrl( $sFile = null, $blAdmin = false, $blSSL = null , $iLang = null )
01378     {
01379         return $this->getUrl( $sFile, $this->_sTemplateDir, $blAdmin, $blSSL, false, $iLang );
01380     }
01381 
01389     public function getTemplateBase( $blAdmin = false )
01390     {
01391         // Base template dir is the parent dir of template dir
01392         return str_replace( $this->_sTemplateDir.'/', '', $this->getDir( null, $this->_sTemplateDir, $blAdmin, null, null, null, false ));
01393     }
01394 
01403     public function getResourcePath($sFile, $blAdmin = false )
01404     {
01405         return $this->getDir( $sFile, $this->_sResourceDir, $blAdmin );
01406     }
01407 
01418     public function getResourceUrl( $sFile, $blAdmin = false , $blSSL = null , $iLang = null )
01419     {
01420         $blNativeImg = $this->getConfigParam( 'blNativeImages' );
01421         return $this->getUrl( $sFile, $this->_sResourceDir, $blAdmin, $blSSL, $blNativeImg, $iLang );
01422     }
01423 
01431     public function getResourceDir( $blAdmin )
01432     {
01433         return $this->getDir( null, $this->_sResourceDir, $blAdmin );
01434     }
01435 
01445     public function getLanguagePath( $sFile, $blAdmin, $iLang = null )
01446     {
01447         return $this->getDir( $sFile, oxLang::getInstance()->getLanguageAbbr( $iLang ), $blAdmin, $iLang );
01448     }
01449 
01459     public function getStdLanguagePath( $sFile, $blAdmin, $iLang = null )
01460     {
01461         $sDir = null;
01462         if ( $iLang !== false ) {
01463             $sDir = oxLang::getInstance()->getLanguageAbbr( $iLang );
01464         }
01465 
01466         return $this->getDir( $sFile, $sDir, $blAdmin, $iLang, null, $this->getConfigParam( "sTheme" ), true, true );
01467     }
01468 
01476     public function getLanguageDir( $blAdmin )
01477     {
01478         return $this->getDir( null, null, $blAdmin );
01479     }
01480 
01488     public function getAbsImageDir()
01489     {
01490         return $this->getImageDir();
01491     }
01492 
01503     public function getDynImageDir( $sOverrideShopId = null, $blNoSsl = null )
01504     {
01505         return $this->getPictureUrl(null, false, $this->isSsl() && !$blNoSsl, null, $sOverrideShopId);
01506 
01507         /*
01508 
01509         $sCacheKey = "getDynImageDir_" . $this->isSsl() . "_" . $this->getShopId() . "_" .oxLang::getInstance()->getTplLanguage() . "_" . $sOverrideShopId . "_" . $blNoSsl;
01510         $sImageDir = oxUtils::getInstance()->fromStaticCache($sCacheKey);
01511 
01512         if ($sImageDir)
01513             return $sImageDir;
01514 
01515         if ( $sAltImageDir = $this->getConfigParam( 'sAltImageDir' ) ) {
01516             if ( $this->isSsl() ) {
01517                 $sAltImageDir = str_replace( 'http://', 'https://', $sAltImageDir );
01518             }
01519             oxUtils::getInstance()->toStaticCache($sCacheKey, $sAltImageDir);
01520             return $sAltImageDir;
01521         }
01522 
01523         //Tomas 2005-01-19
01524         //now it loads images only from either active shop either from oxbaseshop
01525         //later to be fixed to load images from any shop according $sOverrideShopId by implementing
01526         //function oxConfig::getShopURL($sOverrideShopId);
01527 
01528         $blNativeImg = $this->getConfigParam( 'blNativeImages' ) && $sOverrideShopId == $this->getShopId();
01529 
01530         if ( $this->isSsl() && !$blNoSsl ) {
01531             $sUrl = $blNativeImg ? $this->getSSLShopURL():$this->getConfigParam( 'sSSLShopURL');
01532         }
01533 
01534         if(!$sUrl) {
01535             $sUrl = $blNativeImg ? $this->getShopURL():$this->getConfigParam( 'sShopURL' );
01536         }
01537 
01538         $sLang = $this->getConfigParam( 'blUseDifferentDynDirs' )?oxLang::getInstance()->getTplLanguage():0;
01539         $sDir  = $this->_sPictureDir;
01540 
01541         $sImageDir = $sUrl . $this->formatOutDir($sDir, $iLang, false, true, $sOverrideShopId);
01542 
01543         oxUtils::getInstance()->toStaticCache($sCacheKey, $sImageDir);
01544 
01545 
01546         return $sImageDir;
01547         */
01548     }
01549 
01559     public function getAbsDynImageDir( $sOverrideShopId = null )
01560     {
01561         return $this->getPictureDir(false);
01562 
01563         /*
01564         //$sShop = is_null($sOverrideShopId)?$this->getShopId():$sOverrideShopId;
01565 
01566         if (isset($this->_aAbsDynImageDir[$sShop]))
01567             return $this->_aAbsDynImageDir[$sShop];
01568 
01569         $sRoot = $this->getConfigParam('sShopDir');
01570         $iLang = $this->getConfigParam( 'blUseDifferentDynDirs' )?oxLang::getInstance()->getTplLanguage():0;
01571         $sDir  = $this->_sPictureDir;
01572 
01573         $this->_aAbsDynImageDir[$sShop] = $sRoot . $this->formatOutDir($sDir, $iLang, false, true, $sOverrideShopId);
01574         return $this->_aAbsDynImageDir[$sShop];
01575         */
01576     }
01577 
01588     public function getTemplateFile( $sTemplate, $blAdmin = false )
01589     {
01590         return $this->getTemplatePath( $sTemplate, $blAdmin );
01591     }
01592 
01602     public function getBaseTemplateDir( $blAdmin = false )
01603     {
01604         return $this->getResourceUrl( null, $blAdmin );
01605         /*
01606         $blNativeImg = $this->getConfigParam( 'blNativeImages' ) && !$blAdmin;
01607 
01608         if ( $this->isSsl() ) {
01609             $sTemplateUrl = $blNativeImg?$this->getSSLShopURL():$this->getConfigParam( 'sSSLShopURL' );
01610         } else {
01611             $sTemplateUrl = $blNativeImg?$this->getShopURL():$this->getConfigParam( 'sShopURL' );
01612         }
01613 
01614         return $this->getResourceUrl( null, $blAdmin, $this->isSsl() );
01615         */
01616     }
01617 
01627     public function getBaseTplDir( $blAdmin = false )
01628     {
01629         //TODO: check usage
01630         return $this->getResourceUrl( null, $blAdmin);
01631     }
01632 
01640     public function getCurrencyArray( $iCurrency = null )
01641     {
01642         $aConfCurrencies = $this->getConfigParam( 'aCurrencies' );
01643         if ( !is_array( $aConfCurrencies ) ) {
01644             return array();
01645         }
01646 
01647         if ( defined( 'OXID_PHP_UNIT' ) ) {
01648             if ( isset( modConfig::$unitMOD ) && is_object( modConfig::$unitMOD ) ) {
01649                 try{
01650                     $aAltCurrencies = modConfig::getInstance()->getConfigParam( 'modaCurrencies' );
01651                     if ( isset( $aAltCurrencies ) ) {
01652                         $aConfCurrencies = $aAltCurrencies;
01653                     }
01654                 } catch( Exception $e ) {
01655                     // if exception is thrown, use default
01656                 }
01657             }
01658         }
01659 
01660         // processing currency configuration data
01661         $aCurrencies = array();
01662         reset( $aConfCurrencies );
01663         while ( list( $key, $val ) = each( $aConfCurrencies ) ) {
01664             if ( $val ) {
01665                 $oCur = new oxStdClass();
01666                 $oCur->id      = $key;
01667                 $sCur = explode( '@', $val);
01668                 $oCur->name     = trim( $sCur[0] );
01669                 $oCur->rate     = trim( $sCur[1] );
01670                 $oCur->dec      = trim( $sCur[2] );
01671                 $oCur->thousand = trim( $sCur[3] );
01672                 $oCur->sign     = trim( $sCur[4] );
01673                 $oCur->decimal  = trim( $sCur[5] );
01674 
01675                 // change for US version
01676                 if ( isset( $sCur[6] ) ) {
01677                     $oCur->side = trim($sCur[6]);
01678                 }
01679 
01680                 if ( isset( $iCurrency) && $key == $iCurrency ) {
01681                     $oCur->selected = 1;
01682                 } else {
01683                     $oCur->selected = 0;
01684                 }
01685                 $aCurrencies[$key]= $oCur;
01686             }
01687 
01688             // #861C -  performance, do not load other currencies
01689             if ( !$this->getConfigParam( 'bl_perfLoadCurrency' ) ) {
01690                 break;
01691             }
01692         }
01693         return $aCurrencies;
01694     }
01695 
01703     public function getCurrencyObject( $sName )
01704     {
01705         $aSearch = $this->getCurrencyArray();
01706         foreach ( $aSearch as $oCur ) {
01707             if ( $oCur->name == $sName ) {
01708                 return $oCur;
01709             }
01710         }
01711     }
01712 
01718     public function isDemoShop()
01719     {
01720         return $this->getConfigParam('blDemoShop');
01721     }
01722 
01728     public function getEdition()
01729     {
01730             return "CE";
01731 
01732 
01733     }
01734 
01740     public function getFullEdition()
01741     {
01742         $sEdition = $this->getEdition();
01743 
01744             if ($sEdition == "CE") {
01745                 return "Community Edition";
01746             }
01747 
01748 
01749 
01750         return $sEdition;
01751     }
01752 
01758     public function getVersion()
01759     {
01760         $sVersion = $this->getActiveShop()->oxshops__oxversion->value;
01761         return $sVersion;
01762     }
01763 
01769     public function getRevision()
01770     {
01771         try {
01772             $sFileName = getShopBasePath() . "/pkg.rev";
01773             $iRev = (int) trim(@file_get_contents($sFileName));
01774         } catch (Exception $e) {
01775             return false;
01776         }
01777 
01778         if (!$iRev) {
01779             return false;
01780         }
01781 
01782         return $iRev;
01783     }
01784 
01785 
01791     public function isMall()
01792     {
01793 
01794             return false;
01795     }
01796 
01806     public function detectVersion()
01807     {
01808     }
01809 
01810 
01811 
01823     public function saveShopConfVar( $sVarType, $sVarName, $sVarVal, $sShopId = null )
01824     {
01825         switch ( $sVarType ) {
01826             case 'arr':
01827             case 'aarr':
01828                 if (is_array($sVarVal)) {
01829                     $sValue = serialize( $sVarVal );
01830                 } else {
01831                     // Deprecated functionality
01832                     $sValue  = $sVarVal ;
01833                     $sVarVal = unserialize( $sVarVal );
01834                 }
01835                 break;
01836             case 'bool':
01837                 //config param
01838                 $sVarVal = (( $sVarVal == 'true' || $sVarVal) && $sVarVal && strcasecmp($sVarVal, "false"));
01839                 //db value
01840                 $sValue  = $sVarVal?"1":"";
01841                 break;
01842             default:
01843                 $sValue  = $sVarVal;
01844                 break;
01845         }
01846 
01847         if ( !$sShopId ) {
01848             $sShopId = $this->getShopId();
01849         }
01850 
01851         // Update value only for current shop
01852         if ($sShopId == $this->getShopId()) {
01853             $this->setConfigParam( $sVarName, $sVarVal );
01854         }
01855 
01856         $oDb = oxDb::getDb();
01857         $sQ = "delete from oxconfig where oxshopid = '$sShopId' and oxvarname = '$sVarName'";
01858         $oDb->execute( $sQ );
01859 
01860         $sNewOXIDdQuoted  = $oDb->quote(oxUtilsObject::getInstance()->generateUID());
01861         $sShopIdQuoted    = $oDb->quote($sShopId);
01862         $sVarNameQuoted   = $oDb->quote($sVarName);
01863         $sVarTypeQuoted   = $oDb->quote($sVarType);
01864         $sVarValueQuoted  = $oDb->quote($sValue);
01865         $sConfigKeyQuoted = $oDb->quote($this->getConfigParam('sConfigKey'));
01866 
01867         $sQ = "insert into oxconfig (oxid, oxshopid, oxvarname, oxvartype, oxvarvalue)
01868                values($sNewOXIDdQuoted, $sShopIdQuoted, $sVarNameQuoted, $sVarTypeQuoted, ENCODE( $sVarValueQuoted, $sConfigKeyQuoted))";
01869 
01870         $oDb->execute( $sQ );
01871     }
01872 
01881     public function getShopConfVar( $sVarName, $sShopId = null )
01882     {
01883         if ( !$sShopId ) {
01884             $sShopId = $this->getShopId();
01885         }
01886 
01887         $oDb = oxDb::getDb(true);
01888         $sQ  = "select oxvartype, DECODE( oxvarvalue, '".$this->getConfigParam( 'sConfigKey' )."') as oxvarvalue from oxconfig where oxshopid = '$sShopId' and oxvarname = ".$oDb->quote($sVarName);
01889         $oRs = $oDb->Execute( $sQ );
01890 
01891         $sValue = null;
01892         if ( $oRs != false && $oRs->recordCount() > 0 ) {
01893             $sVarType = $oRs->fields['oxvartype'];
01894             $sVarVal  = $oRs->fields['oxvarvalue'];
01895             switch ( $sVarType ) {
01896                 case 'arr':
01897                 case 'aarr':
01898                     $sValue =  unserialize( $sVarVal );
01899                     break;
01900                 case 'bool':
01901                     $sValue =  ( $sVarVal == 'true' || $sVarVal == '1' );
01902                     break;
01903                 default:
01904                     $sValue = $sVarVal;
01905                     break;
01906             }
01907         }
01908         return $sValue;
01909     }
01910 
01916     public function isProductiveMode()
01917     {
01918         $blProductive = false;
01919 
01920         $blProductive = $this->getConfigParam( 'blProductive' );
01921         if ( !isset( $blProductive ) ) {
01922             $sQ = 'select oxproductive from oxshops where oxid = "'.$this->getShopId().'"';
01923             $blProductive = ( bool ) oxDb::getDb()->getOne( $sQ );
01924             $this->setConfigParam( 'blProductive', $blProductive );
01925         }
01926 
01927         return $blProductive;
01928     }
01929 
01930 
01931 
01937     public function getBaseShopId()
01938     {
01939 
01940             return 'oxbaseshop';
01941     }
01942 
01948     public function getActiveShop()
01949     {
01950         if ( $this->_oActShop && $this->_iShopId == $this->_oActShop->getId() &&
01951              $this->_oActShop->getLanguage() == oxLang::getInstance()->getBaseLanguage() ) {
01952             return $this->_oActShop;
01953         }
01954 
01955         $this->_oActShop = oxNew( 'oxshop' );
01956         $this->_oActShop->load( $this->getShopId() );
01957         return $this->_oActShop;
01958     }
01959 
01965     public function getActiveView()
01966     {
01967         if ( $this->_oActView != null ) {
01968             return $this->_oActView;
01969         }
01970 
01971         $this->_oActView = oxNew( 'oxubase' );
01972         return $this->_oActView;
01973     }
01974 
01982     public function setActiveView( $oView )
01983     {
01984         $this->_oActView = $oView;
01985     }
01986 
01992     public function isUtf()
01993     {
01994         return ( bool ) $this->getConfigParam( 'iUtfMode' );
01995     }
01996 
02002     public function getLogsDir()
02003     {
02004         return $this->getConfigParam( 'sShopDir' ).'log/';
02005     }
02006 }