From c7dbea3f126931e26f48f960a60154771a401161 Mon Sep 17 00:00:00 2001 From: helpfulrobot Date: Fri, 18 Dec 2015 09:30:16 +1300 Subject: [PATCH] Converted to PSR-2 --- code/DataIntegrityTest.php | 948 +++++++++--------- code/DataIntegrityTestInnoDB.php | 155 +-- code/DataIntegrityTestUTF8.php | 195 ++-- code/DataIntegrityTestYML.php | 224 ++--- code/model/DataIntegrityTestDefaulEntries.php | 66 +- 5 files changed, 790 insertions(+), 798 deletions(-) diff --git a/code/DataIntegrityTest.php b/code/DataIntegrityTest.php index 1c74e62..c481230 100644 --- a/code/DataIntegrityTest.php +++ b/code/DataIntegrityTest.php @@ -1,473 +1,475 @@ - - "SELECT SiteTree.ID, SiteTree.Title FROM SiteTree_Live RIGHT JOIN SiteTree ON SiteTree_Live.ID = SiteTree.ID WHERE SiteTree.ID IS NULL;", - "ParentID does not exist in SiteTree" => - "SELECT SiteTree.ID, SiteTree.Title FROM SiteTree RIGHT JOIN SiteTree Parent ON SiteTree.ParentID = Parent.ID Where SiteTree.ID IS NULL and SiteTree.ParentID <> 0;", - "ParentID does not exists in SiteTree_Live" => - "SELECT SiteTree_Live.ID, SiteTree_Live.Title FROM SiteTree_Live RIGHT JOIN SiteTree_Live Parent ON SiteTree_Live.ParentID = Parent.ID Where SiteTree_Live.ID IS NULL and SiteTree_Live.ParentID <> 0;", - ); - - private static $global_exceptions = array( - "EditableFormField" => "Version", - "EditableOption" => "Version", - "OrderItem" => "Version" - ); - - /** - *@param array = should be provided as follows: array("Member.UselessField1", "Member.UselessField2", "SiteTree.UselessField3") - */ - private static $fields_to_delete = array(); - - private static $allowed_actions = array( - "obsoletefields" => "ADMIN", - "deleteonefield" => "ADMIN", - "deletemarkedfields" => "ADMIN", - "deleteobsoletetables" => "ADMIN", - "deleteallversions" => "ADMIN", - "cleanupdb" => "ADMIN" - ); - - - function init() { - //this checks security - parent::init(); - } - - function run($request) { - ini_set('max_execution_time', 3000); - if($action = $request->getVar("do")) { - $methodArray = explode("/", $action); - $method = $methodArray[0]; - $allowedActions = Config::inst()->get("DataIntegrityTest", "allowed_actions"); - if(isset($allowedActions[$method])) { - if($method == "obsoletefields") { - $deletesafeones = $fixbrokendataobjects = $deleteall = false; - if(isset($_GET["deletesafeones"]) && $_GET["deletesafeones"]) {$deletesafeones = true;} - if(isset($_GET["fixbrokendataobjects"]) && $_GET["fixbrokendataobjects"]) {$fixbrokendataobjects = true;} - if(isset($_GET["deleteall"]) && $_GET["deleteall"]) {$deleteall = true;} - return $this->$method($deletesafeones, $fixbrokendataobjects, $deleteall); - } - else { - return $this->$method(); - } - } - else { - user_error("could not find method: $method"); - } - } - $warning = Config::inst()->get("DataIntegrityTest", "warning"); - echo "

Database Administration Helpers

"; - echo "

Link()."?do=obsoletefields\">Prepare a list of obsolete fields.

"; - echo "

Link()."?do=obsoletefields&deletesafeones=1\" onclick=\"return confirm('".$warning."');\">Prepare a list of obsolete fields and DELETE! obsolete fields without any data.

"; - echo "

Link()."?do=obsoletefields&fixbrokendataobjects=1\" onclick=\"return confirm('".$warning."');\">Fix broken dataobjects.

"; - echo "

Link()."?do=obsoletefields&deleteall=1\" onclick=\"return confirm('".$warning."');\">Delete all obsolete fields now!

"; - echo "
"; - echo "

Link()."?do=deletemarkedfields\" onclick=\"return confirm('".$warning."');\">Delete fields listed in _config.

"; - echo "
"; - echo "

Link()."?do=deleteobsoletetables\" onclick=\"return confirm('".$warning."');\">Delete all tables that are marked as obsolete

"; - echo "
"; - echo "

Link()."?do=deleteallversions\" onclick=\"return confirm('".$warning."');\">Delete all versioned data

"; - echo "
"; - echo "

Link()."?do=cleanupdb\" onclick=\"return confirm('".$warning."');\">Clean up Database (remove obsolete records)

"; - echo "
"; - echo "

Set all tables to innoDB

"; - echo "

Set all tables to utf-8

"; - } - - protected function Link(){ - return "/dev/tasks/DataIntegrityTest/"; - } - - protected function obsoletefields($deleteSafeOnes = false, $fixBrokenDataObject = false, $deleteAll = false) { - increase_time_limit_to(600); - $dataClasses = ClassInfo::subclassesFor('DataObject'); - $notCheckedArray = array(); - $canBeSafelyDeleted = array(); - //remove dataobject - array_shift($dataClasses); - $rows = DB::query("SHOW TABLES;"); - $actualTables = array(); - if($rows) { - foreach($rows as $key => $item) { - foreach($item as $table) { - $actualTables[$table] = $table; - } - } - } - echo "

Report of fields that may not be required.

"; - echo "

NOTE: it may contain fields that are actually required (e.g. versioning or many-many relationships) and it may also leave out some obsolete fields. Use as a guide only.

"; - foreach($dataClasses as $dataClass) { - // Check if class exists before trying to instantiate - this sidesteps any manifest weirdness - if(class_exists($dataClass)) { - $dataObject = $dataClass::create(); - if(!($dataObject instanceof TestOnly)) { - $requiredFields = $this->swapArray(DataObject::database_fields($dataObject->ClassName)); - if(count($requiredFields)) { - foreach($requiredFields as $field) { - if(!$dataObject->hasOwnTableDatabaseField($field)) { - DB::alteration_message (" **** $dataClass.$field DOES NOT EXIST BUT IT SHOULD BE THERE!", "deleted"); - } - } - $actualFields = $this->swapArray(DB::fieldList($dataClass)); - if($actualFields) { - foreach($actualFields as $actualField) { - if($deleteAll) { - $link = " !!!!!!!!!!! DELETED !!!!!!!!!"; - } - else { - $warning = Config::inst()->get("DataIntegrityTest", "warning"); - $link = "delete field"; - } - if(!in_array($actualField, array("ID", "Version"))) { - if(!in_array($actualField, $requiredFields)) { - $distinctCount = DB::query("SELECT COUNT(DISTINCT \"$actualField\") FROM \"$dataClass\" WHERE \"$actualField\" IS NOT NULL AND \"$actualField\" <> '' AND \"$actualField\" <> '0';")->value(); - DB::alteration_message ("

\n\n$dataClass.$actualField $link - unique entries: $distinctCount", "deleted"); - if($distinctCount) { - $rows = DB::query(" - SELECT \"$actualField\" as N, COUNT(\"$actualField\") as C - FROM \"$dataClass\" - GROUP BY \"$actualField\" - ORDER BY C DESC - LIMIT 7"); - if($rows) { - foreach($rows as $row) { - DB::alteration_message ("       ".$row["C"].": ".$row["N"]); - } - } - } - else { - if(!isset($canBeSafelyDeleted[$dataClass])) { - $canBeSafelyDeleted[$dataClass] = array(); - } - $canBeSafelyDeleted[$dataClass][$actualField] = "$dataClass.$actualField"; - } - if($deleteAll || ($deleteSafeOnes && $distinctCount == 0)) { - $this->deleteField($dataClass, $actualField); - } - } - } - if($actualField == "Version" && !in_array($actualField, $requiredFields)) { - $versioningPresent = $dataObject->hasVersioning(); - if(!$versioningPresent) { - DB::alteration_message ("$dataClass.$actualField $link", "deleted"); - if($deleteAll) { - $this->deleteField($dataClass, $actualField); - } - } - } - } - } - $rawCount = DB::query("SELECT COUNT(\"ID\") FROM \"$dataClass\"")->value(); - Versioned::set_reading_mode("Stage.Stage"); - $realCount = 0; - $allSubClasses = array_unique(array($dataClass)+ClassInfo::subclassesFor($dataClass)); - $objects = $dataClass::get()->filter(array("ClassName" => $allSubClasses)); - if($objects->count()) { - $realCount = $objects->count(); - } - if($rawCount != $realCount) { - echo "
"; - $sign = " > "; - if($rawCount < $realCount) { - $sign = " < "; - } - DB::alteration_message("The DB Table Row Count does not seem to match the DataObject Count for $dataClass ($rawCount $sign $realCount). This could indicate an error as generally these numbers should match.", "deleted"); - if($fixBrokenDataObject) { - $objects = $dataClass::get()->where("LinkedTable.ID IS NULL")->leftJoin($dataClass, "$dataClass.ID = LinkedTable.ID", "LinkedTable"); - if($objects->count() > 500) { - DB::alteration_message("It is recommended that you manually fix the difference in real vs object count in $dataClass. There are more than 500 records so it would take too long to do it now.", "deleted"); - } - else { - DB::alteration_message("Now trying to recreate missing items... COUNT = ".$objects->count(), "created"); - foreach($objects as $object) { - if(DB::query("SELECT COUNT(\"ID\") FROM \"$dataClass\" WHERE \"ID\" = ".$object->ID.";")->value() != 1) { - Config::inst()->update('DataObject', 'validation_enabled', false); - $object->write(true, false, true, false); - Config::inst()->update('DataObject', 'validation_enabled', true); - } - } - $objectCount = $dataClass::get()->count(); - DB::alteration_message("Consider deleting superfluous records from table $dataClass .... COUNT =".($rawCount - $objectCount)); - $ancestors = ClassInfo::ancestry($dataClass, true); - if($ancestors && is_array($ancestors) && count($ancestors)) { - foreach($ancestors as $ancestor) { - if($ancestor != $dataClass) { - echo "DELETE `$dataClass`.* FROM `$dataClass` LEFT JOIN `$ancestor` ON `$dataClass`.`ID` = `$ancestor`.`ID` WHERE `$ancestor`.`ID` IS NULL;"; - DB::query("DELETE `$dataClass`.* FROM `$dataClass` LEFT JOIN `$ancestor` ON `$dataClass`.`ID` = `$ancestor`.`ID` WHERE `$ancestor`.`ID` IS NULL;"); - } - } - } - } - } - echo "
"; - } - unset($actualTables[$dataClass]); - } - else { - $db = DB::getConn(); - if($db->hasTable($dataClass)) { - DB::alteration_message (" **** The $dataClass table exists, but according to the data-scheme it should not be there ", "deleted"); - } - else { - $notCheckedArray[] = $dataClass; - } - } - } - } - } - - if(count($canBeSafelyDeleted)) { - DB::alteration_message("

Can be safely deleted:

"); - foreach($canBeSafelyDeleted as $table => $fields) { - DB::alteration_message($table.": ".implode(", ", $fields)); - } - } - - if(count($notCheckedArray)) { - echo "

Did not check the following classes as no fields appear to be required and hence there is no database table.

"; - foreach($notCheckedArray as $table) { - if( DB::query("SHOW TABLES LIKE '".$table."'")->value()) { - DB::alteration_message ($table ." - NOTE: a table exists for this Class, this is an unexpected result", "deleted"); - } - else { - DB::alteration_message ($table, "created"); - } - } - } - - if(count($actualTables)) { - echo "

Other Tables in Database not directly linked to a Silverstripe DataObject:

"; - foreach($actualTables as $table) { - $remove = true; - if(class_exists($table)) { - $classExistsMessage = " a PHP class with this name exists."; - $obj = singleton($table); - //not sure why we have this. - if($obj instanceof DataExtension) { - $remove = false; - } - elseif(class_exists("Versioned") && $obj->hasExtension("Versioned")) { - $remove = false; - } - } - else { - $classExistsMessage = " NO PHP class with this name exists."; - if(substr($table, -5) == "_Live") { - $remove = false; - } - if(substr($table, -9) == "_versions") { - $remove = false; - } - //many 2 many tables... - if(strpos($table, "_")) { - $class = explode("_", $table); - $manyManyClass = substr($table, 0, strrpos($table, '_') ); - $manyManyExtension = substr($table, strrpos($table, '_') + 1 - strlen($table)); - if(class_exists($manyManyClass)) { - $manyManys = Config::inst()->get($manyManyClass, "many_many"); - if(isset($manyManys[$manyManyExtension])) { - $remove = false; - } - } - } - } - if($remove) { - if(substr($table, 0, strlen("_obsolete_")) != "_obsolete_") { - $rowCount = DB::query("SELECT COUNT(*) FROM $table")->value(); - DB::alteration_message($table.", rows ".$rowCount); - $obsoleteTableName = "_obsolete_".$table; - if(!$this->tableExists($obsoleteTableName)) { - DB::alteration_message ("We recommend deleting $table or making it obsolete by renaming it to ".$obsoleteTableName, "deleted"); - if($deleteAll) { - DB::getConn()->renameTable($table, $obsoleteTableName); - } - else { - DB::alteration_message ($table." - ".$classExistsMessage." It can be moved to _obsolete_".$table."." , "created"); - } - } - else { - DB::alteration_message ("I'd recommend to move $table to ".$obsoleteTableName.", but that table already exists" , "deleted"); - } - } - } - } - } - - echo "back to main menu."; - } - - - - public function deletemarkedfields() { - $fieldsToDelete = Config::inst()->get("DataIntegrityTest", "fields_to_delete"); - if(is_array($fieldsToDelete)) { - if(count($fieldsToDelete)) { - foreach($fieldsToDelete as $key => $tableDotField) { - $tableFieldArray = explode(".", $tableDotField); - $this->deleteField($tableFieldArray[0], $tableFieldArray[1]); - } - } - else { - DB::alteration_message("there are no fields to delete", "created"); - } - } - else { - user_error("you need to select these fields to be deleted first (DataIntegrityTest.fields_to_delete)"); - } - echo "back to main menu."; - } - - public function deleteonefield() { - $requestExploded = explode("/", $_GET["do"]); - if(!isset($requestExploded[1])) { - user_error("no table has been specified", E_USER_WARNING); - } - if(!isset($requestExploded[2])) { - user_error("no field has been specified", E_USER_WARNING); - } - $table = $requestExploded[1]; - $field = $requestExploded[2]; - if($this->deleteField($table, $field)) { - DB::alteration_message("successfully deleted $field from $table now"); - } - else { - DB::alteration_message("COULD NOT delete $field from $table now", "deleted"); - } - DB::alteration_message("return to list of obsolete fields", "created"); - echo "back to main menu."; - } - - private function cleanupdb(){ - $obj = new DatabaseAdmin(); - $obj->cleanup(); - DB::alteration_message("============= COMPLETED =================", ""); - echo "back to main menu."; - } - - private function deleteField($table, $field) { - $fields = $this->swapArray(DB::fieldList($table)); - $globalExeceptions = Config::inst()->get("DataIntegrityTest", "global_exceptions"); - if(count($globalExeceptions)) { - foreach($globalExeceptions as $exceptionTable => $exceptionField) { - if($exceptionTable == $table && $exceptionField == $field) { - DB::alteration_message ("tried to delete $table.$field but this is listed as a global exception and can not be deleted", "created"); - return false; - } - } - } - if(!DB::query("SHOW TABLES LIKE '".$table."'")->value()) { - DB::alteration_message ("tried to delete $table.$field but TABLE does not exist", "deleted"); - return false; - } - if(!class_exists($table)){ - DB::alteration_message ("tried to delete $table.$field but CLASS does not exist", "deleted"); - return false; - } - if(!in_array($field, $fields)) { - DB::alteration_message ("tried to delete $table.$field but FIELD does not exist", "deleted"); - return false; - } - else { - DB::alteration_message ("Deleting $field in $table", "deleted"); - DB::query('ALTER TABLE "'.$table.'" DROP "'.$field.'";'); - $obj = singleton($table); - //to do: make this more reliable - checking for versioning rather than SiteTree - if($obj instanceof SiteTree) { - DB::query('ALTER TABLE "'.$table.'_Live" DROP "'.$field.'";'); - DB::alteration_message ("Deleted $field in {$table}_Live", "deleted"); - DB::query('ALTER TABLE "'.$table.'_versions" DROP "'.$field.'";'); - DB::alteration_message ("Deleted $field in {$table}_versions", "deleted"); - } - return true; - } - } - - private function swapArray($array) { - $newArray = array(); - if(is_array($array)) { - foreach($array as $key => $value) { - $newArray[] = $key; - } - } - return $newArray; - } - - protected function hasVersioning($dataObject) { - $versioningPresent = false; - $array = $dataObject->stat('extensions'); - if(is_array($array) && count($array)) { - if(in_array("Versioned('Stage', 'Live')", $array)) { - $versioningPresent = true; - } - } - if($dataObject->stat('versioning')) { - $versioningPresent = true; - } - return $versioningPresent; - } - - - private function deleteobsoletetables(){ - $tables = DB::query('SHOW tables'); - $unique = array(); - foreach ($tables as $table) { - $table = array_pop($table); - if(substr($table, 0, 10) == "_obsolete_") { - DB::alteration_message("Removing table $table", "deleted"); - DB::query("DROP TABLE \"$table\" "); - } - } - echo "back to main menu."; - } - - private function deleteallversions(){ - $tables = DB::query('SHOW tables'); - $unique = array(); - foreach ($tables as $table) { - $table = array_pop($table); - $endOfTable = substr($table, -9); - if($endOfTable == "_versions") { - $className = substr($table, 0, strlen($table) - 9); - if(class_exists($className)) { - $obj = $className::get()->first(); - if($obj) { - if($obj->hasExtension("Versioned")) { - DB::alteration_message("Removing all records from $table", "created"); - DB::query("DELETE FROM \"$table\" "); - } - } - } - else { - DB::alteration_message("Could not find $className class... the $table may be obsolete", "deleted"); - } - } - } - echo "back to main menu."; - } - - private function tableExists($table){ - $db = DB::getConn(); - return $db->hasTable($table); - } - -} + + "SELECT SiteTree.ID, SiteTree.Title FROM SiteTree_Live RIGHT JOIN SiteTree ON SiteTree_Live.ID = SiteTree.ID WHERE SiteTree.ID IS NULL;", + "ParentID does not exist in SiteTree" => + "SELECT SiteTree.ID, SiteTree.Title FROM SiteTree RIGHT JOIN SiteTree Parent ON SiteTree.ParentID = Parent.ID Where SiteTree.ID IS NULL and SiteTree.ParentID <> 0;", + "ParentID does not exists in SiteTree_Live" => + "SELECT SiteTree_Live.ID, SiteTree_Live.Title FROM SiteTree_Live RIGHT JOIN SiteTree_Live Parent ON SiteTree_Live.ParentID = Parent.ID Where SiteTree_Live.ID IS NULL and SiteTree_Live.ParentID <> 0;", + ); + + private static $global_exceptions = array( + "EditableFormField" => "Version", + "EditableOption" => "Version", + "OrderItem" => "Version" + ); + + /** + *@param array = should be provided as follows: array("Member.UselessField1", "Member.UselessField2", "SiteTree.UselessField3") + */ + private static $fields_to_delete = array(); + + private static $allowed_actions = array( + "obsoletefields" => "ADMIN", + "deleteonefield" => "ADMIN", + "deletemarkedfields" => "ADMIN", + "deleteobsoletetables" => "ADMIN", + "deleteallversions" => "ADMIN", + "cleanupdb" => "ADMIN" + ); + + + public function init() + { + //this checks security + parent::init(); + } + + public function run($request) + { + ini_set('max_execution_time', 3000); + if ($action = $request->getVar("do")) { + $methodArray = explode("/", $action); + $method = $methodArray[0]; + $allowedActions = Config::inst()->get("DataIntegrityTest", "allowed_actions"); + if (isset($allowedActions[$method])) { + if ($method == "obsoletefields") { + $deletesafeones = $fixbrokendataobjects = $deleteall = false; + if (isset($_GET["deletesafeones"]) && $_GET["deletesafeones"]) { + $deletesafeones = true; + } + if (isset($_GET["fixbrokendataobjects"]) && $_GET["fixbrokendataobjects"]) { + $fixbrokendataobjects = true; + } + if (isset($_GET["deleteall"]) && $_GET["deleteall"]) { + $deleteall = true; + } + return $this->$method($deletesafeones, $fixbrokendataobjects, $deleteall); + } else { + return $this->$method(); + } + } else { + user_error("could not find method: $method"); + } + } + $warning = Config::inst()->get("DataIntegrityTest", "warning"); + echo "

Database Administration Helpers

"; + echo "

Link()."?do=obsoletefields\">Prepare a list of obsolete fields.

"; + echo "

Link()."?do=obsoletefields&deletesafeones=1\" onclick=\"return confirm('".$warning."');\">Prepare a list of obsolete fields and DELETE! obsolete fields without any data.

"; + echo "

Link()."?do=obsoletefields&fixbrokendataobjects=1\" onclick=\"return confirm('".$warning."');\">Fix broken dataobjects.

"; + echo "

Link()."?do=obsoletefields&deleteall=1\" onclick=\"return confirm('".$warning."');\">Delete all obsolete fields now!

"; + echo "
"; + echo "

Link()."?do=deletemarkedfields\" onclick=\"return confirm('".$warning."');\">Delete fields listed in _config.

"; + echo "
"; + echo "

Link()."?do=deleteobsoletetables\" onclick=\"return confirm('".$warning."');\">Delete all tables that are marked as obsolete

"; + echo "
"; + echo "

Link()."?do=deleteallversions\" onclick=\"return confirm('".$warning."');\">Delete all versioned data

"; + echo "
"; + echo "

Link()."?do=cleanupdb\" onclick=\"return confirm('".$warning."');\">Clean up Database (remove obsolete records)

"; + echo "
"; + echo "

Set all tables to innoDB

"; + echo "

Set all tables to utf-8

"; + } + + protected function Link() + { + return "/dev/tasks/DataIntegrityTest/"; + } + + protected function obsoletefields($deleteSafeOnes = false, $fixBrokenDataObject = false, $deleteAll = false) + { + increase_time_limit_to(600); + $dataClasses = ClassInfo::subclassesFor('DataObject'); + $notCheckedArray = array(); + $canBeSafelyDeleted = array(); + //remove dataobject + array_shift($dataClasses); + $rows = DB::query("SHOW TABLES;"); + $actualTables = array(); + if ($rows) { + foreach ($rows as $key => $item) { + foreach ($item as $table) { + $actualTables[$table] = $table; + } + } + } + echo "

Report of fields that may not be required.

"; + echo "

NOTE: it may contain fields that are actually required (e.g. versioning or many-many relationships) and it may also leave out some obsolete fields. Use as a guide only.

"; + foreach ($dataClasses as $dataClass) { + // Check if class exists before trying to instantiate - this sidesteps any manifest weirdness + if (class_exists($dataClass)) { + $dataObject = $dataClass::create(); + if (!($dataObject instanceof TestOnly)) { + $requiredFields = $this->swapArray(DataObject::database_fields($dataObject->ClassName)); + if (count($requiredFields)) { + foreach ($requiredFields as $field) { + if (!$dataObject->hasOwnTableDatabaseField($field)) { + DB::alteration_message(" **** $dataClass.$field DOES NOT EXIST BUT IT SHOULD BE THERE!", "deleted"); + } + } + $actualFields = $this->swapArray(DB::fieldList($dataClass)); + if ($actualFields) { + foreach ($actualFields as $actualField) { + if ($deleteAll) { + $link = " !!!!!!!!!!! DELETED !!!!!!!!!"; + } else { + $warning = Config::inst()->get("DataIntegrityTest", "warning"); + $link = "delete field"; + } + if (!in_array($actualField, array("ID", "Version"))) { + if (!in_array($actualField, $requiredFields)) { + $distinctCount = DB::query("SELECT COUNT(DISTINCT \"$actualField\") FROM \"$dataClass\" WHERE \"$actualField\" IS NOT NULL AND \"$actualField\" <> '' AND \"$actualField\" <> '0';")->value(); + DB::alteration_message("

\n\n$dataClass.$actualField $link - unique entries: $distinctCount", "deleted"); + if ($distinctCount) { + $rows = DB::query(" + SELECT \"$actualField\" as N, COUNT(\"$actualField\") as C + FROM \"$dataClass\" + GROUP BY \"$actualField\" + ORDER BY C DESC + LIMIT 7"); + if ($rows) { + foreach ($rows as $row) { + DB::alteration_message("       ".$row["C"].": ".$row["N"]); + } + } + } else { + if (!isset($canBeSafelyDeleted[$dataClass])) { + $canBeSafelyDeleted[$dataClass] = array(); + } + $canBeSafelyDeleted[$dataClass][$actualField] = "$dataClass.$actualField"; + } + if ($deleteAll || ($deleteSafeOnes && $distinctCount == 0)) { + $this->deleteField($dataClass, $actualField); + } + } + } + if ($actualField == "Version" && !in_array($actualField, $requiredFields)) { + $versioningPresent = $dataObject->hasVersioning(); + if (!$versioningPresent) { + DB::alteration_message("$dataClass.$actualField $link", "deleted"); + if ($deleteAll) { + $this->deleteField($dataClass, $actualField); + } + } + } + } + } + $rawCount = DB::query("SELECT COUNT(\"ID\") FROM \"$dataClass\"")->value(); + Versioned::set_reading_mode("Stage.Stage"); + $realCount = 0; + $allSubClasses = array_unique(array($dataClass)+ClassInfo::subclassesFor($dataClass)); + $objects = $dataClass::get()->filter(array("ClassName" => $allSubClasses)); + if ($objects->count()) { + $realCount = $objects->count(); + } + if ($rawCount != $realCount) { + echo "
"; + $sign = " > "; + if ($rawCount < $realCount) { + $sign = " < "; + } + DB::alteration_message("The DB Table Row Count does not seem to match the DataObject Count for $dataClass ($rawCount $sign $realCount). This could indicate an error as generally these numbers should match.", "deleted"); + if ($fixBrokenDataObject) { + $objects = $dataClass::get()->where("LinkedTable.ID IS NULL")->leftJoin($dataClass, "$dataClass.ID = LinkedTable.ID", "LinkedTable"); + if ($objects->count() > 500) { + DB::alteration_message("It is recommended that you manually fix the difference in real vs object count in $dataClass. There are more than 500 records so it would take too long to do it now.", "deleted"); + } else { + DB::alteration_message("Now trying to recreate missing items... COUNT = ".$objects->count(), "created"); + foreach ($objects as $object) { + if (DB::query("SELECT COUNT(\"ID\") FROM \"$dataClass\" WHERE \"ID\" = ".$object->ID.";")->value() != 1) { + Config::inst()->update('DataObject', 'validation_enabled', false); + $object->write(true, false, true, false); + Config::inst()->update('DataObject', 'validation_enabled', true); + } + } + $objectCount = $dataClass::get()->count(); + DB::alteration_message("Consider deleting superfluous records from table $dataClass .... COUNT =".($rawCount - $objectCount)); + $ancestors = ClassInfo::ancestry($dataClass, true); + if ($ancestors && is_array($ancestors) && count($ancestors)) { + foreach ($ancestors as $ancestor) { + if ($ancestor != $dataClass) { + echo "DELETE `$dataClass`.* FROM `$dataClass` LEFT JOIN `$ancestor` ON `$dataClass`.`ID` = `$ancestor`.`ID` WHERE `$ancestor`.`ID` IS NULL;"; + DB::query("DELETE `$dataClass`.* FROM `$dataClass` LEFT JOIN `$ancestor` ON `$dataClass`.`ID` = `$ancestor`.`ID` WHERE `$ancestor`.`ID` IS NULL;"); + } + } + } + } + } + echo "
"; + } + unset($actualTables[$dataClass]); + } else { + $db = DB::getConn(); + if ($db->hasTable($dataClass)) { + DB::alteration_message(" **** The $dataClass table exists, but according to the data-scheme it should not be there ", "deleted"); + } else { + $notCheckedArray[] = $dataClass; + } + } + } + } + } + + if (count($canBeSafelyDeleted)) { + DB::alteration_message("

Can be safely deleted:

"); + foreach ($canBeSafelyDeleted as $table => $fields) { + DB::alteration_message($table.": ".implode(", ", $fields)); + } + } + + if (count($notCheckedArray)) { + echo "

Did not check the following classes as no fields appear to be required and hence there is no database table.

"; + foreach ($notCheckedArray as $table) { + if (DB::query("SHOW TABLES LIKE '".$table."'")->value()) { + DB::alteration_message($table ." - NOTE: a table exists for this Class, this is an unexpected result", "deleted"); + } else { + DB::alteration_message($table, "created"); + } + } + } + + if (count($actualTables)) { + echo "

Other Tables in Database not directly linked to a Silverstripe DataObject:

"; + foreach ($actualTables as $table) { + $remove = true; + if (class_exists($table)) { + $classExistsMessage = " a PHP class with this name exists."; + $obj = singleton($table); + //not sure why we have this. + if ($obj instanceof DataExtension) { + $remove = false; + } elseif (class_exists("Versioned") && $obj->hasExtension("Versioned")) { + $remove = false; + } + } else { + $classExistsMessage = " NO PHP class with this name exists."; + if (substr($table, -5) == "_Live") { + $remove = false; + } + if (substr($table, -9) == "_versions") { + $remove = false; + } + //many 2 many tables... + if (strpos($table, "_")) { + $class = explode("_", $table); + $manyManyClass = substr($table, 0, strrpos($table, '_')); + $manyManyExtension = substr($table, strrpos($table, '_') + 1 - strlen($table)); + if (class_exists($manyManyClass)) { + $manyManys = Config::inst()->get($manyManyClass, "many_many"); + if (isset($manyManys[$manyManyExtension])) { + $remove = false; + } + } + } + } + if ($remove) { + if (substr($table, 0, strlen("_obsolete_")) != "_obsolete_") { + $rowCount = DB::query("SELECT COUNT(*) FROM $table")->value(); + DB::alteration_message($table.", rows ".$rowCount); + $obsoleteTableName = "_obsolete_".$table; + if (!$this->tableExists($obsoleteTableName)) { + DB::alteration_message("We recommend deleting $table or making it obsolete by renaming it to ".$obsoleteTableName, "deleted"); + if ($deleteAll) { + DB::getConn()->renameTable($table, $obsoleteTableName); + } else { + DB::alteration_message($table." - ".$classExistsMessage." It can be moved to _obsolete_".$table.".", "created"); + } + } else { + DB::alteration_message("I'd recommend to move $table to ".$obsoleteTableName.", but that table already exists", "deleted"); + } + } + } + } + } + + echo "back to main menu."; + } + + + + public function deletemarkedfields() + { + $fieldsToDelete = Config::inst()->get("DataIntegrityTest", "fields_to_delete"); + if (is_array($fieldsToDelete)) { + if (count($fieldsToDelete)) { + foreach ($fieldsToDelete as $key => $tableDotField) { + $tableFieldArray = explode(".", $tableDotField); + $this->deleteField($tableFieldArray[0], $tableFieldArray[1]); + } + } else { + DB::alteration_message("there are no fields to delete", "created"); + } + } else { + user_error("you need to select these fields to be deleted first (DataIntegrityTest.fields_to_delete)"); + } + echo "back to main menu."; + } + + public function deleteonefield() + { + $requestExploded = explode("/", $_GET["do"]); + if (!isset($requestExploded[1])) { + user_error("no table has been specified", E_USER_WARNING); + } + if (!isset($requestExploded[2])) { + user_error("no field has been specified", E_USER_WARNING); + } + $table = $requestExploded[1]; + $field = $requestExploded[2]; + if ($this->deleteField($table, $field)) { + DB::alteration_message("successfully deleted $field from $table now"); + } else { + DB::alteration_message("COULD NOT delete $field from $table now", "deleted"); + } + DB::alteration_message("return to list of obsolete fields", "created"); + echo "back to main menu."; + } + + private function cleanupdb() + { + $obj = new DatabaseAdmin(); + $obj->cleanup(); + DB::alteration_message("============= COMPLETED =================", ""); + echo "back to main menu."; + } + + private function deleteField($table, $field) + { + $fields = $this->swapArray(DB::fieldList($table)); + $globalExeceptions = Config::inst()->get("DataIntegrityTest", "global_exceptions"); + if (count($globalExeceptions)) { + foreach ($globalExeceptions as $exceptionTable => $exceptionField) { + if ($exceptionTable == $table && $exceptionField == $field) { + DB::alteration_message("tried to delete $table.$field but this is listed as a global exception and can not be deleted", "created"); + return false; + } + } + } + if (!DB::query("SHOW TABLES LIKE '".$table."'")->value()) { + DB::alteration_message("tried to delete $table.$field but TABLE does not exist", "deleted"); + return false; + } + if (!class_exists($table)) { + DB::alteration_message("tried to delete $table.$field but CLASS does not exist", "deleted"); + return false; + } + if (!in_array($field, $fields)) { + DB::alteration_message("tried to delete $table.$field but FIELD does not exist", "deleted"); + return false; + } else { + DB::alteration_message("Deleting $field in $table", "deleted"); + DB::query('ALTER TABLE "'.$table.'" DROP "'.$field.'";'); + $obj = singleton($table); + //to do: make this more reliable - checking for versioning rather than SiteTree + if ($obj instanceof SiteTree) { + DB::query('ALTER TABLE "'.$table.'_Live" DROP "'.$field.'";'); + DB::alteration_message("Deleted $field in {$table}_Live", "deleted"); + DB::query('ALTER TABLE "'.$table.'_versions" DROP "'.$field.'";'); + DB::alteration_message("Deleted $field in {$table}_versions", "deleted"); + } + return true; + } + } + + private function swapArray($array) + { + $newArray = array(); + if (is_array($array)) { + foreach ($array as $key => $value) { + $newArray[] = $key; + } + } + return $newArray; + } + + protected function hasVersioning($dataObject) + { + $versioningPresent = false; + $array = $dataObject->stat('extensions'); + if (is_array($array) && count($array)) { + if (in_array("Versioned('Stage', 'Live')", $array)) { + $versioningPresent = true; + } + } + if ($dataObject->stat('versioning')) { + $versioningPresent = true; + } + return $versioningPresent; + } + + + private function deleteobsoletetables() + { + $tables = DB::query('SHOW tables'); + $unique = array(); + foreach ($tables as $table) { + $table = array_pop($table); + if (substr($table, 0, 10) == "_obsolete_") { + DB::alteration_message("Removing table $table", "deleted"); + DB::query("DROP TABLE \"$table\" "); + } + } + echo "back to main menu."; + } + + private function deleteallversions() + { + $tables = DB::query('SHOW tables'); + $unique = array(); + foreach ($tables as $table) { + $table = array_pop($table); + $endOfTable = substr($table, -9); + if ($endOfTable == "_versions") { + $className = substr($table, 0, strlen($table) - 9); + if (class_exists($className)) { + $obj = $className::get()->first(); + if ($obj) { + if ($obj->hasExtension("Versioned")) { + DB::alteration_message("Removing all records from $table", "created"); + DB::query("DELETE FROM \"$table\" "); + } + } + } else { + DB::alteration_message("Could not find $className class... the $table may be obsolete", "deleted"); + } + } + } + echo "back to main menu."; + } + + private function tableExists($table) + { + $db = DB::getConn(); + return $db->hasTable($table); + } +} diff --git a/code/DataIntegrityTestInnoDB.php b/code/DataIntegrityTestInnoDB.php index c43fe73..a42b8fa 100644 --- a/code/DataIntegrityTestInnoDB.php +++ b/code/DataIntegrityTestInnoDB.php @@ -1,75 +1,80 @@ - \'InnoDB\''); - foreach ($tables as $table) { - $table = $table["Name"]; - DB::alteration_message("Updating $table to innoDB", "created");$this->flushNow(); - $indexRows = DB::query("SHOW INDEX FROM \"$table\" WHERE Index_type = 'FULLTEXT'"); - unset($done);$done = array(); - foreach($indexRows as $indexRow) { - $key = $indexRow["Key_name"]; - if(!isset($done[$key])) { - DB::alteration_message("Deleting INDEX $key in $table (FullText Index)", "deleted");$this->flushNow(); - DB::query("ALTER TABLE \"$table\" DROP INDEX $key;"); - $done[$key] = $key; - } - } - $sql = "ALTER TABLE \"$table\" ENGINE=INNODB"; - DB::query($sql); - } - //$rows = DB::query("SHOW GLOBAL STATUS LIKE 'Innodb_page_size'"); - $currentInnoDBSetting = DB::query("SELECT @@innodb_buffer_pool_size as V;")->Value(); - $innoDBBufferUsed = DB::query(" - -SELECT (PagesData*PageSize)/POWER(1024,3) DataGB FROM -(SELECT variable_value PagesData -FROM information_schema.global_status -WHERE variable_name='Innodb_buffer_pool_pages_data') A, -(SELECT variable_value PageSize -FROM information_schema.global_status -WHERE variable_name='Innodb_page_size') B; - - ")->value(); - $innoBDBufferRecommended = DB::query( " -SELECT CEILING(Total_InnoDB_Bytes*1.6/POWER(1024,3)) RIBPS FROM - (SELECT SUM(data_length+index_length) Total_InnoDB_Bytes - FROM information_schema.tables WHERE engine='InnoDB') A; -" - )->value(); - DB::alteration_message("






COMPLETED -
- Please check your MYSQL innodb_buffer_pool_size setting. - It is currently using ".round($innoDBBufferUsed, 3)."G, - but it should be set to ".round($innoBDBufferRecommended, 3)."G. - The current setting is: ".round($currentInnoDBSetting / (1042 * 1024* 1024))."G -






"); - } - - private function flushNow(){ - // check that buffer is actually set before flushing - if (ob_get_length()){ - @ob_flush(); - @flush(); - @ob_end_flush(); - } - @ob_start(); - } - -} + \'InnoDB\''); + foreach ($tables as $table) { + $table = $table["Name"]; + DB::alteration_message("Updating $table to innoDB", "created"); + $this->flushNow(); + $indexRows = DB::query("SHOW INDEX FROM \"$table\" WHERE Index_type = 'FULLTEXT'"); + unset($done); + $done = array(); + foreach ($indexRows as $indexRow) { + $key = $indexRow["Key_name"]; + if (!isset($done[$key])) { + DB::alteration_message("Deleting INDEX $key in $table (FullText Index)", "deleted"); + $this->flushNow(); + DB::query("ALTER TABLE \"$table\" DROP INDEX $key;"); + $done[$key] = $key; + } + } + $sql = "ALTER TABLE \"$table\" ENGINE=INNODB"; + DB::query($sql); + } + //$rows = DB::query("SHOW GLOBAL STATUS LIKE 'Innodb_page_size'"); + $currentInnoDBSetting = DB::query("SELECT @@innodb_buffer_pool_size as V;")->Value(); + $innoDBBufferUsed = DB::query(" + +SELECT (PagesData*PageSize)/POWER(1024,3) DataGB FROM +(SELECT variable_value PagesData +FROM information_schema.global_status +WHERE variable_name='Innodb_buffer_pool_pages_data') A, +(SELECT variable_value PageSize +FROM information_schema.global_status +WHERE variable_name='Innodb_page_size') B; + + ")->value(); + $innoBDBufferRecommended = DB::query(" +SELECT CEILING(Total_InnoDB_Bytes*1.6/POWER(1024,3)) RIBPS FROM + (SELECT SUM(data_length+index_length) Total_InnoDB_Bytes + FROM information_schema.tables WHERE engine='InnoDB') A; +" + )->value(); + DB::alteration_message("






COMPLETED +
+ Please check your MYSQL innodb_buffer_pool_size setting. + It is currently using ".round($innoDBBufferUsed, 3)."G, + but it should be set to ".round($innoBDBufferRecommended, 3)."G. + The current setting is: ".round($currentInnoDBSetting / (1042 * 1024* 1024))."G +






"); + } + + private function flushNow() + { + // check that buffer is actually set before flushing + if (ob_get_length()) { + @ob_flush(); + @flush(); + @ob_end_flush(); + } + @ob_start(); + } +} diff --git a/code/DataIntegrityTestUTF8.php b/code/DataIntegrityTestUTF8.php index 852dfeb..21a57c0 100644 --- a/code/DataIntegrityTestUTF8.php +++ b/code/DataIntegrityTestUTF8.php @@ -1,99 +1,96 @@ - '', - 'Â' => '', - 'Â' => '', - '’' => ''', - '–' => '—', - '
' => '', - '“' => '"', - 'â€^Ý' => '"', - '
' => '
', - '•' => '•', - 'Ý' => '- ' - ); - - /** - * standard SS variable - * @var String - */ - protected $title = "Convert tables to utf-8 and replace funny characters."; - - /** - * standard SS variable - * @var String - */ - protected $description = "Converts table to utf-8 by replacing a bunch of characters that show up in the Silverstripe Conversion. CAREFUL: replaces all tables in Database to utf-8!"; - - function run($request) { - ini_set('max_execution_time', 3000); - $tables = DB::query('SHOW tables'); - $unique = array(); - $arrayOfReplacements = Config::inst()->get("DataIntegrityTestUTF8", "replacement_array"); - foreach ($tables as $table) { - $table = array_pop($table); - DB::query("ALTER TABLE \"$table\" CONVERT TO CHARACTER SET utf8 COLLATE utf8_general_ci"); - DB::alteration_message("

Resetting $table to utf8

"); - $this->flushNow(); - $originatingClass = str_replace("_Live", "", $table); - if(class_exists($originatingClass) && !class_exists($table)) { - - } - else { - $originatingClass = $table; - } - if(class_exists($originatingClass)) { - $fields = Config::inst()->get($originatingClass, "db", $uninherited = 1); - if($fields && count($fields)) { - $unusedFields = array(); - foreach($fields as $fieldName => $type) { - $usedFieldsChanged = array("CHECKING $table.$fieldName : "); - if(substr($type, 0, 4) == "HTML") { - foreach($arrayOfReplacements as $from => $to) { - DB::query("UPDATE \"$table\" SET \"$fieldName\" = REPLACE(\"$fieldName\", '$from', '$to');"); - $count = DB::getConn()->affectedRows(); - $toWord = $to; - if($to == '') { - $toWord = '[NOTHING]'; - } - $usedFieldsChanged[] = "$count Replacements $from with $toWord"; - } - } - else { - $unusedFields[] = $fieldName; - } - if(count($usedFieldsChanged )) { - DB::alteration_message (implode("
     - ", $usedFieldsChanged) ); - $this->flushNow(); - } - } - if(count($unusedFields)) { - DB::alteration_message("Skipped the following fields: ".implode(",", $unusedFields)); - } - } - else { - DB::alteration_message("No fields for $originatingClass"); - } - } - else { - DB::alteration_message("Skipping $originatingClass - class can not be found"); - } - } - DB::alteration_message("






COMPLETED






"); - } - - private function flushNow(){ - // check that buffer is actually set before flushing - if (ob_get_length()){ - @ob_flush(); - @flush(); - @ob_end_flush(); - } - @ob_start(); - } - -} + '', + 'Â' => '', + 'Â' => '', + '’' => ''', + '–' => '—', + '
' => '', + '“' => '"', + 'â€^Ý' => '"', + '
' => '
', + '•' => '•', + 'Ý' => '- ' + ); + + /** + * standard SS variable + * @var String + */ + protected $title = "Convert tables to utf-8 and replace funny characters."; + + /** + * standard SS variable + * @var String + */ + protected $description = "Converts table to utf-8 by replacing a bunch of characters that show up in the Silverstripe Conversion. CAREFUL: replaces all tables in Database to utf-8!"; + + public function run($request) + { + ini_set('max_execution_time', 3000); + $tables = DB::query('SHOW tables'); + $unique = array(); + $arrayOfReplacements = Config::inst()->get("DataIntegrityTestUTF8", "replacement_array"); + foreach ($tables as $table) { + $table = array_pop($table); + DB::query("ALTER TABLE \"$table\" CONVERT TO CHARACTER SET utf8 COLLATE utf8_general_ci"); + DB::alteration_message("

Resetting $table to utf8

"); + $this->flushNow(); + $originatingClass = str_replace("_Live", "", $table); + if (class_exists($originatingClass) && !class_exists($table)) { + } else { + $originatingClass = $table; + } + if (class_exists($originatingClass)) { + $fields = Config::inst()->get($originatingClass, "db", $uninherited = 1); + if ($fields && count($fields)) { + $unusedFields = array(); + foreach ($fields as $fieldName => $type) { + $usedFieldsChanged = array("CHECKING $table.$fieldName : "); + if (substr($type, 0, 4) == "HTML") { + foreach ($arrayOfReplacements as $from => $to) { + DB::query("UPDATE \"$table\" SET \"$fieldName\" = REPLACE(\"$fieldName\", '$from', '$to');"); + $count = DB::getConn()->affectedRows(); + $toWord = $to; + if ($to == '') { + $toWord = '[NOTHING]'; + } + $usedFieldsChanged[] = "$count Replacements $from with $toWord"; + } + } else { + $unusedFields[] = $fieldName; + } + if (count($usedFieldsChanged)) { + DB::alteration_message(implode("
     - ", $usedFieldsChanged)); + $this->flushNow(); + } + } + if (count($unusedFields)) { + DB::alteration_message("Skipped the following fields: ".implode(",", $unusedFields)); + } + } else { + DB::alteration_message("No fields for $originatingClass"); + } + } else { + DB::alteration_message("Skipping $originatingClass - class can not be found"); + } + } + DB::alteration_message("






COMPLETED






"); + } + + private function flushNow() + { + // check that buffer is actually set before flushing + if (ob_get_length()) { + @ob_flush(); + @flush(); + @ob_end_flush(); + } + @ob_start(); + } +} diff --git a/code/DataIntegrityTestYML.php b/code/DataIntegrityTestYML.php index 57f49c2..4bf39e1 100644 --- a/code/DataIntegrityTestYML.php +++ b/code/DataIntegrityTestYML.php @@ -1,118 +1,106 @@ -get("DataIntegrityTestYML", "config_files"); - $classesToSkip = Config::inst()->get("DataIntegrityTestYML", "classes_to_skip"); - $variablesToSkip = Config::inst()->get("DataIntegrityTestYML", "variables_to_skip"); - foreach($filesArray as $folderAndFileLocation){ - db::alteration_message("

Checking $folderAndFileLocation

"); - $fixtureFolderAndFile = Director::baseFolder().'/'. $folderAndFileLocation; - if(!file_exists($fixtureFolderAndFile)) { - user_error('No custom configuration has been setup here : "' . $fixtureFolderAndFile . '" set the files here: DataIntegrityTestYML::config_files', E_USER_NOTICE); - } - $parser = new Spyc(); - $arrayOfSettings = $parser->loadFile($fixtureFolderAndFile); - foreach($arrayOfSettings as $className => $variables) { - if(in_array(strtolower($className), $classesToSkip )) { - db::alteration_message("$className : skipped"); - } - else { - echo "

"; - if(!class_exists($className)) { - db::alteration_message("$className does not exist", "deleted"); - } - else { - db::alteration_message("$className", "created"); - foreach($variables as $variable => $setting) { - if($variable == "icon") { - $fileLocationForOthers = Director::baseFolder().'/'.$setting; - $fileLocationForSiteTree = Director::baseFolder().'/'.$setting.'-file.gif'; - if( $className::create() instanceof SiteTree) { - if(!file_exists($fileLocationForSiteTree)) { - db::alteration_message("      $className.$variable icon $fileLocationForSiteTree can not be found", "deleted"); - } - else { - db::alteration_message("      $className.$variable icon $fileLocationForSiteTree exists", "created"); - } - } - else { - if(!file_exists($fileLocationForOthers)) { - db::alteration_message("      $className.$variable icon $fileLocationForOthers can not be found", "deleted"); - } - else { - db::alteration_message("      $className.$variable icon $fileLocationForOthers exists", "created"); - } - - } - } - elseif($variable == "extensions") { - if(!is_array($setting)) { - db::alteration_message("      $className.$variable extensions should be set as an array.", "deleted"); - } - else { - foreach($setting as $extensionClassName) { - if(!class_exists($extensionClassName)){ - db::alteration_message("      $className.$variable extension class $extensionClassName does not exist", "deleted"); - } - else { - db::alteration_message("      $className.$variable extension class $extensionClassName found", "created"); - } - } - } - } - elseif(in_array($variable, $variablesToSkip)) { - db::alteration_message("      $className.$variable skipped"); - } - else { - if(!property_exists($className, $variable)) { - db::alteration_message("      $className.$variable does not exist", "deleted"); - } - else { - db::alteration_message("      $className.$variable found", "created"); - } - } - } - } - } - } - - } - } - -} +get("DataIntegrityTestYML", "config_files"); + $classesToSkip = Config::inst()->get("DataIntegrityTestYML", "classes_to_skip"); + $variablesToSkip = Config::inst()->get("DataIntegrityTestYML", "variables_to_skip"); + foreach ($filesArray as $folderAndFileLocation) { + db::alteration_message("

Checking $folderAndFileLocation

"); + $fixtureFolderAndFile = Director::baseFolder().'/'. $folderAndFileLocation; + if (!file_exists($fixtureFolderAndFile)) { + user_error('No custom configuration has been setup here : "' . $fixtureFolderAndFile . '" set the files here: DataIntegrityTestYML::config_files', E_USER_NOTICE); + } + $parser = new Spyc(); + $arrayOfSettings = $parser->loadFile($fixtureFolderAndFile); + foreach ($arrayOfSettings as $className => $variables) { + if (in_array(strtolower($className), $classesToSkip)) { + db::alteration_message("$className : skipped"); + } else { + echo "

"; + if (!class_exists($className)) { + db::alteration_message("$className does not exist", "deleted"); + } else { + db::alteration_message("$className", "created"); + foreach ($variables as $variable => $setting) { + if ($variable == "icon") { + $fileLocationForOthers = Director::baseFolder().'/'.$setting; + $fileLocationForSiteTree = Director::baseFolder().'/'.$setting.'-file.gif'; + if ($className::create() instanceof SiteTree) { + if (!file_exists($fileLocationForSiteTree)) { + db::alteration_message("      $className.$variable icon $fileLocationForSiteTree can not be found", "deleted"); + } else { + db::alteration_message("      $className.$variable icon $fileLocationForSiteTree exists", "created"); + } + } else { + if (!file_exists($fileLocationForOthers)) { + db::alteration_message("      $className.$variable icon $fileLocationForOthers can not be found", "deleted"); + } else { + db::alteration_message("      $className.$variable icon $fileLocationForOthers exists", "created"); + } + } + } elseif ($variable == "extensions") { + if (!is_array($setting)) { + db::alteration_message("      $className.$variable extensions should be set as an array.", "deleted"); + } else { + foreach ($setting as $extensionClassName) { + if (!class_exists($extensionClassName)) { + db::alteration_message("      $className.$variable extension class $extensionClassName does not exist", "deleted"); + } else { + db::alteration_message("      $className.$variable extension class $extensionClassName found", "created"); + } + } + } + } elseif (in_array($variable, $variablesToSkip)) { + db::alteration_message("      $className.$variable skipped"); + } else { + if (!property_exists($className, $variable)) { + db::alteration_message("      $className.$variable does not exist", "deleted"); + } else { + db::alteration_message("      $className.$variable found", "created"); + } + } + } + } + } + } + } + } +} diff --git a/code/model/DataIntegrityTestDefaulEntries.php b/code/model/DataIntegrityTestDefaulEntries.php index 4bcec3d..d5a9c63 100644 --- a/code/model/DataIntegrityTestDefaulEntries.php +++ b/code/model/DataIntegrityTestDefaulEntries.php @@ -1,38 +1,38 @@ First(); - if($object) { - $tableArray = array($baseTable); - if($object instanceOf SiteTree) { - $tableArray[] = $baseTable."_Live"; - } - foreach($tableArray as $table) { - $value = Convert::raw2sql($value); - $sql = "UPDATE \"$table\" SET \"$table\".\"$field\" = '$value'"; - $where = array(); - if($id) { - $where[] = " \"$table\".\"ID\" = ".$id; - } - if(!$replace) { - $where[] = " \"$table\".\"$field\" IS NULL OR \"$table\".\"$field\" = '' OR \"$table\".\"$field\" = 0 "; - } - $wherePhrase = ''; - if(count($where)) { - $wherePhrase = " WHERE ( " . implode(") AND (", $where) . " )"; - } - $result = DB::query("SELECT COUNT(\"$table\".\"ID\") C FROM \"$table\" ".$wherePhrase); - if($result && $result->value() ) { - $sql .= $wherePhrase; - DB::query($sql); - DB::alteration_message("Updated $field in $table to $value ", "added"); - } - } - } - } - +class DataIntegrityTestDefaulEntries extends Object +{ + public static function update($baseTable, $field, $value, $id = 0, $replace = false, $addLive = false) + { + $object = $baseTable::get()->First(); + if ($object) { + $tableArray = array($baseTable); + if ($object instanceof SiteTree) { + $tableArray[] = $baseTable."_Live"; + } + foreach ($tableArray as $table) { + $value = Convert::raw2sql($value); + $sql = "UPDATE \"$table\" SET \"$table\".\"$field\" = '$value'"; + $where = array(); + if ($id) { + $where[] = " \"$table\".\"ID\" = ".$id; + } + if (!$replace) { + $where[] = " \"$table\".\"$field\" IS NULL OR \"$table\".\"$field\" = '' OR \"$table\".\"$field\" = 0 "; + } + $wherePhrase = ''; + if (count($where)) { + $wherePhrase = " WHERE ( " . implode(") AND (", $where) . " )"; + } + $result = DB::query("SELECT COUNT(\"$table\".\"ID\") C FROM \"$table\" ".$wherePhrase); + if ($result && $result->value()) { + $sql .= $wherePhrase; + DB::query($sql); + DB::alteration_message("Updated $field in $table to $value ", "added"); + } + } + } + } }