public static function OnMetaModelStarted() { try { $oBackupMutex = new iTopMutex('backup.' . utils::GetCurrentEnvironment()); if ($oBackupMutex->TryLock()) { $oBackupMutex->Unlock(); } else { // Not needed: the DB dump is done in a single transaction //MetaModel::GetConfig()->Set('access_mode', ACCESS_READONLY, 'itop-backup'); //MetaModel::GetConfig()->Set('access_message', ' - '.dict::S('bkp-backup-running'), 'itop-backup'); } $oRestoreMutex = new iTopMutex('restore.' . utils::GetCurrentEnvironment()); if ($oRestoreMutex->TryLock()) { $oRestoreMutex->Unlock(); } else { IssueLog::Info(__CLASS__ . '::' . __FUNCTION__ . ' A user is trying to use iTop while a restore is running. The requested page is in read-only mode.'); MetaModel::GetConfig()->Set('access_mode', ACCESS_READONLY, 'itop-backup'); MetaModel::GetConfig()->Set('access_message', ' - ' . dict::S('bkp-restore-running'), 'itop-backup'); } } catch (Exception $e) { IssueLog::Error(__CLASS__ . '::' . __FUNCTION__ . ' Failed to check if a backup/restore is running: ' . $e->getMessage()); } }
/** * @return boolean True if the task record can be deleted */ public function Process() { // By default: consider that the task is not completed $bRet = false; // Attempt to take the ownership $iStatus = $this->MarkAsRunning(); if ($iStatus == self::OK) { try { $sStatus = $this->DoProcess(); if ($this->Get('event_id') != 0) { $oEventLog = MetaModel::GetObject('Event', $this->Get('event_id')); $oEventLog->Set('message', $sStatus); $oEventLog->DBUpdate(); } $bRet = true; } catch (Exception $e) { $iRemaining = $this->Get('remaining_retries'); if ($iRemaining > 0) { $iRetryDelay = $this->GetRetryDelay(); IssueLog::Info('Failed to process async task #' . $this->GetKey() . ' - reason: ' . $e->getMessage() . ' - remaining retries: ' . $iRemaining . ' - next retry in ' . $iRetryDelay . 's'); $this->Set('remaining_retries', $iRemaining - 1); $this->Set('status', 'planned'); $this->Set('started', null); $this->Set('planned', time() + $iRetryDelay); $this->DBUpdate(); } else { IssueLog::Error('Failed to process async task #' . $this->GetKey() . ' - reason: ' . $e->getMessage()); } } } else { // Already done or being handled by another process... skip... $bRet = false; } return $bRet; }
break; case 'xml': default: $oPage->SetContentType('text/xml'); $oObj = MetaModel::GetObject($sClass, $id, true); // Build the root XML part $oXmlDoc = new DOMDocument('1.0', 'UTF-8'); $oXmlRoot = $oXmlDoc->CreateElement('root'); $oXmlNode = $oXmlDoc->CreateElement('node'); $oXmlNode->SetAttribute('id', $oObj->GetKey()); $oXmlNode->SetAttribute('obj_class', get_class($oObj)); $oXmlNode->SetAttribute('obj_class_name', htmlspecialchars(MetaModel::GetName(get_class($oObj)))); $oXmlNode->SetAttribute('name', htmlspecialchars($oObj->GetRawName())); $oXmlNode->SetAttribute('icon', BuildIconPath($oObj->GetIcon(false))); // Hard coded for the moment AddNodeDetails($oXmlNode, $oObj); $oLinks = $oXmlDoc->CreateElement("links"); $oXmlRoot->SetAttribute('position', 'left'); $oXmlRoot->SetAttribute('title', MetaModel::GetRelationDescription($sRelation) . ' ' . htmlspecialchars($oObj->GetRawName())); IssueLog::Info(__FUNCTION__ . " Rel: {$sRelation}"); GetRelatedObjectsAsXml($oObj, $sRelation, $oLinks, $oXmlDoc, $oXmlNode, 0, $aExcludedClasses); $oXmlRoot->AppendChild($oXmlNode); $oXmlDoc->AppendChild($oXmlRoot); $oPage->add($oXmlDoc->SaveXML()); break; } } $oPage->output(); } catch (Exception $e) { echo "Error: " . $e->getMessage(); }
/** * @param hash $aOrderBy Array of '[<classalias>.]attcode' => bAscending */ public function MakeSelectQuery($aOrderBy = array(), $aArgs = array(), $aAttToLoad = null, $aExtendedDataSpec = null, $iLimitCount = 0, $iLimitStart = 0, $bGetCount = false) { // Check the order by specification, and prefix with the class alias // and make sure that the ordering columns are going to be selected // $sClass = $this->GetClass(); $sClassAlias = $this->GetClassAlias(); $aOrderSpec = array(); foreach ($aOrderBy as $sFieldAlias => $bAscending) { if (!is_bool($bAscending)) { throw new CoreException("Wrong direction in ORDER BY spec, found '{$bAscending}' and expecting a boolean value"); } $iDotPos = strpos($sFieldAlias, '.'); if ($iDotPos === false) { $sAttClass = $sClass; $sAttClassAlias = $sClassAlias; $sAttCode = $sFieldAlias; } else { $sAttClassAlias = substr($sFieldAlias, 0, $iDotPos); $sAttClass = $this->GetClassName($sAttClassAlias); $sAttCode = substr($sFieldAlias, $iDotPos + 1); } if ($sAttCode != 'id') { MyHelpers::CheckValueInArray('field name in ORDER BY spec', $sAttCode, MetaModel::GetAttributesList($sAttClass)); $oAttDef = MetaModel::GetAttributeDef($sAttClass, $sAttCode); foreach ($oAttDef->GetOrderBySQLExpressions($sAttClassAlias) as $sSQLExpression) { $aOrderSpec[$sSQLExpression] = $bAscending; } } else { $aOrderSpec['`' . $sAttClassAlias . $sAttCode . '`'] = $bAscending; } // Make sure that the columns used for sorting are present in the loaded columns if (!is_null($aAttToLoad) && !isset($aAttToLoad[$sAttClassAlias][$sAttCode])) { $aAttToLoad[$sAttClassAlias][$sAttCode] = MetaModel::GetAttributeDef($sAttClass, $sAttCode); } } $oSQLQuery = $this->GetSQLQuery($aOrderBy, $aArgs, $aAttToLoad, $aExtendedDataSpec, $iLimitCount, $iLimitStart, $bGetCount); $aScalarArgs = array_merge(MetaModel::PrepareQueryArguments($aArgs), $this->GetInternalParams()); try { $bBeautifulSQL = self::$m_bTraceQueries || self::$m_bDebugQuery || self::$m_bIndentQueries; $sRes = $oSQLQuery->RenderSelect($aOrderSpec, $aScalarArgs, $iLimitCount, $iLimitStart, $bGetCount, $bBeautifulSQL); if ($sClassAlias == '_itop_') { IssueLog::Info('SQL Query (_itop_): ' . $sRes); } } catch (MissingQueryArgument $e) { // Add some information... $e->addInfo('OQL', $this->ToOQL()); throw $e; } $this->AddQueryTraceSelect($aOrderBy, $aArgs, $aAttToLoad, $aExtendedDataSpec, $iLimitCount, $iLimitStart, $bGetCount, $sRes); return $sRes; }
throw new Exception("Error: missing token file: '{$sTokenFile}'"); } $sFile = file_get_contents($sTokenFile); unlink($sTokenFile); $sMySQLBinDir = utils::ReadParam('mysql_bindir', '', false, 'raw_data'); $sDBHost = utils::ReadParam('db_host', '', false, 'raw_data'); $sDBUser = utils::ReadParam('db_user', '', false, 'raw_data'); $sDBPwd = utils::ReadParam('db_pwd', '', false, 'raw_data'); $sDBName = utils::ReadParam('db_name', '', false, 'raw_data'); $sDBSubName = utils::ReadParam('db_subname', '', false, 'raw_data'); $oDBRS = new DBRestore($sDBHost, $sDBUser, $sDBPwd, $sDBName, $sDBSubName); $oDBRS->SetMySQLBinDir($sMySQLBinDir); $sBackupDir = APPROOT . 'data/backups/'; $sBackupFile = $sBackupDir . $sFile; $sRes = $oDBRS->RestoreFromZip($sBackupFile, $sEnvironment); IssueLog::Info('Backup Restore - Done, releasing the LOCK'); $oRestoreMutex->Unlock(); } catch (Exception $e) { $oRestoreMutex->Unlock(); $oPage->p('Error: ' . $e->getMessage()); } } $oPage->output(); break; case 'download': require_once APPROOT . '/application/startup.inc.php'; require_once APPROOT . '/application/loginwebpage.class.inc.php'; LoginWebPage::DoLogin(true); // Check user rights and prompt if needed (must be admin) if (utils::GetConfig()->Get('demo_mode')) { throw new Exception('iTop is in demonstration mode: the feature is disabled');
/** * Overridable to extend the behavior in case of error (logging) */ protected function HandleError($sErrorMessage, $iErrorCode) { if ($this->Get('last_attempt') == '') { // First attempt $this->Set('remaining_retries', $this->GetMaxRetries($iErrorCode)); } $this->Set('last_error', $sErrorMessage); $this->Set('last_error_code', $iErrorCode); // Note: can be ZERO !!! $this->Set('last_attempt', time()); $iRemaining = $this->Get('remaining_retries'); if ($iRemaining > 0) { $iRetryDelay = $this->GetRetryDelay($iErrorCode); IssueLog::Info('Failed to process async task #' . $this->GetKey() . ' - reason: ' . $sErrorMessage . ' - remaining retries: ' . $iRemaining . ' - next retry in ' . $iRetryDelay . 's'); $this->Set('remaining_retries', $iRemaining - 1); $this->Set('status', 'planned'); $this->Set('started', null); $this->Set('planned', time() + $iRetryDelay); } else { IssueLog::Error('Failed to process async task #' . $this->GetKey() . ' - reason: ' . $sErrorMessage); $this->Set('status', 'error'); $this->Set('started', null); $this->Set('planned', null); $this->OnDefinitiveFailure(); } $this->DBUpdate(); }