function InitStep() { global $DB; $wizard =& $this->GetWizard(); $node_id = intval($wizard->GetVar('node_id')); if (!CModule::IncludeModule('cluster')) { $this->SetError(GetMessage('CLUWIZ_NO_MODULE_ERROR')); } elseif ($DB->type != "MYSQL") { $this->SetError(GetMessage('CLUWIZ_DATABASE_NOT_SUPPORTED')); } elseif ($node_id <= 1) { $this->SetError(GetMessage('CLUWIZ_NO_NODE_ERROR')); } else { $this->arNode = CClusterDBNode::GetByID($node_id); if (!is_array($this->arNode)) { $this->SetError(GetMessage('CLUWIZ_NO_NODE_ERROR')); } else { // $arNode["ROLE_ID"] == "SLAVE" // $arNode["STATUS"] == "READY" $this->nodeDB = CDatabase::GetDBNodeConnection($this->arNode["ID"], true, false); if (!is_object($this->nodeDB)) { $this->SetError(GetMessage('CLUWIZ_NO_CONN_ERROR')); } } } }
public static function getServerList() { $servers = array_merge(CClusterDBNode::getServerList(), CClusterMemcache::getServerList(), CClusterWebnode::getServerList()); if (empty($servers)) { $servers[] = array("ID" => 0, "HOST" => "", "DEDICATED" => "Y", "EDIT_URL" => ""); } return $servers; }
function InitStep() { global $DB; $wizard =& $this->GetWizard(); $node_id = intval($wizard->GetVar('node_id')); if (!CModule::IncludeModule('cluster')) { $this->SetError(GetMessage('CLUWIZ_NO_MODULE_ERROR')); } elseif ($DB->type != "MYSQL") { $this->SetError(GetMessage('CLUWIZ_DATABASE_NOT_SUPPORTED')); } elseif ($node_id <= 1) { $this->SetError(GetMessage('CLUWIZ_NO_NODE_ERROR')); } else { $this->arNode = CClusterDBNode::GetByID($node_id); if (!is_array($this->arNode)) { $this->SetError(GetMessage('CLUWIZ_NO_NODE_ERROR')); } else { // $arNode["ROLE_ID"] == "SLAVE" // $arNode["STATUS"] == "READY" $this->nodeDB = CDatabase::GetDBNodeConnection($this->arNode["ID"], true, false); if (!is_object($this->nodeDB)) { $this->SetError(GetMessage('CLUWIZ_NO_CONN_ERROR')); } else { $arGroup = CClusterGroup::GetArrayByID(intval($wizard->GetVar("group_id"))); if (!$arGroup) { $this->SetError(GetMessage('CLUWIZ_NO_GROUP_ERROR')); } else { $cData = new CClusterDBNode(); $rsData = $cData->GetList(array(), array("=ROLE_ID" => array("MAIN", "MASTER"), "=GROUP_ID" => $arGroup["ID"], "=STATUS" => "ONLINE")); $this->arMaster = $rsData->Fetch(); if (!$this->arMaster) { $this->SetError(GetMessage('CLUWIZ_NO_MASTER_ERROR')); } } } } } }
function Delete($ID) { global $DB, $APPLICATION; $aMsg = array(); $ID = intval($ID); $rsWebNodes = CClusterWebnode::GetList(array(), array("=GROUP_ID" => $ID)); if ($rsWebNodes->Fetch()) { $aMsg[] = array("text" => GetMessage("CLU_GROUP_HAS_WEBNODE")); } $rsDBNodes = CClusterDBNode::GetList(array(), array("=GROUP_ID" => $group_id)); if ($rsWebNodes->Fetch()) { $aMsg[] = array("text" => GetMessage("CLU_GROUP_HAS_DBNODE")); } /*TODO: memcache check*/ if (empty($aMsg)) { $res = $DB->Query("DELETE FROM b_cluster_group WHERE ID = " . $ID, false, '', array('fixed_connection' => true)); } else { $e = new CAdminException($aMsg); $APPLICATION->ThrowException($e); return false; } return $res; }
$uptime = CClusterDBNode::GetUpTime($arRes["ID"]); $arModules = CClusterDBNode::GetModules($arRes["ID"]); if ($arRes["ACTIVE"] == "Y") { if ($arRes["STATUS"] == "OFFLINE" && $uptime !== false) { CClusterDBNode::SetOnline($arRes["ID"]); $arRes["STATUS"] = "ONLINE"; } elseif ($arRes["STATUS"] == "ONLINE" && count($arModules) <= 0 && $arRes["ROLE_ID"] == "MODULE") { $ob = new CClusterDBNode(); $ob->Update($arRes["ID"], array("STATUS" => "READY")); $arRes["STATUS"] = "READY"; } elseif ($arRes["STATUS"] == "READY" && count($arModules) > 0) { $ob = new CClusterDBNode(); $ob->Update($arRes["ID"], array("STATUS" => "ONLINE")); $arRes["STATUS"] = "ONLINE"; } elseif ($arRes["STATUS"] == "READY" && $arRes["ROLE_ID"] == "MAIN") { $ob = new CClusterDBNode(); $ob->Update($arRes["ID"], array("STATUS" => "ONLINE")); $arRes["STATUS"] = "ONLINE"; } } if ($arRes["ID"] > 1) { $row->AddViewField("ID", '<a href="cluster_dbnode_edit.php?lang=' . LANGUAGE_ID . '&ID=' . $arRes["ID"] . '">' . $arRes["ID"] . '</a>'); } if ($arRes["ACTIVE"] == "Y" && $arRes["STATUS"] == "ONLINE") { $htmlFLAG = '<div class="lamp-green"></div>'; } else { $htmlFLAG = '<div class="lamp-red"></div>'; } if ($uptime === false) { $htmlFLAG .= GetMessage("CLU_DBNODE_NOCONNECTION"); } elseif ($uptime > 0) {
function SlaveConnection() { if (!class_exists('cmodule') || !class_exists('csqlwhere')) { return null; } if (!CModule::IncludeModule('cluster')) { return false; } $arSlaves = CClusterSlave::GetList(); if (empty($arSlaves)) { return false; } $max_slave_delay = COption::GetOptionInt("cluster", "max_slave_delay", 10); if (isset($_SESSION["BX_REDIRECT_TIME"])) { $redirect_delay = time() - $_SESSION["BX_REDIRECT_TIME"] + 1; if ($redirect_delay > 0 && $redirect_delay < $max_slave_delay) { $max_slave_delay = $redirect_delay; } } $total_weight = 0; foreach ($arSlaves as $i => $slave) { if (defined("BX_CLUSTER_GROUP") && BX_CLUSTER_GROUP != $slave["GROUP_ID"]) { unset($arSlaves[$i]); } elseif ($slave["ROLE_ID"] == "SLAVE") { $arSlaveStatus = CClusterSlave::GetStatus($slave["ID"], true, false, false); if ($arSlaveStatus['Seconds_Behind_Master'] > $max_slave_delay || $arSlaveStatus['Last_SQL_Error'] != '' || $arSlaveStatus['Last_IO_Error'] != '' || $arSlaveStatus['Slave_SQL_Running'] === 'No') { unset($arSlaves[$i]); } else { $total_weight += $slave["WEIGHT"]; } } else { $total_weight += $slave["WEIGHT"]; } } $found = false; foreach ($arSlaves as $slave) { if (mt_rand(0, $total_weight) < $slave["WEIGHT"]) { $found = $slave; break; } } if (!$found || $found["ROLE_ID"] != "SLAVE") { return false; //use main connection } else { ob_start(); $conn = CDatabase::GetDBNodeConnection($found["ID"], true); ob_end_clean(); if (is_object($conn)) { return $conn; } else { self::$arNodes[$found["ID"]]["ONHIT_ERROR"] = true; CClusterDBNode::SetOffline($found["ID"]); return false; //use main connection } } }
function ShowStepNoError() { global $APPLICATION; $wizard =& $this->GetWizard(); $path = $wizard->package->path; $to_node_id = $wizard->GetVar('to_node_id'); if ($wizard->GetVar('module')) { $module = $wizard->GetVar('module'); $from_node_id = intval(COption::GetOptionString($module, "dbnode_id")); if ($from_node_id <= 0) { $from_node_id = 1; } } else { $from_node_id = $wizard->GetVar('from_node_id'); $arNodeModules = CClusterDBNode::GetModules($wizard->GetVar('from_node_id')); $module = key($arNodeModules); } CJSCore::Init(array("ajax")); $APPLICATION->AddHeadScript($path . '/js/import.js'); $this->content = ''; $this->content .= '<div style="padding: 20px;">'; $this->content .= '<div id="output"><br /></div>'; $this->content .= '</div>'; if ($wizard->GetPrevStepID() == 'step1' || $wizard->GetPrevStepID() == 'step2') { $this->content .= ' <script type="text/javascript"> var nextButtonID = "' . $wizard->GetNextButtonID() . '"; var formID = "' . $wizard->GetFormName() . '"; var LANG = \'' . LANG . '\'; var from_node_id = "' . CUtil::JSEscape($from_node_id) . '"; var to_node_id = "' . CUtil::JSEscape($to_node_id) . '"; var module = "' . CUtil::JSEscape($module) . '"; var status = "' . CUtil::JSEscape($wizard->GetVar('status')) . '"; var path = "' . CUtil::JSEscape($path) . '"; var sessid = "' . bitrix_sessid() . '"; BX.ready(DisableButton); BX.ready(MoveTables); </script> '; } }
function AdjustServerID($arNode, $nodeDB) { $rs = $nodeDB->Query("show variables like 'server_id'", false, '', array("fixed_connection" => true)); if ($ar = $rs->Fetch()) { if ($ar["Value"] != $arNode["SERVER_ID"]) { $ob = new CClusterDBNode(); $ob->Update($arNode["ID"], array("SERVER_ID" => $ar["Value"])); } } }
function InstallDB($arParams = array()) { global $DBType, $APPLICATION; $node_id = strlen($arParams["DATABASE"]) > 0 ? intval($arParams["DATABASE"]) : false; if ($node_id !== false) { $DB = $GLOBALS["DB"]->GetDBNodeConnection($node_id); } else { $DB = $GLOBALS["DB"]; } $this->errors = false; $arAllErrors = array(); // check if module was deinstalled without table save $DATE_INSTALL_TABLES = ""; $no_tables = "N"; if (!$DB->Query("SELECT count('x') FROM b_stat_day WHERE 1=0", true)) { // last installation date have to be current $DATE_INSTALL_TABLES = date("d.m.Y H:i:s", time()); $no_tables = "Y"; } if ($no_tables == "Y") { $this->errors = $DB->RunSQLBatch($_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/statistic/install/db/" . strtolower($DB->type) . "/install.sql"); } if ($this->errors !== false) { $APPLICATION->ThrowException(implode("<br>", $this->errors)); return false; } RegisterModule("statistic"); RegisterModuleDependences("main", "OnPageStart", "statistic", "CStopList", "Check", "100"); RegisterModuleDependences("main", "OnBeforeProlog", "statistic", "CStatistics", "Keep", "100"); RegisterModuleDependences("main", "OnEpilog", "statistic", "CStatistics", "Set404", "100"); RegisterModuleDependences("main", "OnBeforeProlog", "statistic", "CStatistics", "StartBuffer", "1000"); RegisterModuleDependences("main", "OnAfterEpilog", "statistic", "CStatistics", "EndBuffer", "10"); RegisterModuleDependences("main", "OnEventLogGetAuditTypes", "statistic", "CStatistics", "GetAuditTypes", 10); RegisterModuleDependences("statistic", "OnCityLookup", "statistic", "CCityLookup_geoip_mod", "OnCityLookup", "100"); RegisterModuleDependences("statistic", "OnCityLookup", "statistic", "CCityLookup_geoip_extension", "OnCityLookup", "200"); RegisterModuleDependences("statistic", "OnCityLookup", "statistic", "CCityLookup_geoip_pure", "OnCityLookup", "300"); RegisterModuleDependences("statistic", "OnCityLookup", "statistic", "CCityLookup_stat_table", "OnCityLookup", "400"); RegisterModuleDependences("cluster", "OnGetTableList", "statistic", "statistic", "OnGetTableList"); if (strlen($DATE_INSTALL_TABLES) > 0) { COption::SetOptionString("main", "INSTALL_STATISTIC_TABLES", $DATE_INSTALL_TABLES, "Date of installation of statistics module tables"); } if ($node_id !== false) { COption::SetOptionString("statistic", "dbnode_id", $node_id); if (CModule::IncludeModule('cluster')) { CClusterDBNode::SetOnline($node_id); } } else { COption::SetOptionString("statistic", "dbnode_id", "N"); } COption::SetOptionString("statistic", "dbnode_status", "ok"); // init counters if (array_key_exists("allow_initial", $arParams) && $arParams["allow_initial"] == "Y") { $strSql = "SELECT ID FROM b_stat_day"; $e = $DB->Query($strSql, false, $err_mess . __LINE__); if (!($er = $e->Fetch())) { if (intval($arParams["START_HITS"]) > 0 || intval($arParams["START_HOSTS"]) > 0 || intval($arParams["START_GUESTS"]) > 0) { $arFields = array("DATE_STAT" => $DB->GetNowDate(), "HITS" => intval($arParams["START_HITS"]), "C_HOSTS" => intval($arParams["START_HOSTS"]), "GUESTS" => intval($arParams["START_GUESTS"]), "NEW_GUESTS" => intval($arParams["START_GUESTS"])); $DB->Insert("b_stat_day", $arFields, $err_mess . __LINE__); } } } $arr = getdate(); $ndate = mktime(0, 1, 0, $arr["mon"], $arr["mday"], $arr["year"]); CAgent::AddAgent("CStatistics::SetNewDay();", "statistic", "Y", 86400, "", "Y", ConvertTimeStamp($ndate + CTimeZone::GetOffset(), "FULL"), 200); $ndate = mktime(3, 0, 0, $arr["mon"], $arr["mday"], $arr["year"]); CAgent::AddAgent("CStatistics::CleanUpStatistics_1();", "statistic", "Y", 86400, "", "Y", ConvertTimeStamp($ndate + CTimeZone::GetOffset(), "FULL"), 50); $ndate = mktime(4, 0, 0, $arr["mon"], $arr["mday"], $arr["year"]); CAgent::AddAgent("CStatistics::CleanUpStatistics_2();", "statistic", "Y", 86400, "", "Y", ConvertTimeStamp($ndate + CTimeZone::GetOffset(), "FULL"), 30); CAgent::AddAgent("CStatistics::CleanUpSessionData();", "statistic", "N", 7200); CAgent::AddAgent("CStatistics::CleanUpPathCache();", "statistic", "N", 3600); CAgent::RemoveAgent("SendDailyStatistics();", "statistic"); if (strpos($_SERVER["SERVER_SOFTWARE"], "(Win32)") <= 0) { $ndate = mktime(9, 0, 0, $arr["mon"], $arr["mday"], $arr["year"]); CAgent::AddAgent("SendDailyStatistics();", "statistic", "Y", 86400, "", "Y", ConvertTimeStamp($ndate + CTimeZone::GetOffset(), "FULL"), 25); } if ($no_tables == "Y") { $arAllErrors[] = $DB->RunSQLBatch($_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/statistic/install/db/" . strtolower($DB->type) . "/searchers.sql"); $arAllErrors[] = $DB->RunSQLBatch($_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/statistic/install/db/" . strtolower($DB->type) . "/browsers.sql"); $arAllErrors[] = $DB->RunSQLBatch($_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/statistic/install/db/" . strtolower($DB->type) . "/adv.sql"); } // ip-to-country require_once $_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/statistic/ip_tools.php"; i2c_load_countries(); if (!array_key_exists("CREATE_I2C_INDEX", $arParams) || $arParams["CREATE_I2C_INDEX"] == "Y") { i2c_create_db($total_reindex, $reindex_success, $step_reindex, $int_prev); } $fname = $_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/statistic/install/db/" . strtolower($DB->type) . "/optimize.sql"; if (file_exists($fname)) { $arAllErrors[] = $DB->RunSQLBatch($fname); } $this->errors = array(); foreach ($arAllErrors as $ar) { if (is_array($ar)) { foreach ($ar as $strError) { $this->errors[] = $strError; } } } if (count($this->errors) < 1) { $this->errors = false; } if ($this->errors !== false) { $APPLICATION->ThrowException(implode("<br>", $this->errors)); return false; } return true; }
public function SlaveNodeForMaster($nodeDB) { global $DB; $result = array(); $arMasters = array(); $cData = new CClusterDBNode(); $rsData = $cData->GetList(array("ID" => "ASC"), array("=ROLE_ID" => array("MAIN", "MASTER"))); while ($arData = $rsData->Fetch()) { $arMasters[$arData["ID"]] = $arData; } $arMasters["v99"] = array(); //virtual connection must be alredy setup foreach ($arMasters as $node_id => $arNode) { if ($node_id == 1) { $nodeDB = $DB; } else { $nodeDB = CDatabase::GetDBNodeConnection($node_id, true); } $arMasters[$node_id]["DB"] = $nodeDB; } $auto_increment_increment = count($arMasters); $bIncIsOK = true; foreach ($arMasters as $node_id => $arNode) { $inc = $this->GetServerVariable($arNode["DB"], "auto_increment_increment"); if ($inc != $auto_increment_increment) { $bIncIsOK = false; if ($node_id == "v99") { $result[$node_id . "_auto_increment_increment"] = array("IS_OK" => CClusterDBNodeCheck::ERROR, "MESSAGE" => GetMessage("CLU_AUTO_INCREMENT_INCREMENT_NODE_ERR_MSG", array("#value#" => $auto_increment_increment, "#current#" => $inc)), "WIZ_REC" => GetMessage("CLU_AUTO_INCREMENT_INCREMENT_WIZREC", array("#value#" => $auto_increment_increment))); } else { $result[$node_id . "_auto_increment_increment"] = array("IS_OK" => CClusterDBNodeCheck::ERROR, "MESSAGE" => GetMessage("CLU_AUTO_INCREMENT_INCREMENT_ERR_MSG", array("#node_id#" => $node_id, "#value#" => $auto_increment_increment, "#current#" => $inc)), "WIZ_REC" => GetMessage("CLU_AUTO_INCREMENT_INCREMENT_WIZREC", array("#value#" => $auto_increment_increment))); } } } if ($bIncIsOK) { $result["_auto_increment_increment"] = array("IS_OK" => CClusterDBNodeCheck::OK, "MESSAGE" => GetMessage("CLU_AUTO_INCREMENT_INCREMENT_OK_MSG", array("#value#" => $auto_increment_increment)), "WIZ_REC" => ""); } $auto_increment_offset = array(); $bIncIsOK = true; foreach ($arMasters as $node_id => $arNode) { $offset = $this->GetServerVariable($arNode["DB"], "auto_increment_offset"); $mod = $offset % $auto_increment_increment; if (array_key_exists($mod, $auto_increment_offset)) { $bIncIsOK = false; if ($node_id == "v99") { $result[$node_id . "_auto_increment_offset"] = array("IS_OK" => CClusterDBNodeCheck::ERROR, "MESSAGE" => GetMessage("CLU_AUTO_INCREMENT_OFFSET_NODE_ERR_MSG", array("#current#" => $offset)), "WIZ_REC" => GetMessage("CLU_AUTO_INCREMENT_OFFSET_WIZREC", array("#current#" => $offset))); } else { $result[$node_id . "_auto_increment_offset"] = array("IS_OK" => CClusterDBNodeCheck::ERROR, "MESSAGE" => GetMessage("CLU_AUTO_INCREMENT_OFFSET_ERR_MSG", array("#node_id#" => $node_id, "#current#" => $offset)), "WIZ_REC" => GetMessage("CLU_AUTO_INCREMENT_OFFSET_WIZREC", array("#current#" => $offset))); } } else { $auto_increment_offset[$mod] = $node_id; } } if ($bIncIsOK) { $result["_auto_increment_offset"] = array("IS_OK" => CClusterDBNodeCheck::OK, "MESSAGE" => GetMessage("CLU_AUTO_INCREMENT_OFFSET_OK_MSG", array("#value#" => $auto_increment_increment)), "WIZ_REC" => ""); } $bRelayIsOK = true; foreach ($arMasters as $node_id => $arNode) { $relay_log = $this->GetServerVariable($arNode["DB"], "relay_log"); if (strlen($relay_log) <= 0) { $bIncIsOK = false; $result[$node_id . "_relay_log"] = array("IS_OK" => CClusterDBNodeCheck::ERROR, "MESSAGE" => GetMessage("CLU_RELAY_LOG_ERR_MSG", array("#node_id#" => $node_id, "#relay-log#" => $relay_log)), "WIZ_REC" => GetMessage("CLU_RELAY_LOG_WIZREC")); } } if ($bRelayIsOK) { $result["_relay_log"] = array("IS_OK" => CClusterDBNodeCheck::OK, "MESSAGE" => GetMessage("CLU_RELAY_LOG_OK_MSG", array("#value#" => $auto_increment_increment)), "WIZ_REC" => ""); } $log_bin = $this->GetServerVariable($nodeDB, "log_bin"); $is_ok = $log_bin === "ON"; $result["log_bin"] = array("IS_OK" => $is_ok ? CClusterDBNodeCheck::OK : CClusterDBNodeCheck::ERROR, "MESSAGE" => GetMessage("CLU_LOG_BIN_NODE_MSG", array("#log-bin#" => $log_bin)), "WIZ_REC" => GetMessage("CLU_LOG_BIN_WIZREC")); $skip_networking = $this->GetServerVariable($nodeDB, "skip_networking"); $is_ok = $skip_networking === "OFF"; $result["skip_networking"] = array("IS_OK" => $is_ok ? CClusterDBNodeCheck::OK : CClusterDBNodeCheck::ERROR, "MESSAGE" => GetMessage("CLU_SKIP_NETWORKING_NODE_MSG", array("#skip-networking#" => $skip_networking)), "WIZ_REC" => GetMessage("CLU_SKIP_NETWORKING_WIZREC")); $innodb_flush_log_at_trx_commit = $this->GetServerVariable($nodeDB, "innodb_flush_log_at_trx_commit"); $is_ok = $innodb_flush_log_at_trx_commit === '1'; $result["innodb_flush_log_at_trx_commit"] = array("IS_OK" => $is_ok ? CClusterDBNodeCheck::OK : CClusterDBNodeCheck::WARNING, "MESSAGE" => GetMessage("CLU_FLUSH_ON_COMMIT_MSG", array("#innodb_flush_log_at_trx_commit#" => $innodb_flush_log_at_trx_commit)), "WIZ_REC" => ""); $sync_binlog = $this->GetServerVariable($nodeDB, "sync_binlog"); $is_ok = $sync_binlog === '1'; $result["sync_binlog"] = array("IS_OK" => $is_ok ? CClusterDBNodeCheck::OK : CClusterDBNodeCheck::WARNING, "MESSAGE" => GetMessage("CLU_SYNC_BINLOG_MSG", array("#sync_binlog#" => $sync_binlog)), "WIZ_REC" => ""); $DatabaseName = $DB->DBName; $is_ok = false; $rsBinLogs = $nodeDB->Query("show master status", true, '', array("fixed_connection" => true)); if (!$rsBinLogs) { $result["master_status"] = array("IS_OK" => CClusterDBNodeCheck::ERROR, "MESSAGE" => GetMessage("CLU_MASTER_STATUS_MSG"), "WIZ_REC" => GetMessage("CLU_MASTER_STATUS_WIZREC", array("#sql#" => "GRANT REPLICATION CLIENT on *.* to 'user name'@'%';"))); } else { if ($ar = $rsBinLogs->Fetch()) { if ($ar["Binlog_Do_DB"] === $DatabaseName) { $is_ok = true; } } while ($ar = $rsBinLogs->Fetch()) { $is_ok = false; } $result["binlog_do_db"] = array("IS_OK" => $is_ok ? CClusterDBNodeCheck::OK : CClusterDBNodeCheck::ERROR, "MESSAGE" => GetMessage("CLU_SYNC_BINLOGDODB_MSG"), "WIZ_REC" => GetMessage("CLU_SYNC_BINLOGDODB_WIZREC", array("#database#" => $DatabaseName))); } return $result; }
case "stop": CClusterSlave::Stop($ID); break; case "skip_sql_error": CClusterSlave::SkipSQLError($ID); break; } } } $arHeaders = array(array("id" => "ID", "content" => GetMessage("CLU_SLAVE_LIST_ID"), "align" => "right", "default" => true), array("id" => "FLAG", "content" => GetMessage("CLU_SLAVE_LIST_FLAG"), "align" => "center", "default" => true), array("id" => "NAME", "content" => GetMessage("CLU_SLAVE_LIST_NAME"), "align" => "left", "default" => true), array("id" => "BEHIND", "content" => GetMessage("CLU_SLAVE_LIST_BEHIND"), "align" => "right", "default" => true), array("id" => "STATUS", "content" => GetMessage("CLU_SLAVE_LIST_STATUS"), "align" => "center", "default" => true), array("id" => "WEIGHT", "content" => GetMessage("CLU_SLAVE_LIST_WEIGHT"), "align" => "right", "default" => true), array("id" => "DESCRIPTION", "content" => GetMessage("CLU_SLAVE_LIST_DESCRIPTION"), "align" => "left", "default" => false), array("id" => "DB_HOST", "content" => GetMessage("CLU_SLAVE_LIST_DB_HOST"), "align" => "left", "default" => false), array("id" => "DB_NAME", "content" => GetMessage("CLU_SLAVE_LIST_DB_NAME"), "align" => "left", "default" => false), array("id" => "DB_LOGIN", "content" => GetMessage("CLU_SLAVE_LIST_DB_LOGIN"), "align" => "left", "default" => false)); $lAdmin->AddHeaders($arHeaders); $arFilter = array("=ROLE_ID" => array("MAIN", "SLAVE", "MASTER")); if ($group_id > 0) { $arFilter["=GROUP_ID"] = $group_id; } $cData = new CClusterDBNode(); $rsData = $cData->GetList(array("ID" => "ASC"), $arFilter); if (!isset($_SESSION["SLAVE_LIST"])) { $_SESSION["SLAVE_LIST"] = array(); } $rsData = new CAdminResult($rsData, $sTableID); $Position = 0; $bNote1Show = false; $bHasMaster = false; while ($arRes = $rsData->Fetch()) { $row =& $lAdmin->AddRow($arRes["ID"], $arRes); if ($arRes["ROLE_ID"] == "MASTER" || $arRes["ROLE_ID"] == "MAIN") { $bHasMaster = true; } $arSlaveStatus = CClusterSlave::GetStatus($arRes["ID"]); if (is_array($arSlaveStatus) && $arRes["STATUS"] == "OFFLINE") {
/** * Creates a new slave connection. * * @return bool|null|Connection * @throws \Bitrix\Main\Config\ConfigurationException */ protected function createSlaveConnection() { if (!class_exists('csqlwhere')) { return null; } if (!Main\Loader::includeModule('cluster')) { return false; } $found = \CClusterSlave::GetRandomNode(); if ($found !== false) { $node = \CClusterDBNode::GetByID($found["ID"]); if (is_array($node) && $node["ACTIVE"] == "Y" && ($node["STATUS"] == "ONLINE" || $node["STATUS"] == "READY")) { $parameters = array('host' => $node["DB_HOST"], 'database' => $node["DB_NAME"], 'login' => $node["DB_LOGIN"], 'password' => $node["DB_PASSWORD"]); $connection = $this->cloneConnection(self::DEFAULT_CONNECTION_NAME, "node" . $node["ID"], $parameters); $connection->setNodeId($node["ID"]); return $connection; } } return false; }
function ShowStepNoError() { $wizard =& $this->GetWizard(); $to_node_id = $wizard->GetVar('to_node_id'); if ($wizard->GetVar('module')) { $module = $wizard->GetVar('module'); $from_node_id = intval(COption::GetOptionString($module, "dbnode_id")); if ($from_node_id <= 0) { $from_node_id = 1; } } else { $from_node_id = $wizard->GetVar('from_node_id'); $arNodeModules = CClusterDBNode::GetModules($wizard->GetVar('from_node_id')); $module = key($arNodeModules); } $path = $wizard->package->path; $this->content = ''; $this->content .= '<div style="padding: 20px;">'; $this->content .= '<div id="output"><br /></div>'; $this->content .= '</div>'; $this->content .= '<script type="text/javascript" src="' . $path . '/js/import.js?rand=' . mt_rand() . '"></script>'; $this->content .= '<script type="text/javascript"> var nextButtonID = "' . $wizard->GetNextButtonID() . '"; var formID = "' . $wizard->GetFormName() . '"; var LANG = \'' . LANG . '\'; var from_node_id = "' . CUtil::JSEscape($from_node_id) . '"; var to_node_id = "' . CUtil::JSEscape($to_node_id) . '"; var module = "' . CUtil::JSEscape($module) . '"; var status = "' . CUtil::JSEscape($wizard->GetVar('status')) . '"; var path = "' . CUtil::JSEscape($path) . '"; var sessid = "' . bitrix_sessid() . '"; if (window.addEventListener) { window.addEventListener("load", DisableButton, false); window.addEventListener("load", MoveTables, false); } else if (window.attachEvent) { window.attachEvent("onload", DisableButton); window.attachEvent("onload", MoveTables); } </script>'; }
function InstallDB($arParams = array()) { global $DBType, $APPLICATION; $this->errors = false; $node_id = strlen($arParams["DATABASE"]) > 0 ? intval($arParams["DATABASE"]) : false; if ($node_id !== false) { $DB = $GLOBALS["DB"]->GetDBNodeConnection($node_id); } else { $DB = $GLOBALS["DB"]; } // Database tables creation if (!$DB->Query("SELECT 'x' FROM b_search_content WHERE 1=0", true)) { $this->errors = $DB->RunSQLBatch($_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/search/install/db/" . strtolower($DB->type) . "/install.sql"); if ($this->errors === false && strtolower($DB->type) == "mssql") { $rs = $DB->Query("\n\t\t\t\t\tselect c.*\n\t\t\t\t\tfrom sys.tables t\n\t\t\t\t\tinner join sys.columns c on t.object_id = c.object_id\n\t\t\t\t\twhere t.name='b_search_tags'\n\t\t\t\t\tand c.name='NAME'\n\t\t\t\t"); if ($ar = $rs->Fetch()) { if (strpos($ar["collation_name"], "_CI_") !== false) { $new_collation = str_replace("_CI_", "_CS_", $ar["collation_name"]); $rs = $DB->Query("DROP TABLE b_search_tags"); if ($rs) { $rs = $DB->Query("\n\t\t\t\t\t\t\t\tCREATE TABLE b_search_tags\n\t\t\t\t\t\t\t\t(\n\t\t\t\t\t\t\t\t\tSEARCH_CONTENT_ID INT NOT NULL,\n\t\t\t\t\t\t\t\t\tSITE_ID CHAR(2) NOT NULL,\n\t\t\t\t\t\t\t\t\tNAME VARCHAR(255) COLLATE " . $new_collation . " NOT NULL,\n\t\t\t\t\t\t\t\t\tCONSTRAINT PK_B_SEARCH_TAGS PRIMARY KEY (SEARCH_CONTENT_ID, SITE_ID, NAME)\n\t\t\t\t\t\t\t\t)\n\t\t\t\t\t\t\t"); } if (!$rs) { $this->errors = array($DB->db_Error); } } } } } if ($this->errors === false && !$DB->Query("SELECT 'x' FROM b_search_phrase WHERE 1=0", true)) { $this->errors = $DB->RunSQLBatch($_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/search/install/db/" . strtolower($DB->type) . "/stat_install.sql"); } if ($this->errors !== false) { $APPLICATION->ThrowException(implode("<br>", $this->errors)); return false; } else { RegisterModule("search"); CModule::IncludeModule("search"); RegisterModuleDependences("main", "OnChangePermissions", "search", "CSearch", "OnChangeFilePermissions"); RegisterModuleDependences("main", "OnChangeFile", "search", "CSearch", "OnChangeFile"); RegisterModuleDependences("main", "OnGroupDelete", "search", "CSearch", "OnGroupDelete"); RegisterModuleDependences("main", "OnLangDelete", "search", "CSearch", "OnLangDelete"); RegisterModuleDependences("main", "OnAfterUserUpdate", "search", "CSearchUser", "OnAfterUserUpdate"); RegisterModuleDependences("main", "OnUserDelete", "search", "CSearchUser", "DeleteByUserID"); RegisterModuleDependences("cluster", "OnGetTableList", "search", "search", "OnGetTableList"); RegisterModuleDependences("perfmon", "OnGetTableSchema", "search", "search", "OnGetTableSchema"); if ($node_id !== false) { COption::SetOptionString("search", "dbnode_id", $node_id); if (CModule::IncludeModule('cluster')) { CClusterDBNode::SetOnline($node_id); } } else { COption::SetOptionString("search", "dbnode_id", "N"); } COption::SetOptionString("search", "dbnode_status", "ok"); CAgent::AddAgent("CSearchSuggest::CleanUpAgent();", "search", "N", 86400, "", "Y", "", 10); CAgent::AddAgent("CSearchStatistic::CleanUpAgent();", "search", "N", 86400, "", "Y", "", 10); CSearchStatistic::SetActive(COption::GetOptionString("search", "stat_phrase") == "Y"); return true; } }
<?php } ?> </table><br> <?php if (CModule::IncludeModule('cluster')) { ?> <p><?php echo GetMessage("STAT_INSTALL_DATABASE"); ?> <select name="DATABASE"> <option value=""><?php echo GetMessage("STAT_MAIN_DATABASE"); ?> </option><?php $rsDBNodes = CClusterDBNode::GetListForModuleInstall(); while ($arDBNode = $rsDBNodes->Fetch()) { ?> <option value="<?php echo $arDBNode["ID"]; ?> "><?php echo htmlspecialcharsbx($arDBNode["NAME"]); ?> </option><?php } ?> </select></p> <br> <?php }
function OnPostForm() { $wizard =& $this->GetWizard(); if ($wizard->IsNextButtonClick()) { $obNode = new CClusterDBNode(); $obNode->Add(array("ACTIVE" => "Y", "ROLE_ID" => "MODULE", "NAME" => $wizard->GetVar("node_name"), "DESCRIPTION" => false, "DB_HOST" => $wizard->GetVar("db_host"), "DB_NAME" => $wizard->GetVar("db_name"), "DB_LOGIN" => $wizard->GetVar("db_login"), "DB_PASSWORD" => $wizard->GetVar("db_password"), "MASTER_ID" => false, "SERVER_ID" => false, "STATUS" => "READY")); $this->location = '/bitrix/admin/cluster_dbnode_list.php?lang=' . LANGUAGE_ID; } }
if ($arSource) { $DB->Query("\n\t\t\t\t\tUPDATE b_cluster_table\n\t\t\t\t\tSET LAST_ID = " . (strlen($arTable["KEY_COLUMN"]) > 0 ? $arSource[$arTable["KEY_COLUMN"]] : $i) . "\n\t\t\t\t\t,REC_COUNT = " . $i . "\n\t\t\t\t\tWHERE ID = '" . $arTable["ID"] . "'\n\t\t\t\t", false, '', array("fixed_connection" => true)); } elseif (strlen($last_id)) { $DB->Query("\n\t\t\t\t\tUPDATE b_cluster_table\n\t\t\t\t\tSET LAST_ID = " . $last_id . "\n\t\t\t\t\t,REC_COUNT = " . $i . "\n\t\t\t\t\tWHERE ID = '" . $arTable["ID"] . "'\n\t\t\t\t", false, '', array("fixed_connection" => true)); } else { $DB->Query("\n\t\t\t\t\tDELETE FROM b_cluster_table\n\t\t\t\t\tWHERE ID = '" . $arTable["ID"] . "'\n\t\t\t\t", false, '', array("fixed_connection" => true)); } } else { if ($to_node_id > 1) { COption::SetOptionString($_REQUEST["module"], "dbnode_id", $to_node_id); } else { COption::SetOptionString($_REQUEST["module"], "dbnode_id", "N"); } COption::SetOptionString($_REQUEST["module"], "dbnode_status", 'ok'); CClusterDBNode::SetOnline($to_node_id); $ob = new CClusterDBNode(); if ($from_node_id > 1) { $ob->Update($from_node_id, array("STATUS" => "READY")); } } } while (is_array($arTable) && time() < $end_time); if (is_array($arTable)) { echo GetMessage('CLUWIZ_TABLE_PROGRESS', array("#table_name#" => $arTable["TABLE_NAME"], "#records#" => $i)); echo "<script>MoveTables(2)</script>"; } else { if ($_REQUEST["status"] == "READY") { echo GetMessage("CLUWIZ_ALL_DONE1"); } else { echo GetMessage("CLUWIZ_ALL_DONE2"); } echo '<script>EnableButton();</script>';
/** * Return information about DB from cluster module * * @return array */ protected static function getDBHostsFromCluster() { $result = array(); if (CModule::IncludeModule("cluster")) { $clusterDBs = CClusterDBNode::GetList(array("ID" => "ASC"), array("=ROLE_ID" => array("SLAVE", "MASTER")), array("DB_HOST")); while ($clusterDBServer = $clusterDBs->Fetch()) { $result[] = array("host" => $clusterDBServer["DB_HOST"]); } } return $result; }
/** @global CDatabase $DB */ /** @global CUser $USER */ require_once $_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/perfmon/include.php"; require_once $_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/perfmon/prolog.php"; IncludeModuleLangFile(__FILE__); $RIGHT = $APPLICATION->GetGroupRight("perfmon"); if ($RIGHT == "D") { $APPLICATION->AuthForm(GetMessage("ACCESS_DENIED")); } $bCluster = CModule::IncludeModule('cluster'); $node_id = 0; $statDB = $DB; $queryOptions = array("fixed_connection" => true); $arClusterNodes = array(); if ($bCluster) { $rsNodes = CClusterDBNode::GetList(); while ($node = $rsNodes->fetch()) { $arClusterNodes[$node["ID"]] = htmlspecialcharsex($node["NAME"]); } if (!empty($arClusterNodes)) { $node_id = intval($_REQUEST["node_id"]); if ($node_id > 1) { $statDB = $DB->GetDBNodeConnection($node_id); $queryOptions = array(); } else { $node_id = 1; } } } $message = null; $data = array();
function OnPostForm() { $wizard =& $this->GetWizard(); $group_id = intval($wizard->GetVar("group_id")); if ($wizard->IsNextButtonClick()) { $obNode = new CClusterDBNode(); $node_id = $obNode->Add(array("ACTIVE" => "Y", "ROLE_ID" => "MASTER", "GROUP_ID" => $group_id, "NAME" => $wizard->GetVar("node_name"), "DESCRIPTION" => false, "DB_HOST" => $wizard->GetVar("db_host"), "DB_NAME" => $GLOBALS["DB"]->DBName, "DB_LOGIN" => $wizard->GetVar("db_login"), "DB_PASSWORD" => $wizard->GetVar("db_password"), "MASTER_ID" => 1, "MASTER_HOST" => $wizard->GetVar("master_host", true), "MASTER_PORT" => $wizard->GetVar("master_port", true), "SERVER_ID" => false, "STATUS" => $wizard->GetVar("status") === "online" ? "ONLINE" : "READY", "SELECTABLE" => "Y", "WEIGHT" => 100)); $this->location = '/bitrix/admin/cluster_slave_list.php?lang=' . LANGUAGE_ID . '&group_id=' . $group_id; } }
public static function GetListForModuleInstall() { return CClusterDBNode::GetList(array("NAME" => "ASC", "ID" => "ASC"), array("=ACTIVE" => "Y", "=ROLE_ID" => "MODULE", "=STATUS" => "READY"), array("ID", "NAME")); }
/** * Returns module database connection. * Can be used only if module supports sharding. * * @param string $module_id * @param bool $bModuleInclude * @return bool|CDatabase */ public static function GetModuleConnection($module_id, $bModuleInclude = false) { $node_id = COption::GetOptionString($module_id, "dbnode_id", "N"); if (is_numeric($node_id)) { if ($bModuleInclude) { $status = COption::GetOptionString($module_id, "dbnode_status", "ok"); if ($status === "move") { return false; } } $moduleDB = CDatabase::GetDBNodeConnection($node_id, $bModuleInclude); if (is_object($moduleDB)) { $moduleDB->bModuleConnection = true; return $moduleDB; } //There was an connection error if ($bModuleInclude && CModule::IncludeModule('cluster')) { CClusterDBNode::SetOffline($node_id); } //TODO: unclear what to return when node went offline //in the middle of the hit. return false; } else { return $GLOBALS["DB"]; } }
$res = $ID = $ob->Add($arFields); } if ($res) { if ($apply != "") { LocalRedirect("/bitrix/admin/cluster_dbnode_edit.php?ID=" . $ID . "&lang=" . LANGUAGE_ID . "&" . $tabControl->ActiveTabParam() . '&group_id=' . $group_id); } else { LocalRedirect("/bitrix/admin/cluster_dbnode_list.php?lang=" . LANGUAGE_ID . '&group_id=' . $group_id); } } else { if ($e = $APPLICATION->GetException()) { $message = new CAdminMessage(GetMessage("CLU_DBNODE_EDIT_SAVE_ERROR"), $e); } $bVarsFromForm = true; } } elseif ($delete != "" && $ID > 1) { $ob = new CClusterDBNode(); $res = $ob->Delete($ID); if ($res) { LocalRedirect("/bitrix/admin/cluster_dbnode_list.php?lang=" . LANGUAGE_ID . '&group_id=' . $group_id); } else { $bVarsFromForm = true; } } } ClearVars("str_"); $str_ACTIVE = "Y"; $str_SORT = "10"; $str_NAME = ""; $str_DESCRIPTION = ""; $str_DB_HOST = ""; $str_DB_NAME = "";
public function Query($strSql, $bIgnoreErrors = false, $error_position = "", $arOptions = array()) { global $DB; $this->DoConnect(); $this->db_Error = ""; if ($this->DebugToFile || $DB->ShowSqlStat) { $start_time = microtime(true); } //We track queries for DML statements //and when there is no one we can choose //to run query against master connection //or replicated one $connectionPool = \Bitrix\Main\Application::getInstance()->getConnectionPool(); if ($connectionPool->isMasterOnly()) { //We requested to process all queries //by master connection } elseif ($this->bModuleConnection) { //In case of dedicated module database //were is nothing to do } elseif (isset($arOptions["fixed_connection"])) { //We requested to process this query //by current connection } elseif ($this->bNodeConnection) { //It is node so nothing to do } else { if (isset($arOptions["ignore_dml"])) { $connectionPool->ignoreDml(true); } $connection = $connectionPool->getSlaveConnection($strSql); if (isset($arOptions["ignore_dml"])) { $connectionPool->ignoreDml(false); } if ($connection !== null) { if (!isset($this->obSlave)) { $nodeId = $connection->getNodeId(); ob_start(); $conn = CDatabase::GetDBNodeConnection($nodeId, true); ob_end_clean(); if (is_object($conn)) { $this->obSlave = $conn; } else { self::$arNodes[$nodeId]["ONHIT_ERROR"] = true; CClusterDBNode::SetOffline($nodeId); } } if (is_object($this->obSlave)) { return $this->obSlave->Query($strSql, $bIgnoreErrors, $error_position, $arOptions); } } } $result = $this->QueryInternal($strSql); if ($this->DebugToFile || $DB->ShowSqlStat) { /** @noinspection PhpUndefinedVariableInspection */ $exec_time = round(microtime(true) - $start_time, 10); if ($DB->ShowSqlStat) { $DB->addDebugQuery($strSql, $exec_time, $connectionPool->isSlavePossible() ? $this->node_id : -1); } if ($this->DebugToFile) { $this->startSqlTracker()->writeFileLog($strSql, $exec_time, "CONN: " . $this->getThreadId()); } } if (!$result) { $this->db_Error = $this->GetError(); $this->db_ErrorSQL = $strSql; if (!$bIgnoreErrors) { AddMessage2Log($error_position . " MySql Query Error: " . $strSql . " [" . $this->db_Error . "]", "main"); if ($this->DebugToFile) { $this->startSqlTracker()->writeFileLog("ERROR: " . $this->db_Error, 0, "CONN: " . $this->getThreadId()); } if ($this->debug || @session_start() && $_SESSION["SESS_AUTH"]["ADMIN"]) { echo $error_position . "<br><font color=#ff0000>MySQL Query Error: " . htmlspecialcharsbx($strSql) . "</font>[" . htmlspecialcharsbx($this->db_Error) . "]<br>"; } $error_position = preg_replace("#<br[^>]*>#i", "\n", $error_position); SendError($error_position . "\nMySQL Query Error:\n" . $strSql . " \n [" . $this->db_Error . "]\n---------------\n\n"); if (file_exists($_SERVER["DOCUMENT_ROOT"] . BX_PERSONAL_ROOT . "/php_interface/dbquery_error.php")) { include $_SERVER["DOCUMENT_ROOT"] . BX_PERSONAL_ROOT . "/php_interface/dbquery_error.php"; } elseif (file_exists($_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/main/include/dbquery_error.php")) { include $_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/main/include/dbquery_error.php"; } else { die("MySQL Query Error!"); } die; } return false; } $res = new CDBResult($result); $res->DB = $this; if ($DB->ShowSqlStat) { $res->SqlTraceIndex = count($DB->arQueryDebug) - 1; } return $res; }
break; case "resume": CClusterSlave::Resume($ID); break; case "stop": CClusterSlave::Stop($ID); break; case "skip_sql_error": CClusterSlave::SkipSQLError($ID); break; } } } $arHeaders = array(array("id" => "ID", "content" => GetMessage("CLU_SLAVE_LIST_ID"), "align" => "right", "default" => true), array("id" => "FLAG", "content" => GetMessage("CLU_SLAVE_LIST_FLAG"), "align" => "center", "default" => true), array("id" => "NAME", "content" => GetMessage("CLU_SLAVE_LIST_NAME"), "align" => "left", "default" => true), array("id" => "BEHIND", "content" => GetMessage("CLU_SLAVE_LIST_BEHIND"), "align" => "right", "default" => true), array("id" => "STATUS", "content" => GetMessage("CLU_SLAVE_LIST_STATUS"), "align" => "center", "default" => true), array("id" => "WEIGHT", "content" => GetMessage("CLU_SLAVE_LIST_WEIGHT"), "align" => "right", "default" => true), array("id" => "DESCRIPTION", "content" => GetMessage("CLU_SLAVE_LIST_DESCRIPTION"), "align" => "left", "default" => false), array("id" => "DB_HOST", "content" => GetMessage("CLU_SLAVE_LIST_DB_HOST"), "align" => "left", "default" => false), array("id" => "DB_NAME", "content" => GetMessage("CLU_SLAVE_LIST_DB_NAME"), "align" => "left", "default" => false), array("id" => "DB_LOGIN", "content" => GetMessage("CLU_SLAVE_LIST_DB_LOGIN"), "align" => "left", "default" => false)); $lAdmin->AddHeaders($arHeaders); $cData = new CClusterDBNode(); $rsData = $cData->GetList(array("ID" => "ASC"), array("=ROLE_ID" => array("MAIN", "SLAVE", "MASTER"), "=GROUP_ID" => $group_id)); if (!isset($_SESSION["SLAVE_LIST"])) { $_SESSION["SLAVE_LIST"] = array(); } $rsData = new CAdminResult($rsData, $sTableID); $Position = 0; $bNote1Show = false; $bHasMaster = false; while ($arRes = $rsData->Fetch()) { $row =& $lAdmin->AddRow($arRes["ID"], $arRes); if ($arRes["ROLE_ID"] == "MASTER" || $arRes["ROLE_ID"] == "MAIN") { $bHasMaster = true; } $arSlaveStatus = CClusterSlave::GetStatus($arRes["ID"]); if (is_array($arSlaveStatus) && $arRes["STATUS"] == "OFFLINE") {