34 "trac",
"taxf",
"auth",
"rolf",
"assf",
"svyf",
"extt",
"adve",
"fold");
46 "restore_trash" =>
false,
47 "purge_trash" =>
false
118 global $objDefinition,
$ilDB;
122 $this->rbac_object_types =
"'".implode(
"','",$objDefinition->getAllRBACObjects()).
"'";
123 $this->rbac_object_types = $objDefinition->getAllRBACObjects();
129 $this->logging =
true;
133 include_once
"./Services/Logging/classes/class.ilLog.php";
139 $this->scan_log =
new ilLog(CLIENT_DATA_DIR,
"scanlog.log");
140 $this->scan_log->setLogFormat(
"");
153 return array_keys($this->mode);
169 if ((!in_array($a_mode,array_keys($this->mode)) and $a_mode !=
"all") or !is_bool($a_value))
175 if ($a_mode ==
"all")
177 foreach ($this->mode as
$mode => $value)
179 $this->mode[
$mode] = $a_value;
184 $this->mode[$a_mode] = $a_value;
203 if (!in_array($a_mode,array_keys($this->mode)))
209 return $this->mode[$a_mode];
229 if ($this->mode[
"restore"] ===
true)
231 $this->mode[
"scan"] =
true;
232 $this->mode[
"purge"] =
false;
235 if ($this->mode[
"purge"] ===
true)
237 $this->mode[
"scan"] =
true;
238 $this->mode[
"restore"] =
false;
241 if ($this->mode[
"restore_trash"] ===
true)
243 $this->mode[
"scan"] =
true;
244 $this->mode[
"purge_trash"] =
false;
247 if ($this->mode[
"purge_trash"] ===
true)
249 $this->mode[
"scan"] =
true;
250 $this->mode[
"restore_trash"] =
false;
253 if ($this->mode[
"clean"] ===
true)
255 $this->mode[
"scan"] =
true;
277 $summary .=
$lng->txt(
"scanning_system");
280 $summary .=
$lng->txt(
"disabled");
284 $summary .=
"<br/>".$lng->txt(
"searching_invalid_refs");
291 $summary .=
$lng->txt(
"found_none");
294 $summary .=
"<br/>".$lng->txt(
"searching_invalid_childs");
302 $summary .=
$lng->txt(
"found_none");
305 $summary .=
"<br/>".$lng->txt(
"searching_missing_objs");
313 $summary .=
$lng->txt(
"found_none");
316 $summary .=
"<br/>".$lng->txt(
"searching_unbound_objs");
324 $summary .=
$lng->txt(
"found_none");
327 $summary .=
"<br/>".$lng->txt(
"searching_deleted_objs");
335 $summary .=
$lng->txt(
"found_none");
338 $summary .=
"<br/>".$lng->txt(
"searching_invalid_rolfs");
346 $summary .=
$lng->txt(
"found_none");
349 $summary .=
"<br/><br/>".$lng->txt(
"analyzing_tree_structure");
352 $summary .=
$lng->txt(
"tree_corrupt");
356 $summary .=
$lng->txt(
"done");
362 $summary .=
"<br /><br />".$lng->txt(
"dumping_tree");
365 $summary .=
$lng->txt(
"disabled");
370 if ($error_count > 0)
372 $summary .=
$lng->txt(
"tree_corrupt");
376 $summary .=
$lng->txt(
"done");
382 $summary .=
"<br /><br />".$lng->txt(
"cleaning");
385 $summary .=
$lng->txt(
"disabled");
389 $summary .=
"<br />".$lng->txt(
"removing_invalid_refs");
392 $summary .= strtolower(
$lng->txt(
"done"));
396 $summary .=
$lng->txt(
"nothing_to_remove").$lng->txt(
"skipped");
399 $summary .=
"<br />".$lng->txt(
"removing_invalid_childs");
402 $summary .= strtolower(
$lng->txt(
"done"));
406 $summary .=
$lng->txt(
"nothing_to_remove").$lng->txt(
"skipped");
409 $summary .=
"<br />".$lng->txt(
"removing_invalid_rolfs");
412 $summary .= strtolower(
$lng->txt(
"done"));
416 $summary .=
$lng->txt(
"nothing_to_remove").$lng->txt(
"skipped");
426 $summary .=
"<br /><br />".$lng->txt(
"restoring");
430 $summary .=
$lng->txt(
"disabled");
434 $summary .=
"<br />".$lng->txt(
"restoring_missing_objs");
437 $summary .= strtolower(
$lng->txt(
"done"));
441 $summary .=
$lng->txt(
"nothing_to_restore").$lng->txt(
"skipped");
444 $summary .=
"<br />".$lng->txt(
"restoring_unbound_objs");
447 $summary .= strtolower(
$lng->txt(
"done"));
451 $summary .=
$lng->txt(
"nothing_to_restore").$lng->txt(
"skipped");
456 $summary .=
"<br /><br />".$lng->txt(
"restoring_trash");
460 $summary .=
$lng->txt(
"disabled");
466 $summary .= strtolower(
$lng->txt(
"done"));
470 $summary .=
$lng->txt(
"nothing_to_restore").$lng->txt(
"skipped");
475 $summary .=
"<br /><br />".$lng->txt(
"purging");
479 $summary .=
$lng->txt(
"disabled");
483 $summary .=
"<br />".$lng->txt(
"purging_missing_objs");
486 $summary .= strtolower(
$lng->txt(
"done"));
490 $summary .=
$lng->txt(
"nothing_to_purge").$lng->txt(
"skipped");
493 $summary .=
"<br />".$lng->txt(
"purging_unbound_objs");
496 $summary .= strtolower(
$lng->txt(
"done"));
500 $summary .=
$lng->txt(
"nothing_to_purge").$lng->txt(
"skipped");
505 $summary .=
"<br /><br />".$lng->txt(
"purging_trash");
509 $summary .=
$lng->txt(
"disabled");
515 $summary .= strtolower(
$lng->txt(
"done"));
519 $summary .=
$lng->txt(
"nothing_to_purge").$lng->txt(
"skipped");
526 $summary .=
"<br /><br />".$lng->txt(
"cleaning_final");
529 $summary .=
"<br />".$lng->txt(
"initializing_gaps").
" ".strtolower(
$lng->txt(
"done"));
537 foreach ($this->mode as
$mode => $value)
539 $arr[] =
$mode.
"[".(int)$value.
"]";
560 if ($this->mode[
"scan"] !==
true)
566 $this->missing_objects = array();
575 $q =
"SELECT object_data.*, ref_id FROM object_data ".
576 "LEFT JOIN object_reference ON object_data.obj_id = object_reference.obj_id ".
577 "LEFT JOIN tree ON object_reference.ref_id = tree.child ".
578 "WHERE tree.child IS NULL ".
579 "AND (object_reference.obj_id IS NOT NULL ".
580 " OR object_data.type <> 'file' AND ".
581 $ilDB->in(
'object_data.type',$this->rbac_object_types,
false,
'text').
583 $r = $this->db->query($q);
587 #if (!in_array($row->type,$this->object_types_exclude))
590 $this->missing_objects[] = array(
591 "obj_id" =>
$row->obj_id,
592 "type" =>
$row->type,
593 "ref_id" =>
$row->ref_id,
594 "child" =>
$row->child,
595 "title" =>
$row->title,
596 "desc" =>
$row->description,
597 "owner" =>
$row->owner,
598 "create_date" =>
$row->create_date,
599 "last_update" =>
$row->last_update
605 if (count($this->missing_objects) > 0)
607 $this->
writeScanLogLine(
"obj_id\ttype\tref_id\tchild\ttitle\tdesc\towner\tcreate_date\tlast_update");
632 if ($this->mode[
"scan"] !==
true)
638 $this->invalid_rolefolders = array();
643 $q =
"SELECT object_data.*, ref_id FROM object_data ".
644 "LEFT JOIN object_reference ON object_data.obj_id = object_reference.obj_id ".
645 "LEFT JOIN tree ON object_reference.ref_id = tree.child ".
646 "WHERE (object_reference.obj_id IS NULL OR tree.child IS NULL) ".
647 "AND object_data.type='rolf'";
648 $r = $this->db->query($q);
652 $this->invalid_rolefolders[] = array(
653 "obj_id" =>
$row->obj_id,
654 "type" =>
$row->type,
655 "ref_id" =>
$row->ref_id,
656 "child" =>
$row->child,
657 "title" =>
$row->title,
658 "desc" =>
$row->description,
659 "owner" =>
$row->owner,
660 "create_date" =>
$row->create_date,
661 "last_update" =>
$row->last_update
666 $q =
"SELECT object_data.*, ref_id FROM object_data ".
667 "LEFT JOIN object_reference ON object_data.obj_id = object_reference.obj_id ".
668 "LEFT JOIN tree ON object_reference.ref_id = tree.child ".
669 "WHERE object_reference.ref_id = ".$ilDB->quote(RECOVERY_FOLDER_ID,
'integer').
" ".
670 "AND object_data.type='rolf'";
671 $r = $this->db->query($q);
675 $this->invalid_rolefolders[] = array(
676 "obj_id" =>
$row->obj_id,
677 "type" =>
$row->type,
678 "ref_id" =>
$row->ref_id,
679 "child" =>
$row->child,
680 "title" =>
$row->title,
681 "desc" =>
$row->description,
682 "owner" =>
$row->owner,
683 "create_date" =>
$row->create_date,
684 "last_update" =>
$row->last_update
689 if (count($this->invalid_rolefolders) > 0)
691 $this->
writeScanLogLine(
"obj_id\ttype\tref_id\tchild\ttitle\tdesc\towner\tcreate_date\tlast_update");
714 if ($this->mode[
"scan"] !==
true)
720 $this->invalid_rbac_entries = array();
724 $q =
"SELECT object_data.*, ref_id FROM object_data ".
725 "LEFT JOIN object_reference ON object_data.obj_id = object_reference.obj_id ".
726 "LEFT JOIN tree ON object_reference.ref_id = tree.child ".
727 "WHERE (object_reference.obj_id IS NULL OR tree.child IS NULL) ".
728 "AND object_data.type='rolf'";
729 $r = $this->db->query($q);
733 $this->invalid_rolefolders[] = array(
734 "obj_id" =>
$row->obj_id,
735 "type" =>
$row->type,
736 "ref_id" =>
$row->ref_id,
737 "child" =>
$row->child,
738 "title" =>
$row->title,
739 "desc" =>
$row->description,
740 "owner" =>
$row->owner,
741 "create_date" =>
$row->create_date,
742 "last_update" =>
$row->last_update
747 $q =
"SELECT object_data.*, ref_id FROM object_data ".
748 "LEFT JOIN object_reference ON object_data.obj_id = object_reference.obj_id ".
749 "LEFT JOIN tree ON object_reference.ref_id = tree.child ".
750 "WHERE object_reference.ref_id =".$ilDB->quote(RECOVERY_FOLDER_ID).
" ".
751 "AND object_data.type='rolf'";
752 $r = $this->db->query($q);
756 $this->invalid_rolefolders[] = array(
757 "obj_id" =>
$row->obj_id,
758 "type" =>
$row->type,
759 "ref_id" =>
$row->ref_id,
760 "child" =>
$row->child,
761 "title" =>
$row->title,
762 "desc" =>
$row->description,
763 "owner" =>
$row->owner,
764 "create_date" =>
$row->create_date,
765 "last_update" =>
$row->last_update
770 if (count($this->invalid_rolefolders) > 0)
772 $this->
writeScanLogLine(
"obj_id\ttype\tref_id\tchild\ttitle\tdesc\towner\tcreate_date\tlast_update");
813 if ($this->mode[
"scan"] !==
true)
819 $this->invalid_references = array();
822 $q =
"SELECT object_reference.* FROM object_reference ".
823 "LEFT JOIN object_data ON object_data.obj_id = object_reference.obj_id ".
824 "WHERE object_data.obj_id IS NULL ".
825 "OR ".$ilDB->in(
'object_data.type',$this->rbac_object_types,
true,
'text');
826 $r = $this->db->query($q);
830 $this->invalid_references[] = array(
831 "ref_id" =>
$row->ref_id,
832 "obj_id" =>
$row->obj_id,
833 "msg" =>
"Object does not exist."
838 if (count($this->invalid_references) > 0)
876 if ($this->mode[
"scan"] !==
true)
882 $this->invalid_childs = array();
886 $q =
"SELECT tree.*,object_reference.ref_id FROM tree ".
887 "LEFT JOIN object_reference ON tree.child = object_reference.ref_id ".
888 "LEFT JOIN object_data ON object_reference.obj_id = object_data.obj_id ".
889 "WHERE object_reference.ref_id IS NULL or object_data.obj_id IS NULL";
890 $r = $this->db->query($q);
893 $this->invalid_childs[] = array(
894 "child" =>
$row->child,
895 "ref_id" =>
$row->ref_id,
896 "msg" =>
"No object found"
900 if (count($this->invalid_childs) > 0)
938 if ($this->mode[
"scan"] !==
true)
944 $this->unbound_objects = array();
948 $q =
"SELECT T1.tree,T1.child,T1.parent,".
949 "T2.tree deleted,T2.parent grandparent ".
951 "LEFT JOIN tree T2 ON T2.child=T1.parent ".
952 "WHERE (T2.tree!=1 OR T2.tree IS NULL) AND T1.parent!=0";
953 $r = $this->db->query($q);
958 if (
$row->deleted === NULL)
960 $this->unbound_objects[] = array(
961 "child" =>
$row->child,
962 "parent" =>
$row->parent,
963 "tree" =>
$row->tree,
964 "msg" =>
"No valid parent node found"
969 if (count($this->unbound_objects) > 0)
994 if ($this->mode[
"scan"] !==
true)
1000 $this->deleted_objects = array();
1005 $query =
"SELECT object_data.*,tree.tree,tree.child,tree.parent,deleted ".
1006 "FROM object_data ".
1007 "LEFT JOIN object_reference ON object_data.obj_id=object_reference.obj_id ".
1008 "LEFT JOIN tree ON tree.child=object_reference.ref_id ".
1009 " WHERE tree != 1 ".
1010 " ORDER BY deleted";
1011 $r = $this->db->query(
$query);
1013 include_once
'./Services/Calendar/classes/class.ilDateTime.php';
1018 $this->deleted_objects[] = array(
1019 "child" =>
$row->child,
1020 "parent" =>
$row->parent,
1021 "tree" =>
$row->tree,
1022 "type" =>
$row->type,
1023 "title" =>
$row->title,
1024 "desc" =>
$row->description,
1025 "owner" =>
$row->owner,
1026 "deleted" =>
$row->deleted,
1027 "deleted_timestamp" => $tmp_date->get(
IL_CAL_UNIX),
1028 "create_date" =>
$row->create_date,
1029 "last_update" =>
$row->last_update
1033 if (count($this->deleted_objects) > 0)
1101 if ($this->mode[
"clean"] !==
true)
1108 if ($a_invalid_refs === NULL and isset($this->invalid_references))
1114 if (!is_array($a_invalid_refs))
1120 if (count($a_invalid_refs) == 0)
1130 $message = sprintf(
'%s::removeInvalidReferences(): Started...',
1137 foreach ($a_invalid_refs as $entry)
1139 $query =
"DELETE FROM object_reference WHERE ref_id= ".$this->db->quote($entry[
"ref_id"],
'integer').
1140 " AND obj_id = ".$this->db->quote($entry[
"obj_id"],
'integer').
" ";
1143 $message = sprintf(
'%s::removeInvalidReferences(): Reference %s removed',
1168 if ($this->mode[
"clean"] !==
true)
1175 if ($a_invalid_childs === NULL and isset($this->invalid_childs))
1181 if (!is_array($a_invalid_childs))
1188 if (count($a_invalid_childs) == 0)
1198 $message = sprintf(
'%s::removeInvalidChilds(): Started...',
1202 foreach ($a_invalid_childs as $entry)
1204 $q =
"DELETE FROM tree WHERE child='".$entry[
"child"].
"'";
1205 $this->db->query($q);
1207 $message = sprintf(
'%s::removeInvalidChilds(): Entry child=%s removed',
1233 if ($this->mode[
"clean"] !==
true)
1240 if ($a_invalid_rolefolders === NULL and isset($this->invalid_rolefolders))
1246 if (!is_array($a_invalid_rolefolders))
1253 if (count($a_invalid_rolefolders) == 0)
1265 $message = sprintf(
'%s::removeInvalidRolefolders(): Started...',
1272 foreach ($a_invalid_rolefolders as $rolf)
1275 if ($rolf[
"ref_id"] === NULL)
1279 $this->
writeScanLogLine(
"Created missing reference '".$rolf[
"ref_id"].
"' for rolefolder object '".$rolf[
"obj_id"].
"'");
1283 $obj_data =& $ilias->obj_factory->getInstanceByRefId($rolf[
"ref_id"]);
1284 $obj_data->delete();
1287 $this->
writeScanLogLine(
"Removed invalid rolefolder '".$rolf[
"title"].
"' (id=".$rolf[
"obj_id"].
",ref=".$rolf[
"ref_id"].
") from system");
1305 global $ilias,$rbacadmin,
$ilLog;
1308 if ($this->mode[
"restore"] !==
true)
1315 if ($a_missing_objects === NULL and isset($this->missing_objects))
1321 if (!is_array($a_missing_objects))
1328 if (count($a_missing_objects) == 0)
1340 $message = sprintf(
'%s::restoreMissingObjects(): Started...',
1347 foreach ($a_missing_objects as $missing_obj)
1350 if ($missing_obj[
"ref_id"] === NULL)
1354 $this->
writeScanLogLine(
"Created missing reference '".$missing_obj[
"ref_id"].
"' for object '".$missing_obj[
"obj_id"].
"'");
1358 #if (!in_array($missing_obj["type"],$this->object_types_exclude))
1361 $rbacadmin->revokePermission($missing_obj[
"ref_id"]);
1362 $obj_data =& $ilias->obj_factory->getInstanceByRefId($missing_obj[
"ref_id"]);
1363 $obj_data->putInTree(RECOVERY_FOLDER_ID);
1364 $obj_data->setPermissions(RECOVERY_FOLDER_ID);
1368 $this->
writeScanLogLine(
"Restored object '".$missing_obj[
"title"].
"' (id=".$missing_obj[
"obj_id"].
",ref=".$missing_obj[
"ref_id"].
") in 'Restored objects folder'");
1391 if (empty($a_obj_id))
1397 $query =
"INSERT INTO object_reference (ref_id,obj_id) ".
1398 "VALUES (".$next_id =
$ilDB->nextId(
'object_reference').
",".$this->db->quote($a_obj_id,
'integer').
" )";
1401 $message = sprintf(
'%s::restoreReference(): new reference %s for obj_id %s created',
1425 if ($this->mode[
"restore"] !==
true)
1432 if ($a_unbound_objects === NULL and isset($this->unbound_objects))
1438 if (!is_array($a_unbound_objects))
1444 $message = sprintf(
'%s::restoreUnboundObjects(): Started...',
1466 if ($this->mode[
"restore_trash"] !==
true)
1473 if ($a_deleted_objects === NULL and isset($this->deleted_objects))
1479 if (!is_array($a_deleted_objects))
1485 $message = sprintf(
'%s::restoreTrash(): Started...',
1494 $q =
"DELETE FROM tree WHERE tree!=1";
1495 $this->db->query($q);
1497 $message = sprintf(
'%s::restoreTrash(): Removed all trees with tree id <> 1',
1517 global $tree,$rbacadmin,$ilias,
$ilLog;
1520 if (!is_array($a_nodes))
1527 if (count($a_nodes) == 0)
1533 $message = sprintf(
'%s::restoreDeletedObjects()): Started...',
1540 foreach ($a_nodes as $key => $node)
1542 if ($node[
"type"] ==
"rolf")
1545 $tree->deleteTree($node);
1547 $obj_data =& $ilias->obj_factory->getInstanceByRefId($node[
"child"]);
1548 $obj_data->delete();
1549 unset($a_nodes[$key]);
1554 foreach ($a_nodes as $node)
1557 $tree->deleteTree($node);
1559 $rbacadmin->revokePermission($node[
"child"]);
1560 $obj_data =& $ilias->obj_factory->getInstanceByRefId($node[
"child"]);
1561 $obj_data->putInTree(RECOVERY_FOLDER_ID);
1562 $obj_data->setPermissions(RECOVERY_FOLDER_ID);
1578 global $tree,$rbacadmin,$ilias,
$ilLog;
1581 if (!is_array($a_nodes))
1588 if (count($a_nodes) == 0)
1598 $subnodes = array();
1601 $message = sprintf(
'%s::restoreSubTrees(): Started...',
1606 foreach ($a_nodes as $node)
1609 $topnode = $tree->getNodeData($node[
"child"], $node[
'tree']);
1613 if ($topnode[
"type"] ==
"rolf")
1615 $rolfObj = $ilias->obj_factory->getInstanceByRefId($topnode[
"child"]);
1623 $subnodes[$node[
"child"]] = $tree->getSubtree($topnode);
1626 $tree->deleteTree($topnode);
1631 foreach ($subnodes as $key => $subnode)
1635 $rbacadmin->revokePermission($key);
1636 $obj_data =& $ilias->obj_factory->getInstanceByRefId($key);
1637 $obj_data->putInTree(RECOVERY_FOLDER_ID);
1638 $obj_data->setPermissions(RECOVERY_FOLDER_ID);
1643 array_shift($subnode);
1646 if (count($subnode) > 0)
1648 foreach ($subnode as $node)
1650 $rbacadmin->revokePermission($node[
"child"]);
1651 $obj_data =& $ilias->obj_factory->getInstanceByRefId($node[
"child"]);
1652 $obj_data->putInTree($node[
"parent"]);
1653 $obj_data->setPermissions($node[
"parent"]);
1681 if ($this->mode[
"purge_trash"] !==
true)
1688 if ($a_nodes === NULL and isset($this->deleted_objects))
1694 $message = sprintf(
'%s::purgeTrash(): Started...',
1716 if ($this->mode[
"purge"] !==
true)
1723 if ($a_nodes === NULL and isset($this->unbound_objects))
1728 $message = sprintf(
'%s::purgeUnboundObjects(): Started...',
1750 if ($this->mode[
"purge"] !==
true)
1757 if ($a_nodes === NULL and isset($this->missing_objects))
1762 $message = sprintf(
'%s::purgeMissingObjects(): Started...',
1782 $count_limit = $ilias->account->getPref(
"systemcheck_count_limit");
1783 if (! is_numeric($count_limit) || $count_limit < 0)
1785 $count_limit = count($a_nodes);
1787 $timestamp_limit = time();
1788 $age_limit = $ilias->account->getPref(
"systemcheck_age_limit");
1789 if (is_numeric($age_limit) && $age_limit > 0)
1791 $timestamp_limit -= $age_limit * 60 * 60 * 24;
1793 $type_limit = $ilias->account->getPref(
"systemcheck_type_limit");
1796 $type_limit = trim($type_limit);
1797 if (strlen($type_limit) == 0)
1804 if (!is_array($a_nodes))
1813 foreach ($a_nodes as $node)
1815 if ($type_limit && $node[
'type'] != $type_limit)
1818 $node[
'child'].
"\t\t".$node[
'type'].
"\t\t".$node[
'title']
1825 if ($count > $count_limit)
1827 $this->
writeScanLogLine(
"Stopped purging after ".($count - 1).
" objects, because count limit was reached: ".$count_limit);
1830 if ($node[
"deleted_timestamp"] > $timestamp_limit)
1832 $this->
writeScanLogLine(
"Stopped purging after ".($count - 1).
" objects, because timestamp limit was reached: ".date(
"c", $timestamp_limit));
1836 $ref_id = ($node[
"child"]) ? $node[
"child"] : $node[
"ref_id"];
1837 $node_obj =& $ilias->obj_factory->getInstanceByRefId(
$ref_id,
false);
1839 if ($node_obj ===
false)
1841 $this->invalid_objects[] = $node;
1845 $message = sprintf(
'%s::purgeObjects(): Removing object (id:%s ref:%s)',
1848 $node_obj->getId());
1851 $startTime = microtime(
true);
1852 $node_obj->delete();
1854 $endTime = microtime(
true);
1857 "\t".$node[
'type'].
"\t".round($endTime-$startTime,1).
"\t".$node[
'title']);
1883 $message = sprintf(
'%s::initGapsInTree(): Started...',
1888 if ($this->mode[
"clean"] !==
true)
1894 $tree->renumber(ROOT_FOLDER_ID);
1912 $call_loc = $error->backtrace[count($error->backtrace)-1];
1913 $num_args = count($call_loc[
"args"]);
1917 foreach ($call_loc[
"args"] as $arg)
1919 $type = gettype($arg);
1924 $value = strlen($arg);
1928 $value = count($arg);
1932 $value = get_class($arg);
1936 $value = ($arg) ?
"true" :
"false";
1944 $arg_list[] = array(
1946 "value" =>
"(".$value.
")"
1950 foreach ($arg_list as $arg)
1952 $arg_str .= implode(
"",$arg).
" ";
1956 $err_msg =
"<br/><b>".$error->getCode().
":</b> ".$error->getMessage().
" in ".$call_loc[
"class"].$call_loc[
"type"].$call_loc[
"function"].
"()".
1957 "<br/>Called from: ".basename($call_loc[
"file"]).
" , line ".$call_loc[
"line"].
1958 "<br/>Passed parameters: [".$num_args.
"] ".$arg_str.
"<br/>";
1961 if ($error->getUserInfo())
1963 printf(
"<br/>Parameter details:");
1965 var_dump($call_loc[
"args"]);
1969 if ($error->getCode() == FATAL)
1982 foreach ($a_arr as $entry)
1984 $this->scan_log->write(implode(
"\t",$entry));
1995 $this->scan_log->write($a_msg);
2004 return is_file(CLIENT_DATA_DIR.
"/".$this->scan_log_file);
2012 @unlink(CLIENT_DATA_DIR.
"/".$this->scan_log_file);
2023 $scanfile =& file(CLIENT_DATA_DIR.
"/".$this->scan_log_file);
2036 $logs = array_keys($a_scan_log,$this->scan_log_separator.
"\n");
2038 if (count($logs) > 0)
2040 return array_slice($a_scan_log,array_pop($logs)+2);
2070 $q =
'SELECT child FROM tree GROUP BY child HAVING COUNT(*) > 1';
2071 $r = $this->db->query($q);
2072 $duplicateNodes = array();
2075 $duplicateNodes[] =
$row->child;
2079 $q =
"SELECT tree.*,ref.ref_id,dat.obj_id objobj_id,ref.obj_id refobj_id,ref.deleted,dat.*,usr.login "
2081 .
"RIGHT JOIN object_reference ref ON tree.child = ref.ref_id "
2082 .
"RIGHT JOIN object_data dat ON ref.obj_id = dat.obj_id "
2083 .
"LEFT JOIN usr_data usr ON usr.usr_id = dat.owner "
2084 .
"ORDER BY tree, lft, type, dat.title";
2085 $r = $this->db->query($q);
2089 .
'<td>tree, child, parent, lft, rgt, depth</td>'
2090 .
'<td>ref_id, ref.obj_id, deleted</td>'
2091 .
'<td>obj_id, type, owner, title</td>'
2100 $repository_tree_count = 0;
2101 $trash_trees_count = 0;
2102 $other_trees_count = 0;
2103 $not_in_tree_count = 0;
2106 $previousNumber = 0;
2113 if($this->workspace_object_ids &&
2114 in_array(
$row->objobj_id, $this->workspace_object_ids))
2120 if (is_null(
$row->child))
2122 switch (
$row->type) {
2136 if (is_null(
$row->ref_id)) {
2146 $isParentOkay =
false;
2149 $isDepthOkay =
false;
2163 $isParentOkay =
false;
2166 $isDepthOkay =
false;
2171 $not_in_tree_count++;
2176 .(($isRowOkay) ?
'' :
'<font color=#ff0000>')
2179 .(($isParentOkay) ?
'' :
'parent:<b>')
2181 .(($isParentOkay) ?
'' :
'</b>')
2183 .(($isLftOkay) ?
'' :
'lft:<b>')
2185 .(($isLftOkay) ?
'' :
'</b>')
2187 .(($isRgtOkay) ?
'' :
'rgt:<b>')
2189 .(($isRgtOkay) ?
'' :
'</b>')
2191 .(($isDepthOkay) ?
'' :
'depth:<b>')
2193 .(($isDepthOkay) ?
'' :
'</b>')
2194 .(($isRowOkay) ?
'' :
'</font>')
2196 .(($isRowOkay) ?
'' :
'<font color=#ff0000>')
2197 .(($isRefRefOkay && $isChildOkay) ?
'' :
'ref.ref_id:<b>')
2199 .(($isRefRefOkay && $isChildOkay) ?
'' :
'</b>')
2201 .(($isRefObjOkay) ?
'' :
'ref.obj_id:<b>')
2203 .(($isRefObjOkay) ?
'' :
'</b>')
2204 .(($isRowOkay) ?
'' :
'<font color=#ff0000>')
2205 .((
$row->deleted !=
null) ?
', '.$row->deleted :
'')
2207 .(($isRowOkay) ?
'' :
'<font color=#ff0000>')
2213 .(($isRowOkay) ?
'' :
' <b>*ERROR*</b><font color=#ff0000>')
2223 for ($i = 1; $i <
$row->depth; $i++)
2229 if (count($stack) == 0 || $stack[0]->tree !=
$row->tree)
2232 $previousNumber =
$row->lft - 1;
2236 while (count($stack) > 0 && $stack[count($stack) - 1]->rgt < $row->lft)
2238 $popped = array_pop($stack);
2241 $gap = $popped->rgt - $previousNumber - 1;
2245 for ($i = 1; $i < $popped->depth; $i++)
2247 $poppedIndent .=
". ";
2251 .
'<td colspan=2><div align="right">'
2252 .
'<font color=#00cc00>*gap* for '.($gap/2).
' nodes at end of </font>'
2255 .
'<font color=#00cc00>'
2257 .$popped->obj_id.
', '
2259 .$popped->login.
', '
2266 $previousNumber = $popped->rgt;
2275 $isChildOkay =
true;
2276 $isParentOkay =
true;
2279 $isDepthOkay =
true;
2282 if (count($stack) > 0)
2284 $parent = $stack[count($stack) - 1];
2285 if ($parent->depth + 1 !=
$row->depth)
2287 $isDepthOkay =
false;
2290 if ($parent->child !=
$row->parent)
2292 $isParentOkay =
false;
2295 if ($parent->lft >=
$row->lft)
2300 if ($parent->rgt <=
$row->rgt)
2314 if (in_array(
$row->child, $duplicateNodes))
2316 $isChildOkay =
false;
2321 $isRefRefOkay =
true;
2322 $isRefObjOkay =
true;
2323 if (
$row->ref_id ==
null)
2325 $isRefRefOkay =
false;
2328 if (
$row->obj_id ==
null)
2330 $isRefObjOkay =
false;
2341 $gap =
$row->lft - $previousNumber - 1;
2342 $previousNumber =
$row->lft;
2347 .
'<td colspan=2><div align="right">'
2348 .
'<font color=#00cc00>*gap* for '.($gap/2).
' nodes between </font>'
2351 .
'<font color=#00cc00>siblings</font>'
2362 .(($isRowOkay) ?
'' :
'<font color=#ff0000>')
2365 .(($isParentOkay) ?
'' :
'parent:<b>')
2367 .(($isParentOkay) ?
'' :
'</b>')
2369 .(($isLftOkay) ?
'' :
'lft:<b>')
2371 .(($isLftOkay) ?
'' :
'</b>')
2373 .(($isRgtOkay) ?
'' :
'rgt:<b>')
2375 .(($isRgtOkay) ?
'' :
'</b>')
2377 .(($isDepthOkay) ?
'' :
'depth:<b>')
2379 .(($isDepthOkay) ?
'' :
'</b>')
2380 .(($isRowOkay) ?
'' :
'</font>')
2382 .(($isRowOkay) ?
'' :
'<font color=#ff0000>')
2383 .(($isRefRefOkay && $isChildOkay) ?
'' :
'ref.ref_id:<b>')
2385 .(($isRefRefOkay && $isChildOkay) ?
'' :
'</b>')
2387 .(($isRefObjOkay) ?
'' :
'ref.obj_id:<b>')
2389 .(($isRefObjOkay) ?
'' :
'</b>')
2390 .(($isRowOkay) ?
'' :
'<font color=#ff0000>')
2391 .((
$row->tree < 0) ?
', '.$row->deleted :
'')
2393 .(($isRowOkay) ?
'' :
'<font color=#ff0000>')
2399 .(($isRowOkay) ?
'' :
' <b>*ERROR*</b><font color=#ff0000>')
2411 if (
$row->tree == 1)
2413 $repository_tree_count++;
2415 else if (
$row->tree < 0)
2417 $trash_trees_count++;
2421 $other_trees_count++;
2427 while (count($stack) > 0)
2429 $popped = array_pop($stack);
2432 $gap = $popped->rgt - $previousNumber - 1;
2436 for ($i = 1; $i < $popped->depth; $i++)
2438 $poppedIndent .=
". ";
2442 .
'<td colspan=2><div align="right">'
2443 .
'<font color=#00cc00>*gap* for '.($gap/2).
' nodes at end of </font>'
2446 .
'<font color=#00cc00>'
2448 .$popped->obj_id.
', '
2450 .$popped->login.
', '
2457 $previousNumber = $popped->rgt;
2464 if ($error_count > 0)
2466 $this->
writeScanLogLine(
'<font color=#ff0000>'.$error_count.
' errors found while dumping tree.</font>');
2472 $this->
writeScanLogLine(
"$repository_tree_count nodes in repository tree");
2478 return $error_count;
2485 if(!is_array($this->media_pool_ids))
2487 $this->media_pool_ids = array();
2488 $query =
"SELECT child FROM mep_tree ";
2492 $this->media_pool_ids[] =
$row->child;
2496 return in_array($a_obj_id,$this->media_pool_ids) ? true :
false;
2515 return in_array($a_type,$this->object_types_exclude);
2522 if($this->workspace_object_ids ===
null)
2524 $this->workspace_object_ids = array();
2527 $set =
$ilDB->query(
"SELECT DISTINCT(obj_id) FROM object_reference_ws");
2530 $this->workspace_object_ids[] =
$row[
"obj_id"];
2534 $set =
$ilDB->query(
"SELECT id FROM usr_portfolio");
2537 $this->workspace_object_ids[] =
$row[
"id"];
2549 if(is_array($this->workspace_object_ids))
2551 foreach($a_data as $idx => $item)
2553 if(in_array($item[$a_index], $this->workspace_object_ids))
2555 unset($a_data[$idx]);
const PEAR_ERROR_CALLBACK
& throwError($message=null, $code=null, $userinfo=null)
Simpler form of raiseError with fewer options.
PEAR($error_class=null)
Constructor.
setErrorHandling($mode=null, $options=null)
Sets how errors generated by this object should be handled.
const DB_FETCHMODE_OBJECT
@classDescription Date and time handling
_removeEntry($a_tree, $a_child, $a_db_table="tree")
STATIC METHOD Removes a single entry from a tree.
ILIAS Data Validator & Recovery Tool.
restoreUnboundObjects($a_unbound_objects=NULL)
Restore objects (and their subobjects) to RecoveryFolder that are valid but not linked correctly in t...
deleteScanLog()
Delete scan log.
findUnboundObjects()
Search database for all tree entries having no valid parent (=> no valid path to root node) and store...
handleErr($error)
Callback function handles PEAR_error and outputs detailed infos about error TODO: implement that in g...
isExcludedFromRecovery($a_type, $a_obj_id)
Check if type is excluded from recovery.
restoreReference($a_obj_id)
restore a reference for an object Creates a new reference entry in DB table object_reference for $a_o...
getInvalidChilds()
Gets all tree entries without any link to a valid object.
getDeletedObjects()
Gets all object in trash.
getInvalidReferences()
Gets all reference entries that are not linked with a valid object id.
purgeTrash($a_nodes=NULL)
Removes all objects in trash from system.
writeScanLogArray($a_arr)
filterWorkspaceObjects(array &$a_data, $a_index="obj_id")
getInvalidRolefolders()
Gets invalid rolefolders (same as missing objects)
removeInvalidRolefolders($a_invalid_rolefolders=NULL)
Removes invalid rolefolders.
restoreTrash($a_deleted_objects=NULL)
Restore all objects in trash to RecoveryFolder NOTE: All objects will be restored to top of RecoveryF...
purgeObjects($a_nodes)
removes objects from system
removeInvalidChilds($a_invalid_childs=NULL)
Removes all tree entries without any link to a valid object.
checkTreeStructure($a_startnode=null)
restoreSubTrees($a_nodes)
Restore objects (and their subobjects) to RecoveryFolder.
purgeUnboundObjects($a_nodes=NULL)
Removes all invalid objects from system.
setModeDependencies()
Sets modes by considering mode dependencies; some modes require other modes to be activated.
getUnboundObjects()
Gets all tree entries having no valid parent (=> no valid path to root node) Returns an array with ch...
restoreDeletedObjects($a_nodes)
Restore deleted objects (and their subobjects) to RecoveryFolder.
isModeEnabled($a_mode)
Is a particular mode enabled?
get_last_scan($a_scan_log)
getPossibleModes()
get possible ilValidator modes @access public
findDeletedObjects()
Search database for all tree entries having no valid parent (=> no valid path to root node) and store...
hasScanLog()
Quickly determine if there is a scan log.
dumpTree()
Dumps the Tree structure into the scan log.
findInvalidChilds()
Search database for all tree entries without any link to a valid object and stores result in $this->i...
restoreMissingObjects($a_missing_objects=NULL)
Restores missing reference and/or tree entry for all objects found by this::getMissingObjects() Resto...
setMode($a_mode, $a_value)
set mode of ilValidator Usage: setMode("restore",true) => enable object restorey setMode("all",...
findMissingObjects()
Search database for all object entries with missing reference and/or tree entry and stores result in ...
findInvalidRBACEntries()
Search database for all role entries that are linked to invalid ref_ids.
purgeMissingObjects($a_nodes=NULL)
Removes all missing objects from system.
removeInvalidReferences($a_invalid_refs=NULL)
Removes all reference entries that are linked with invalid object IDs.
findInvalidReferences()
Search database for all reference entries that are not linked with a valid object id and stores resul...
findInvalidRolefolders()
Search database for all rolefolder object entries with missing reference entry.
validate()
Performs the validation for each enabled mode.
getMissingObjects()
Gets all object entries with missing reference and/or tree entry.
ilValidator($a_log=false)
Constructor.