ILIAS  Release_4_1_x_branch Revision 61804
 All Data Structures Namespaces Files Functions Variables Groups Pages
class.ilCtrl.php
Go to the documentation of this file.
1 <?php
2 /* Copyright (c) 1998-2009 ILIAS open source, Extended GPL, see docs/LICENSE */
3 
11 class ilCtrl
12 {
13  const IL_RTOKEN_NAME = 'rtoken';
14 
16  var $forward; // forward array
17  var $parent; // parent array (reverse forward)
18  var $save_parameter; // save parameter array
19  var $return; // return commmands
20  var $call_hist = array(); // calling history
21  var $debug = array();
22  var $calls = array();
23  var $rtoken = false;
24 
28  function ilCtrl()
29  {
30  global $ilBench;
31 
32  $this->bench =& $ilBench;
33 
34  // initialisation
35  $this->init();
36 
37  // this information should go to xml files one day
38  $this->stored_trees = array
39  ("ilrepositorygui", "ilpersonaldesktopgui",
40  "illmpresentationgui", "illmeditorgui",
41  "iladministrationgui");
42  }
43 
49  function debug($str)
50  {
51  $this->debug[] = $str;
52  }
53 
59  function getDebug()
60  {
61  return $this->debug;
62  }
63 
67  function init()
68  {
69  $this->transit = array();
70  $this->forward = array(); // forward array
71  $this->forwards = array(); // forward array
72  $this->parent = array(); // parent array (reverse forward)
73  $this->save_parameter = array(); // save parameter array
74  $this->parameter = array(); // save parameter array
75  $this->return = ""; // return commmands
76  $this->location = array();
77  $this->tab = array();
78  $this->current_node = 0;
79  $this->module_dir = "";
80  $this->service_dir = "";
81  $this->call_node = array();
82  $this->root_class = "";
83  }
84 
91  function callBaseClass()
92  {
93  global $ilDB;
94 
95  $baseClass = strtolower($_GET["baseClass"]);
96 
97  // get class information
98  $mc_set = $ilDB->query("SELECT * FROM module_class WHERE LOWER(class) = ".
99  $ilDB->quote($baseClass, "text"));
100  $mc_rec = $ilDB->fetchAssoc($mc_set);
101  $module = $mc_rec["module"];
102  $class = $mc_rec["class"];
103  $class_dir = $mc_rec["dir"];
104 
105  if ($module != "")
106  {
107  $m_set = $ilDB->query("SELECT * FROM il_component WHERE name = ".
108  $ilDB->quote($module, "text"));
109  $m_rec = $ilDB->fetchAssoc($m_set);
110  $this->module_dir = $m_rec["type"]."/".$m_rec["name"];
111  include_once $this->module_dir."/".$class_dir."/class.".$class.".php";
112  }
113  else // check whether class belongs to a service
114  {
115  $mc_set = $ilDB->query("SELECT * FROM service_class WHERE LOWER(class) = ".
116  $ilDB->quote($baseClass, "text"));
117  $mc_rec = $ilDB->fetchAssoc($mc_set);
118 
119  $service = $mc_rec["service"];
120  $class = $mc_rec["class"];
121  $class_dir = $mc_rec["dir"];
122 
123  if ($service == "")
124  {
125  echo "Could not find entry in modules.xml or services.xml for ".
126  $baseClass." <br/>".str_replace("&", "<br />&", htmlentities($_SERVER["REQUEST_URI"]));
127  exit;
128  }
129 
130  // get service information
131  $m_set = $ilDB->query("SELECT * FROM il_component WHERE name = ".
132  $ilDB->quote($service, "text"));
133  $m_rec = $ilDB->fetchAssoc($m_set);
134  $this->service_dir = $m_rec["type"]."/".$m_rec["name"];
135 
136  include_once $this->service_dir."/".$class_dir."/class.".$class.".php";;
137  }
138 
139  // forward processing to base class
140  $this->getCallStructure(strtolower($baseClass));
141  $base_class_gui =& new $class();
142  $this->forwardCommand($base_class_gui);
143  }
144 
148  function getModuleDir()
149  {
150  return $this->module_dir;
151  }
152 
162  function &forwardCommand(&$a_gui_object)
163  {
164  $class = strtolower(get_class($a_gui_object));
165 //echo "<br>forward to $class";
166  $nr = $this->getNodeIdForTargetClass($this->current_node, $class);
167  if ($nr != "")
168  {
169  $current_node = $this->current_node;
170 
171  $this->current_node = $nr;
172 
173  if (DEVMODE == "1")
174  {
175  $this->call_hist[] = array("class" => get_class($a_gui_object),
176  "mode" => "execComm", "cmd" => $this->getCmd());
177  }
178 //echo "<br>class:".get_class($a_gui_object).":";
179  $html = $a_gui_object->executeCommand();
180 
181  // reset current node
182  $this->current_node = $current_node;
183 
184  return $html;
185 
186  }
187  echo "ERROR: Can't forward to class $class."; exit;
188  }
189 
197  function &getHTML(&$a_gui_object)
198  {
199  $class = strtolower(get_class($a_gui_object));
200 
201  $nr = $this->getNodeIdForTargetClass($this->current_node, $class);
202  if ($nr != "")
203  {
204  $current_node = $this->current_node;
205 
206  // set current node to new gui class
207  $this->current_node = $nr;
208 
209  if (DEVMODE == "1")
210  {
211  $this->call_hist[] = array("class" => get_class($a_gui_object),
212  "mode" => "getHtml", "cmd" => $this->getCmd());
213  }
214 
215  // get block
216  $html = $a_gui_object->getHTML();
217 
218  // reset current node
219  $this->current_node = $current_node;
220 
221  // return block
222  return $html;
223  }
224  echo "ERROR: Can't getHTML from class $class."; exit;
225  }
226 
236  function setContext($a_obj_id, $a_obj_type, $a_sub_obj_id = 0, $a_sub_obj_type = "")
237  {
238  $this->context_obj_id = $a_obj_id;
239  $this->context_obj_type = $a_obj_type;
240  $this->context_sub_obj_id = $a_sub_obj_id;
241  $this->context_sub_obj_type = $a_sub_obj_type;
242  }
243 
249  public function getContextObjId()
250  {
251  return $this->context_obj_id;
252  }
253 
259  public function getContextObjType()
260  {
261  return $this->context_obj_type;
262  }
263 
269  public function getContextSubObjId()
270  {
271  return $this->context_sub_obj_id;
272  }
273 
279  public function getContextSubObjType()
280  {
281  return $this->context_sub_obj_type;
282  }
283 
302  function getNodeIdForTargetClass($a_par_node, $a_class, $a_check = false)
303  {
304  $class = strtolower($a_class);
305  $this->readClassInfo($class);
306 
307  if ($a_par_node === 0 || $a_par_node == "")
308  {
309  return $this->getCidForClass($class);
310  }
311 
312 //return parent::getNodeIdForTargetClass($a_par_node, $a_class);
313  $this->readNodeInfo($a_par_node);
314 
315  $node_cid = $this->getCurrentCidOfNode($a_par_node);
316 
317  // target class is class of current node id
318  if ($class == $this->getClassForCid($node_cid))
319  {
320  return $a_par_node;
321  }
322 
323  // target class is child of current node id
324  if (isset($this->calls[$this->getClassForCid($node_cid)]) &&
325  is_array($this->calls[$this->getClassForCid($node_cid)]) &&
326  in_array($a_class, $this->calls[$this->getClassForCid($node_cid)]))
327  {
328  return $a_par_node.":".$this->getCidForClass($class);
329  }
330 
331  // target class is sibling
332  $par_cid = $this->getParentCidOfNode($a_par_node);
333  if ($par_cid != "")
334  {
335  if (is_array($this->calls[$this->getClassForCid($par_cid)]) &&
336  in_array($a_class, $this->calls[$this->getClassForCid($par_cid)]))
337  {
338  return $this->removeLastCid($a_par_node).":".$this->getCidForClass($class);;
339  }
340  }
341 
342  // target class is parent
343  $temp_node = $this->removeLastCid($a_par_node);
344  while($temp_node != "")
345  {
346  $temp_cid = $this->getCurrentCidOfNode($temp_node);
347  if ($this->getClassForCid($temp_cid) == $a_class)
348  {
349  return $temp_node;
350  }
351  $temp_node = $this->removeLastCid($temp_node);
352  }
353 
354  if ($a_check)
355  {
356  return false;
357  }
358 
359  // Please do NOT change these lines.
360  // Developers must be aware, if they use classes unknown to the controller
361  // otherwise certain problem will be extremely hard to track down...
362  echo "ERROR: Can't find target class $a_class for node $a_par_node ".
363  "(".$this->cid_class[$this->getParentCidOfNode($a_par_node)].").<br>";
364  error_log( "ERROR: Can't find target class $a_class for node $a_par_node ".
365  "(".$this->cid_class[$this->getParentCidOfNode($a_par_node)].")");
366 
367  if (DEVMODE == 1)
368  {
369  try
370  {
371  throw new Exception("");
372  }
373  catch(Exception $e)
374  {
375  echo "<pre>".$e->getTraceAsString()."</pre>";
376  }
377  }
378 
379  exit;
380  }
381 
388  function checkTargetClass($a_class)
389  {
390  if (!is_array($a_class))
391  {
392  $a_class = array($a_class);
393  }
394 
395  $nr = $this->current_node;
396  foreach ($a_class as $class)
397  {
398  $class = strtolower($class);
399 
400  if (!$this->getCidForClass($class, true))
401  {
402  return false;
403  }
404 
405  $nr = $this->getNodeIdForTargetClass($nr, $class, true);
406  if ($nr === false)
407  {
408  return false;
409  }
410  }
411  return true;
412  }
413 
419  function getCmdNode()
420  {
421  return $_GET["cmdNode"];
422  }
423 
431  function addLocation($a_title, $a_link, $a_target = "", $a_ref_id = 0)
432  {
433  $this->location[] = array("title" => $a_title,
434  "link" => $a_link, "target" => $a_target, "ref_id" => $a_ref_id);
435  }
436 
442  function getLocations()
443  {
444  return $this->location;
445  }
446 
455  function addTab($a_lang_var, $a_link, $a_cmd, $a_class)
456  {
457  $a_class = strtolower($a_class);
458 
459  $this->tab[] = array("lang_var" => $a_lang_var,
460  "link" => $a_link, "cmd" => $a_cmd, "class" => $a_class);
461  }
462 
468  function getTabs()
469  {
470  return $this->tab;
471  }
472 
479  function getCallHistory()
480  {
481  return $this->call_hist;
482  }
483 
500  function getCallStructure($a_class)
501  {
502  $this->readClassInfo($a_class);
503  }
504 
509 /* function storeCommonStructures()
510  {
511  global $ilDB;
512 
513  $ilDB->manipulate("DELETE FROM ctrl_structure");
514 
515  foreach ($this->stored_trees as $root_gui_class)
516  {
517  $this->call_node = array();
518  $this->forward = array();
519  $this->parent = array();
520  $this->readCallStructure($root_gui_class);
521  $ilDB->insert("ctrl_structure", array(
522  "root_class" => array("text", $root_gui_class),
523  "call_node" => array("text", serialize($this->call_node)),
524  "forward" => array("text", serialize($this->forward)),
525  "parent" => array("clob", serialize($this->parent))));
526  }
527  }
528 */
529 
533  function readCallStructure($a_class, $a_nr = 0, $a_parent = 0)
534  {
535  global $ilDB;
536 
537  $a_class = strtolower($a_class);
538 
539  $a_nr++;
540 
541  // determine call node structure
542  $this->call_node[$a_nr] = array("class" => $a_class, "parent" => $a_parent);
543 
544 //echo "<br>nr:$a_nr:class:$a_class:parent:$a_parent:";
545  $call_set = $ilDB->query("SELECT * FROM ctrl_calls WHERE parent = ".
546  $ilDB->quote(strtolower($a_class), "text").
547  " ORDER BY child", array("text"));
548  $a_parent = $a_nr;
549  while ($call_rec = $ilDB->fetchAssoc($call_set))
550  {
551  $a_nr = $this->readCallStructure($call_rec["child"], $a_nr, $a_parent);
552  $forw[] = $call_rec["child"];
553  }
554 
555  // determin forward and parent array
556  $this->forwards($a_class, $forw);
557 //echo "<br>forwards:".$a_class."<br>"; var_dump($forw);
558 
559  // determine root class
560  $this->root_class = $a_class;
561  return $a_nr;
562  }
563 
564 
571  private function forwards($a_from_class, $a_to_class)
572  {
573  $a_from_class = strtolower($a_from_class);
574 
575  if (is_array($a_to_class))
576  {
577  foreach($a_to_class as $to_class)
578  {
579  if ($a_from_class != "" && $to_class != "")
580  {
581  if (!is_array($this->forward[$a_from_class]) || !in_array(strtolower($to_class), $this->forward[$a_from_class]))
582  {
583  $this->forward[$a_from_class][] = strtolower($to_class);
584  }
585  if (!is_array($this->parent[strtolower($to_class)]) || !in_array($a_from_class, $this->parent[strtolower($to_class)]))
586  {
587  $this->parent[strtolower($to_class)][] = $a_from_class;
588  }
589  }
590  }
591  }
592  else
593  {
594  $to_class = $a_to_class;
595  if ($a_from_class != "" && $to_class != "")
596  {
597  if (!is_array($this->forward[$a_from_class]) || !in_array(strtolower($to_class), $this->forward[$a_from_class]))
598  {
599  $this->forward[$a_from_class][] = strtolower($to_class);
600  }
601  if (!is_array($this->parent[strtolower($to_class)]) || !in_array($a_from_class, $this->parent[strtolower($to_class)]))
602  {
603  $this->parent[strtolower($to_class)][] = $a_from_class;
604  }
605  }
606  }
607  }
608 
609 
629  public function saveParameter(&$a_obj, $a_parameter)
630  {
631  if (is_object($a_obj))
632  {
633  $this->saveParameterByClass(get_class($a_obj), $a_parameter);
634  }
635  }
636 
643  function saveParameterByClass($a_class, $a_parameter)
644  {
645  if (is_array($a_parameter))
646  {
647  foreach($a_parameter as $parameter)
648  {
649  $this->save_parameter[strtolower($a_class)][] = $parameter;
650  }
651  }
652  else
653  {
654  $this->save_parameter[strtolower($a_class)][] = $a_parameter;
655  }
656  }
657 
658 
681  public function setParameter(&$a_obj, $a_parameter, $a_value)
682  {
683  $this->parameter[strtolower(get_class($a_obj))][$a_parameter] = $a_value;
684  }
685 
686 
694  public function setParameterByClass($a_class, $a_parameter, $a_value)
695  {
696  $this->parameter[strtolower($a_class)][$a_parameter] = $a_value;
697  }
698 
699 
706  public function clearParameters(&$a_obj)
707  {
708  $this->clearParametersByClass(strtolower(get_class($a_obj)));
709  }
710 
717  public function clearParametersByClass($a_class)
718  {
719  $this->parameter[strtolower($a_class)] = array();
720  }
721 
730  function getNextClass()
731  {
732  $cmdNode = $this->getCmdNode();
733 //echo "<br>getNextClass (current node: ".$this->current_node."; cmd node: ".$cmdNode.") ";
734  if ($cmdNode == "")
735  {
736  return false;
737  }
738  else
739  {
740  if ($this->current_node == $cmdNode)
741  {
742 //echo "1:".$this->call_node[$cmdNode]["class"]."<br>";
743  //return $this->call_node[$cmdNode]["class"];
744  return "";
745  }
746  else
747  {
748  $path = $this->getPathNew($this->current_node, $cmdNode);
749 //var_dump($path);
750 //echo " - Next Node: ".$path[1];
751  $this->readCidInfo($this->getCurrentCidOfNode($path[1]));
752 //echo ":".$this->cid_class[$this->getCurrentCidOfNode($path[1])].":".$this->getCurrentCidOfNode($path[1]).":";
753  return $this->cid_class[$this->getCurrentCidOfNode($path[1])];
754  }
755  }
756  }
757 
764  function lookupClassPath($a_class_name)
765  {
766  global $ilDB;
767  $a_class_name = strtolower($a_class_name);
768 
769  $class_set = $ilDB->query("SELECT * FROM ctrl_classfile WHERE class = ".
770  $ilDB->quote($a_class_name, "text"));
771  $class_rec = $ilDB->fetchAssoc($class_set);
772 
773  if ($class_rec["plugin_path"] != "")
774  {
775  return $class_rec["plugin_path"]."/".$class_rec["filename"];
776  }
777  else
778  {
779  return $class_rec["filename"];
780  }
781  }
782 
791  function getClassForClasspath($a_class_path)
792  {
793  $path = pathinfo($a_class_path);
794  $file = $path["basename"];
795  $class = substr($file, 6, strlen($file) - 10);
796 
797  return $class;
798  }
799 
806  private function getPathNew($a_source_node, $a_target_node)
807  {
808 //if ($this->getCmdClass() == "ilmailfoldergui") echo "-".$a_source_node."-".$a_target_node."-";
809 //echo "-".$a_source_node."-".$a_target_node."-";
810 //echo "<br>:::$a_source_node:::";
811  if ($a_source_node == "1")
812  {
813  $a_source_node = "";
814  }
815  if (substr($a_target_node, 0, strlen($a_source_node)) != $a_source_node)
816  {
817  echo "ERROR: Path not found. Source:".$a_source_node.
818  ", Target:".$a_target_node;
819  exit;
820  }
821 //echo "<br>:::$a_source_node:::";
822  $temp_node = $a_source_node;
823 
824  $path = array();
825  if ($a_source_node != "")
826  {
827  $path = array($a_source_node);
828  }
829 
830  $diffstart = ($a_source_node == "")
831  ? 0
832  : strlen($a_source_node) + 1;
833  $diff = substr($a_target_node, $diffstart);
834 //echo "=$diff=$diffstart=";
835  $diff_arr = explode(":", $diff);
836  foreach($diff_arr as $cid)
837  {
838  if ($temp_node != "")
839  {
840  $temp_node.= ":";
841  }
842  $temp_node.= $cid;
843  $path[] = $temp_node;
844  }
845 //if ($this->getCmdClass() == "ilmailfoldergui") var_dump($path);
846 //var_dump($path);
847  return $path;
848  }
849 
855  public function setTargetScript($a_target_script)
856  {
857  $this->target_script = $a_target_script;
858  }
859 
860 
866  public function getTargetScript()
867  {
868  return $this->target_script;
869  }
870 
871 
880  public function initBaseClass($a_base_class)
881  {
882  $_GET["baseClass"] = $a_base_class;
883  $_GET["cmd"] = "";
884  $_GET["cmdClass"] = "";
885  $_GET["cmdNode"] = "";
886  $this->init();
887  }
888 
896  public function getCmd($a_default_cmd = "", $a_safe_commands = "")
897  {
898  $cmd = "";
899  if (isset($_GET["cmd"]))
900  {
901  $cmd = $_GET["cmd"];
902  }
903  if($cmd == "post")
904  {
905  if (isset($_POST["cmd"]) && is_array($_POST["cmd"]))
906  {
907  reset($_POST["cmd"]);
908  }
909  $cmd = @key($_POST["cmd"]);
910 
911  // verify command
912  if ($this->verified_cmd != "")
913  {
914  return $this->verified_cmd;
915  }
916  else
917  {
918  if (!$this->verifyToken() &&
919  (!is_array($a_safe_commands) || !in_array($cmd, $a_safe_commands)))
920  {
921  return $a_default_cmd;
922  }
923  }
924 
925  $this->verified_cmd = $cmd;
926  if($cmd == "" && isset($_POST["table_top_cmd"])) // selected command in multi-list (table2)
927  {
928  $cmd = @key($_POST["table_top_cmd"]);
929  $this->verified_cmd = $cmd;
930  $_POST[$_POST["cmd_sv"][$cmd]] = $_POST[$_POST["cmd_sv"][$cmd]."_2"];
931  }
932  if($cmd == "" && isset($_POST["select_cmd2"])) // selected command in multi-list (table2)
933  {
934  $cmd = $_POST["selected_cmd2"];
935  $this->verified_cmd = $cmd;
936  }
937  if($cmd == "" && isset($_POST["select_cmd"])) // selected command in multi-list (table2)
938  {
939  $cmd = $_POST["selected_cmd"];
940  $this->verified_cmd = $cmd;
941  }
942  if($cmd == "")
943  {
944  $cmd = $_GET["fallbackCmd"];
945  $this->verified_cmd = $cmd;
946  }
947  }
948  if($cmd == "")
949  {
950  $cmd = $a_default_cmd;
951  }
952  return $cmd;
953  }
954 
965  function setCmd($a_cmd)
966  {
967  $_GET["cmd"] = $a_cmd;
968  }
969 
980  public function setCmdClass($a_cmd_class)
981  {
982  $a_cmd_class = strtolower($a_cmd_class);
983  $nr = $this->getNodeIdForTargetClass($this->current_node, $a_cmd_class);
984  $_GET["cmdClass"] = $a_cmd_class;
985  $_GET["cmdNode"] = $nr;
986  }
987 
993  function getCmdClass()
994  {
995  return strtolower($_GET["cmdClass"]);
996  }
997 
1008  function getFormAction(&$a_gui_obj, $a_fallback_cmd = "", $a_anchor = "", $a_asynch = false,
1009  $xml_style = true)
1010  {
1011  $script = $this->getFormActionByClass(strtolower(get_class($a_gui_obj)),
1012  $a_fallback_cmd, $a_anchor, $a_asynch, $xml_style);
1013  return $script;
1014  }
1015 
1026  function getFormActionByClass($a_class, $a_fallback_cmd = "", $a_anchor = "", $a_asynch = false,
1027  $xml_style = true)
1028  {
1029  $a_class = strtolower($a_class);
1030 
1031  $tok = $this->getRequestToken();
1032 
1033  if ($a_asynch)
1034  {
1035  $xml_style = false;
1036  }
1037 
1038  $script = $this->getLinkTargetByClass($a_class, "post", "", $a_asynch);
1039  if ($a_fallback_cmd != "")
1040  {
1041  $script = ilUtil::appendUrlParameterString($script, "fallbackCmd=".$a_fallback_cmd, $xml_style);
1042  }
1043  $script = ilUtil::appendUrlParameterString($script, self::IL_RTOKEN_NAME.'='.$this->getRequestToken(),
1044  $xml_style);
1045  if ($a_anchor != "")
1046  {
1047  $script = $script."#".$a_anchor;
1048  }
1049 
1050  return $script;
1051  }
1052 
1059  public function appendRequestTokenParameterString($a_url, $xml_style = true)
1060  {
1061  return ilUtil::appendUrlParameterString($a_url, self::IL_RTOKEN_NAME.'='.$this->getRequestToken(),
1062  $xml_style);
1063  }
1064 
1070  public function getRequestToken()
1071  {
1072  global $ilDB, $ilUser;
1073 
1074  if ($this->rtoken != "")
1075  {
1076  return $this->rtoken;
1077  }
1078  else
1079  {
1080  if (is_object($ilDB) && is_object($ilUser) && $ilUser->getId() > 0 &&
1081  $ilUser->getId() != ANONYMOUS_USER_ID)
1082  {
1083  $res = $ilDB->query("SELECT token FROM il_request_token WHERE user_id = ".
1084  $ilDB->quote($ilUser->getId(), "integer").
1085  " AND session_id = ".$ilDB->quote(session_id(), "text"));
1086  $rec = $ilDB->fetchAssoc($res);
1087 
1088  if ($rec["token"] != "")
1089  {
1090  return $rec["token"];
1091  }
1092 
1093  $this->rtoken = md5(uniqid(rand(), true));
1094 
1095  // delete entries older than two days
1096  if (rand(1, 200) == 2)
1097  {
1098  $dt = new ilDateTime(time(),IL_CAL_UNIX);
1099  $dt->increment(IL_CAL_DAY, -2);
1100  $dq = "DELETE FROM il_request_token WHERE ".
1101  " stamp < ".$ilDB->quote($dt->get(IL_CAL_DATETIME), "timestamp");
1102  $ilDB->manipulate($dq);
1103  }
1104 
1105  // IMPORTANT: Please do NOT try to move this implementation to a
1106  // session basis. This will fail due to framesets that are used
1107  // occasionally in ILIAS, e.g. in the chat, where multiple
1108  // forms are loaded in different frames.
1109  $ilDB->manipulate("INSERT INTO il_request_token (user_id, token, stamp, session_id) VALUES ".
1110  "(".
1111  $ilDB->quote($ilUser->getId(), "integer").",".
1112  $ilDB->quote($this->rtoken, "text").",".
1113  $ilDB->now().",".
1114  $ilDB->quote(session_id(), "text").")");
1115  return $this->rtoken;
1116  }
1117  //$this->rtoken = md5(uniqid(rand(), true));
1118  }
1119  return "";
1120  }
1121 
1127  private function verifyToken()
1128  {
1129  global $ilDB, $ilUser;
1130 
1131  if (is_object($ilUser) && is_object($ilDB) && $ilUser->getId() > 0 &&
1132  $ilUser->getId() != ANONYMOUS_USER_ID)
1133  {
1134  if ($_GET["rtoken"] == "")
1135  {
1136  echo "ilCtrl::No Request Token Given!"; // for debugging, maybe changed later
1137  return false;
1138  }
1139 
1140  $set = $ilDB->query("SELECT * FROM il_request_token WHERE ".
1141  " user_id = ".$ilDB->quote($ilUser->getId(), "integer")." AND ".
1142  " token = ".$ilDB->quote($_GET[self::IL_RTOKEN_NAME]), "text");
1143  if ($ilDB->numRows($set) > 0)
1144  {
1145  // remove used token
1146  /*
1147  $ilDB->query("DELETE FROM il_request_token WHERE ".
1148  " user_id = ".$ilDB->quote($ilUser->getId())." AND ".
1149  " token = ".$ilDB->quote($_GET[self::IL_RTOKEN_NAME]));
1150  */
1151 
1152  // remove tokens from older sessions
1153  $ilDB->manipulate("DELETE FROM il_request_token WHERE ".
1154  " user_id = ".$ilDB->quote($ilUser->getId(), "integer")." AND ".
1155  " session_id != ".$ilDB->quote(session_id(), "text"));
1156  return true;
1157  }
1158  else
1159  {
1160  return false;
1161  }
1162 
1163  if ($_SESSION["rtokens"][$_GET[self::IL_RTOKEN_NAME]] != "")
1164  {
1165  // remove used token
1166  unset($_SESSION["rtokens"][$_GET[self::IL_RTOKEN_NAME]]);
1167 
1168  // remove old tokens
1169  if (count($_SESSION["rtokens"]) > 100)
1170  {
1171  $to_remove = array();
1172  $sec = 7200; // two hours
1173 
1174  foreach($_SESSION["rtokens"] as $tok => $time)
1175  {
1176  if (time() - $time > $sec)
1177  {
1178  $to_remove[] = $tok;
1179  }
1180  }
1181  foreach($to_remove as $tok)
1182  {
1183  unset($_SESSION["rtokens"][$tok]);
1184  }
1185  }
1186 
1187  return true;
1188  }
1189  return false;
1190  }
1191  else
1192  {
1193  return true; // do not verify, if user or db object is missing
1194  }
1195 
1196  return false;
1197  }
1198 
1206  public function redirect(&$a_gui_obj, $a_cmd = "", $a_anchor = "")
1207  {
1208  global $ilBench;
1209 
1210  $script = $this->getLinkTargetByClass(strtolower(get_class($a_gui_obj)), $a_cmd,
1211  "", false, false);
1212  if (is_object($ilBench))
1213  {
1214  $ilBench->save();
1215  }
1216  if ($a_anchor != "")
1217  {
1218  $script = $script."#".$a_anchor;
1219  }
1220  ilUtil::redirect($script);
1221  }
1222 
1223 
1230  public function redirectByClass($a_class, $a_cmd = "")
1231  {
1232  $script = $this->getLinkTargetByClass($a_class, $a_cmd, "", false, false);
1233  ilUtil::redirect($script);
1234  }
1235 
1241  public function isAsynch()
1242  {
1243  if (isset($_GET["cmdMode"]) && $_GET["cmdMode"] == "asynch")
1244  {
1245  return true;
1246  }
1247  else
1248  {
1249  return false;
1250  }
1251  }
1252 
1253 
1265  function getLinkTarget(&$a_gui_obj, $a_cmd = "", $a_anchor = "", $a_asynch = false,
1266  $xml_style = true)
1267  {
1268  $script = $this->getLinkTargetByClass(strtolower(get_class($a_gui_obj)), $a_cmd, $a_anchor, $a_asynch,
1269  $xml_style);
1270  return $script;
1271  }
1272 
1273 
1285  function getLinkTargetByClass($a_class, $a_cmd = "", $a_anchor = "", $a_asynch = false,
1286  $xml_style = true)
1287  {
1288  if ($a_asynch)
1289  {
1290  $xml_style = false;
1291  }
1292 
1293  // note: $a_class may be an array
1294  //$a_class = strtolower($a_class);
1295 
1296 //echo "<br>getLinkTargetByClass";
1297  $script = $this->getTargetScript();
1298  $script = $this->getUrlParameters($a_class, $script, $a_cmd, $xml_style);
1299 
1300  if ($a_asynch)
1301  {
1302  //$amp = $xml_style
1303  // ? "&amp;"
1304  // : "&";
1305  $amp = "&";
1306  $script.= $amp."cmdMode=asynch";
1307  }
1308 
1309  if ($a_anchor != "")
1310  {
1311  $script = $script."#".$a_anchor;
1312  }
1313 
1314  return $script;
1315  }
1316 
1320  function setReturn(&$a_gui_obj, $a_cmd)
1321  {
1322  $script = $this->getTargetScript();
1323  $script = $this->getUrlParameters(strtolower(get_class($a_gui_obj)), $script, $a_cmd);
1324 //echo "<br>setReturn:".get_class($a_gui_obj).":".$script.":<br>";
1325  $this->return[strtolower(get_class($a_gui_obj))] = $script;
1326  }
1327 
1331  function setReturnByClass($a_class, $a_cmd)
1332  {
1333  // may not be an array!
1334  $a_class = strtolower($a_class);
1335 
1336  $script = $this->getTargetScript();
1337  $script = $this->getUrlParameters($a_class, $script, $a_cmd);
1338 //echo "<br>setReturn:".get_class($a_gui_obj).":".$script.":<br>";
1339  $this->return[strtolower($a_class)] = $script;
1340  }
1341 
1345  function returnToParent(&$a_gui_obj, $a_anchor = "")
1346  {
1347  $script = $this->getParentReturn($a_gui_obj);
1348 
1349  $script = ilUtil::appendUrlParameterString($script,
1350  "redirectSource=".strtolower(get_class($a_gui_obj)));
1351  $script = ilUtil::appendUrlParameterString($script,
1352  "cmdMode=".$_GET["cmdMode"]);
1353  if ($a_anchor != "")
1354  {
1355  $script = $script."#".$a_anchor;
1356  }
1357 
1358  ilUtil::redirect($script);
1359  }
1360 
1361 
1368  {
1369  return $_GET["redirectSource"];
1370  }
1371 
1375  function getParentReturn(&$a_gui_obj)
1376  {
1377  return $this->getParentReturnByClass(strtolower(get_class($a_gui_obj)));
1378  }
1379 
1380 
1384  function getParentReturnByClass($a_class)
1385  {
1386  $a_class = strtolower($a_class);
1387  $ret_class = $this->searchReturnClass($a_class);
1388 //echo ":$ret_class:";
1389  if($ret_class)
1390  {
1391 //echo ":".$this->return[$ret_class].":";
1392  return $this->return[$ret_class];
1393  }
1394  }
1395 
1399  private function searchReturnClass($a_class)
1400  {
1401  $a_class = strtolower($a_class);
1402 
1403  $node = $this->getNodeIdForTargetClass($this->current_node, $a_class);
1404  $n_arr = explode(":", $node);
1405  for($i = count($n_arr)-2; $i>=0; $i--)
1406  {
1407  if ($this->return[$this->getClassForCid($n_arr[$i])] != "")
1408  {
1409  return $this->getClassForCid($n_arr[$i]);
1410  }
1411  }
1412 
1413  return false;
1414  }
1415 
1419  public function getUrlParameters($a_class, $a_str, $a_cmd = "", $xml_style = false)
1420  {
1421  // note: $a_class may be an array!
1422  //$a_class = strtolower($a_class);
1423 
1424  $params = $this->getParameterArrayByClass($a_class, $a_cmd);
1425 
1426  foreach ($params as $par => $value)
1427  {
1428  if (strlen($value))
1429  {
1430  $a_str = ilUtil::appendUrlParameterString($a_str, $par."=".$value, $xml_style);
1431  }
1432  }
1433 
1434  return $a_str;
1435  }
1436 
1440  public function getParameterArray(&$a_gui_obj, $a_cmd = "")
1441  {
1442  $par_arr = $this->getParameterArrayByClass(strtolower(get_class($a_gui_obj)), $a_cmd);
1443 
1444  return $par_arr;
1445  }
1446 
1454  public function getParameterArrayByClass($a_class, $a_cmd = "")
1455  {
1456  if ($a_class == "")
1457  {
1458  return array();
1459  }
1460 
1461  if (!is_array($a_class))
1462  {
1463  $a_class = array($a_class);
1464  }
1465 
1466  $nr = $this->current_node;
1467  foreach ($a_class as $class)
1468  {
1469  $class = strtolower($class);
1470  $nr = $this->getNodeIdForTargetClass($nr, $class);
1471  $target_class = $class;
1472  }
1473 
1474  $path = $this->getPathNew(1, $nr);
1475  $params = array();
1476 
1477  // append parameters of parent classes
1478  foreach($path as $node_id)
1479  {
1480  $class = ($node_id == "")
1481  ? strtolower($_GET["baseClass"])
1482  : $this->getClassForCid($this->getCurrentCidOfNode($node_id));
1483  if (isset($this->save_parameter[$class]) && is_array($this->save_parameter[$class]))
1484  {
1485  foreach($this->save_parameter[$class] as $par)
1486  {
1487  if (isset($_GET[$par]))
1488  {
1489  $params[$par] = $_GET[$par];
1490  }
1491  }
1492  }
1493 
1494  if (isset($this->parameter[$class]) && is_array($this->parameter[$class]))
1495  {
1496  foreach($this->parameter[$class] as $par => $value)
1497  {
1498  $params[$par] = $value;
1499  }
1500  }
1501  }
1502 
1503  if ($a_cmd != "")
1504  {
1505  $params["cmd"] = $a_cmd;
1506  }
1507 
1508  $params["cmdClass"] = $target_class;
1509  $params["cmdNode"] = $nr;
1510  $params["baseClass"] = $_GET["baseClass"];
1511 
1512  return $params;
1513  }
1514 
1518  private function getCidForClass($a_class, $a_check = false)
1519  {
1520  if ($this->class_cid[$a_class] == "")
1521  {
1522  $this->readClassInfo($a_class);
1523  }
1524  if ($this->class_cid[$a_class] == "")
1525  {
1526  if ($a_check)
1527  {
1528  return false;
1529  }
1530  if (DEVMODE == 1)
1531  {
1532  $add = "<br><br>Please make sure your GUI class name ends with 'GUI' and that the filename is 'class.[YourClassName].php'. In exceptional cases you
1533  may solve the issue by putting an empty * @ilCtrl_Calls [YourClassName]: into your class header.".
1534  " In both cases you need to reload the control structure in the setup.";
1535  }
1536  die("Cannot find cid for class ".$a_class.".".$add);
1537  }
1538  return $this->class_cid[$a_class];
1539  }
1540 
1544  private function getClassForCid($a_cid)
1545  {
1546  if ($this->cid_class[$a_cid] == "")
1547  {
1548  $this->readCidInfo($a_cid);
1549  }
1550  if ($this->cid_class[$a_cid] == "")
1551  {
1552  die("Cannot find class for cid ".$a_cid.".");
1553  }
1554  return $this->cid_class[$a_cid];
1555  }
1556 
1562  private function readCidInfo($a_cid)
1563  {
1564  global $ilDB;
1565 
1566  if (isset($this->info_read_cid[$a_cid]))
1567  {
1568  return;
1569  }
1570  $set = $ilDB->query("SELECT * FROM ctrl_classfile ".
1571  " WHERE cid = ".$ilDB->quote($a_cid, "text")
1572  );
1573  if ($rec = $ilDB->fetchAssoc($set))
1574  {
1575  $this->cid_class[$a_cid] = $rec["class"];
1576  $this->class_cid[$rec["class"]] = $a_cid;
1577 
1578  $set = $ilDB->query("SELECT * FROM ctrl_calls ".
1579  " WHERE parent = ".$ilDB->quote($rec["class"], "text")
1580  );
1581  while ($rec2 = $ilDB->fetchAssoc($set))
1582  {
1583  if (!isset($this->calls[$rec["class"]]) || !is_array($this->calls[$rec["class"]]) || !in_array($rec2["child"], $this->calls[$rec["class"]]))
1584  {
1585  if ($rec2["child"] != "")
1586  {
1587  $this->calls[$rec["class"]][] = $rec2["child"];
1588  }
1589  }
1590  }
1591  $this->info_read_class[$rec["class"]] = true;
1592  }
1593 
1594  $this->info_read_cid[$a_cid] = true;
1595  }
1596 
1602  private function readNodeInfo($a_node)
1603  {
1604  $n_arr = explode(":", $a_node);
1605  foreach ($n_arr as $cid)
1606  {
1607  $this->readCidInfo($cid);
1608  }
1609  }
1610 
1616  private function readClassInfo($a_class)
1617  {
1618  global $ilDB;
1619 
1620  $a_class = strtolower($a_class);
1621  if (isset($this->info_read_class[$a_class]))
1622  {
1623  return;
1624  }
1625  $set = $ilDB->query("SELECT * FROM ctrl_classfile ".
1626  " WHERE class = ".$ilDB->quote($a_class, "text")
1627  );
1628  if ($rec = $ilDB->fetchAssoc($set))
1629  {
1630  $this->cid_class[$rec["cid"]] = $a_class;
1631  $this->class_cid[$a_class] = $rec["cid"];
1632  }
1633 
1634  $set = $ilDB->query("SELECT * FROM ctrl_calls ".
1635  " WHERE parent = ".$ilDB->quote($a_class, "text")
1636  );
1637  while ($rec = $ilDB->fetchAssoc($set))
1638  {
1639  if (!isset($this->calls[$a_class]) || !is_array($this->calls[$a_class]) || !in_array($rec["child"], $this->calls[$a_class]))
1640  {
1641  if ($rec["child"] != "")
1642  {
1643  $this->calls[$a_class][] = $rec["child"];
1644  }
1645  }
1646  }
1647 
1648  $this->info_read_class[$a_class] = true;
1649  $this->info_read_cid[$this->class_cid[$a_class]] = true;
1650  }
1651 
1655  private function getParentCidOfNode($a_node)
1656  {
1657  $n_arr = explode(":", $a_node);
1658  return $n_arr[count($n_arr) - 2];
1659  }
1660 
1664  private function removeLastCid($a_node)
1665  {
1666  $lpos = strrpos($a_node, ":");
1667  return substr($a_node, 0, $lpos);
1668  }
1669 
1673  private function getCurrentCidOfNode($a_node)
1674  {
1675  $n_arr = explode(":", $a_node);
1676  return $n_arr[count($n_arr) - 1];
1677  }
1678 
1685  function insertCtrlCalls($a_parent, $a_child, $a_comp_prefix)
1686  {
1687  global $ilDB;
1688 
1689  $a_parent = strtolower($a_parent);
1690  $a_child = strtolower($a_child);
1691  $a_comp_prefix = strtolower($a_comp_prefix);
1692 
1693  $set = $ilDB->query("SELECT * FROM ctrl_calls WHERE ".
1694  " parent = ".$ilDB->quote($a_parent, "text")." AND ".
1695  " child = ".$ilDB->quote($a_child, "text")." AND ".
1696  " comp_prefix = ".$ilDB->quote($a_comp_prefix, "text")
1697  );
1698  if ($rec = $ilDB->fetchAssoc($set))
1699  {
1700  return;
1701  }
1702  $ilDB->manipulate("INSERT INTO ctrl_calls ".
1703  "(parent, child, comp_prefix) VALUES (".
1704  $ilDB->quote($a_parent, "text").",".
1705  $ilDB->quote($a_child, "text").",".
1706  $ilDB->quote($a_comp_prefix, "text").
1707  ")");
1708  }
1709 
1710 }
1711 ?>