ILIAS  release_5-2 Revision v5.2.25-18-g3f80b828510
class.ilStudyProgrammeUserProgress.php
Go to the documentation of this file.
1 <?php
2 
3 /* Copyright (c) 2015 Richard Klees <richard.klees@concepts-and-training.de> Extended GPL, see docs/LICENSE */
4 
5 require_once("./Modules/StudyProgramme/classes/model/class.ilStudyProgrammeProgress.php");
6 
16  protected $progress; // ilStudyProgrammeProgress
17 
27  public function __construct($a_ids_or_model) {
28  if ($a_ids_or_model instanceof ilStudyProgrammeProgress) {
29  $this->progress = $a_ids_or_model;
30  }
31  else {
32  if (count($a_ids_or_model) != 3) {
33  throw new ilException("ilStudyProgrammeUserProgress::__construct: "
34  ."expected array with 3 items.");
35  }
36 
37  // TODO: ActiveRecord won't be caching the model objects, since
38  // we are not using find. Maybe we should do this ourselves??
39  // Or should we instead cache in getInstance?
40  $this->progress = array_shift(
42  ( "assignment_id" => $a_ids_or_model[0]
43  , "prg_id" => $a_ids_or_model[1]
44  , "usr_id" => $a_ids_or_model[2]
45  ))->get());
46  }
47  if ($this->progress === null) {
48  throw new ilException("ilStudyProgrammeUserProgress::__construct: Could not find progress.");
49  }
50  }
51 
61  static public function getInstance($a_assignment_id, $a_program_id, $a_user_id) {
62  return new ilStudyProgrammeUserProgress(array($a_assignment_id, $a_program_id, $a_user_id));
63  }
64 
71  static public function getInstanceById($a_prgrs_id) {
72  $prgrs = ilStudyProgrammeProgress::find($a_prgrs_id);
73  if ($prgrs === null) {
74  throw new ilException("Unknown progress id $a_prgrs_id.");
75  }
76  return new ilStudyProgrammeUserProgress($prgrs);
77  }
78 
86  static public function getInstancesForUser($a_program_id, $a_user_id) {
88  ( "prg_id" => $a_program_id
89  , "usr_id" => $a_user_id
90  ))->get();
91  return array_values(array_map(function($dat) {
92  return new ilStudyProgrammeUserProgress($dat);
93  }, $progresses));
94  }
95 
106  static public function getInstanceForAssignment($a_program_id, $a_assignment_id) {
108  ( "prg_id" => $a_program_id
109  , "assignment_id" => $a_assignment_id
110  ))->get();
111  if (count($progresses) == 0) {
112  require_once("Modules/StudyProgramme/classes/exceptions/class.ilStudyProgrammeNoProgressForAssignmentException.php");
114  ("ilStudyProgrammeUserProgress::getInstanceForAssignment: "
115  ."Assignment '$a_assignment_id' does not belong to program "
116  ."'$a_program_id'");
117  }
118  return new ilStudyProgrammeUserProgress(array_shift($progresses));
119  }
120 
131  static public function getInstancesForAssignment($a_assignment_id) {
133  ( "assignment_id" => $a_assignment_id
134  ))->get();
135  if (count($progresses) == 0) {
136  require_once("Modules/StudyProgramme/classes/exceptions/class.ilStudyProgrammeNoProgressForAssignmentException.php");
138  ("ilStudyProgrammeUserProgress::getInstancesForAssignment: "
139  ."Can't find progresses for assignment '$a_assignment_id'.");
140  }
141  return array_map(function($dat) {
142  return new ilStudyProgrammeUserProgress($dat);
143  }, $progresses);
144  }
145 
152  static public function getInstancesForProgram($a_program_id) {
154  ( "prg_id" => $a_program_id
155  ))->get();
156  return array_values(array_map(function($dat) {
157  return new ilStudyProgrammeUserProgress($dat);
158  }, $progresses));
159  }
160 
164  static public function statusToRepr($a_status) {
165  global $DIC;
166  $lng = $DIC['lng'];
167  $lng->loadLanguageModule("prg");
168 
170  return $lng->txt("prg_status_in_progress");
171  }
173  return $lng->txt("prg_status_completed");
174  }
176  return $lng->txt("prg_status_accredited");
177  }
179  return $lng->txt("prg_status_not_relevant");
180  }
181  throw new ilException("Unknown status: '$a_status'");
182  }
183 
194  public function getStudyProgramme() {
195  require_once("./Modules/StudyProgramme/classes/class.ilObjStudyProgramme.php");
196  $refs = ilObject::_getAllReferences($this->progress->getNodeId());
197  if (!count($refs)) {
198  throw new ilException("ilStudyProgrammeUserAssignment::getStudyProgramme: "
199  ."could not find ref_id for program '"
200  .$this->progress->getNodeId()."'.");
201  }
202  return ilObjStudyProgramme::getInstanceByRefId(array_shift($refs));
203  }
204 
210  public function getAssignment() {
211  require_once("Modules/StudyProgramme/classes/class.ilStudyProgrammeUserAssignment.php");
212  return ilStudyProgrammeUserAssignment::getInstance($this->progress->getAssignmentId());
213  }
214 
220  public function getId() {
221  return $this->progress->getId();
222  }
223 
229  public function getNodeId() {
230  return $this->progress->getNodeId();
231  }
232 
238  public function getUserId() {
239  return $this->progress->getUserId();
240  }
241 
247  public function getStatus() {
248  return $this->progress->getStatus();
249  }
250 
257  public function getAmountOfPoints() {
258  return $this->progress->getAmountOfPoints();
259  }
260 
266  public function getCurrentAmountOfPoints() {
267  if ( $this->isAccredited()
268  || ($this->isSuccessful() && $this->getStudyProgramme()->hasLPChildren())) {
269  return $this->getAmountOfPoints();
270  }
271  return $this->progress->getCurrentAmountOfPoints();
272  }
273 
279  public function getLastChange() {
280  return $this->progress->getLastChange();
281  }
282 
288  public function getLastChangeBy() {
289  return $this->progress->getLastChangeBy();
290  }
291 
297  public function getCompletionBy() {
298  return $this->progress->getCompletionBy();
299  }
300 
304  public function delete() {
305  $this->progress->delete();
306  }
307 
308 
319  public function markAccredited($a_user_id) {
321  $prg = $this->getStudyProgramme();
322  if ($prg->getStatus() == ilStudyProgramme::STATUS_OUTDATED) {
323  throw new ilException("ilStudyProgrammeUserProgress::markAccredited: "
324  ."Can't mark as accredited since program is outdated.");
325  }
326  }
327 
328  $this->progress->setStatus(ilStudyProgrammeProgress::STATUS_ACCREDITED)
329  ->setCompletionBy($a_user_id)
330  ->update();
331 
332  require_once("Modules/StudyProgramme/classes/class.ilStudyProgrammeEvents.php");
334 
335  $this->updateParentStatus();
336  return $this;
337  }
338 
347  public function unmarkAccredited() {
348  if ($this->progress->getStatus() != ilStudyProgrammeProgress::STATUS_ACCREDITED) {
349  throw new ilException("Expected status ACCREDITED.");
350  }
351 
352  $this->progress->setStatus(ilStudyProgrammeProgress::STATUS_IN_PROGRESS)
353  ->setCompletionBy(null)
354  ->update();
355 
356  $this->refreshLPStatus();
357 
358  $this->updateParentStatus();
359  return $this;
360  }
361 
371  public function markNotRelevant($a_user_id) {
372  $this->progress->setStatus(ilStudyProgrammeProgress::STATUS_NOT_RELEVANT)
373  ->setCompletionBy($a_user_id)
374  ->setLastChangeBy($a_user_id)
375  ->update();
376 
377  $this->updateStatus();
378  return $this;
379  }
380 
390  public function markRelevant($a_user_id) {
391  if ($this->progress->getStatus() != ilStudyProgrammeProgress::STATUS_NOT_RELEVANT) {
392  throw new ilException("Expected status IN_PROGRESS.");
393  }
394 
395  $this->progress->setStatus(ilStudyProgrammeProgress::STATUS_IN_PROGRESS)
396  ->setCompletionBy($a_user_id)
397  ->setLastChangeBy($a_user_id)
398  ->update();
399 
400  $this->updateStatus();
401  return $this;
402  }
403 
414  public function setRequiredAmountOfPoints($a_points, $a_user_id) {
415  $this->progress->setAmountOfPoints($a_points)
416  ->setLastChangeBy($a_user_id)
417  ->update();
418 
419  $this->updateStatus();
420  return $this;
421  }
422 
435  public function getMaximumPossibleAmountOfPoints($only_relevant = false) {
436  $prg = $this->getStudyProgramme();
437  if ($prg->getLPMode() == ilStudyProgramme::MODE_LP_COMPLETED) {
438  return $this->getAmountOfPoints();
439  }
440  $children = $prg->getChildren();
441  $ass = $this->progress->getAssignmentId();
442  $points = array_map(function($child) use ($ass, $only_relevant) {
443  $relevant = $child->getProgressForAssignment($ass)->isRelevant();
444  if($only_relevant) {
445  if($relevant) {
446  return $child->getProgressForAssignment($ass)->getAmountOfPoints();
447  } else {
448  return 0;
449  }
450  } else {
451  return $child->getProgressForAssignment($ass)->getAmountOfPoints();
452  }
453  }, $children);
454 
455  return array_reduce($points, function($a, $b) { return $a + $b; }, 0);
456  }
457 
464  public function canBeCompleted() {
465  $prg = $this->getStudyProgramme();
466 
467  if ($prg->getLPMode() == ilStudyProgramme::MODE_LP_COMPLETED) {
468  return true;
469  }
470 
471  if ($this->getMaximumPossibleAmountOfPoints(true) < $this->getAmountOfPoints()) {
472  // Fast track
473  return false;
474  }
475 
476  $children_progress = $this->getChildrenProgress();
477  foreach ($children_progress as $progress) {
478  if ($progress->isRelevant() && !$progress->canBeCompleted()) {
479  return false;
480  }
481  }
482  return true;
483  }
484 
490  public function hasIndividualModifications() {
491  return $this->getLastChangeBy() !== null;
492  }
493 
500  public function isSuccessful() {
501  $status = $this->getStatus();
502 
505  }
506 
512  public function isAccredited() {
513  $status = $this->getStatus();
514 
516  }
517 
523  public function isRelevant() {
525  }
526 
534  public function updateFromProgramNode() {
535  if ($this->hasIndividualModifications()) {
536  return false;
537  }
539  return false;
540  }
541 
542  $prg = $this->getStudyProgramme();
543  $this->progress->setAmountOfPoints($prg->getPoints())
544  ->setStatus($prg->getStatus() == ilStudyProgramme::STATUS_ACTIVE
547  )
548  ->update();
549 
550  $this->updateStatus();
551  }
552 
557  protected function updateStatus() {
558  $prg = $this->getStudyProgramme();
559  if (( $prg->getLPMode() == ilStudyProgramme::MODE_LP_COMPLETED
562  // Nothing to do here, as the status will be set by LP.
563  // OR current status is NOT RELEVANT
564  return;
565  }
566 
567  $add = function($a, $b) { return $a + $b; };
568  $get_points = function($child) {
569  if (!$child->isSuccessful()) {
570  return 0;
571  }
572  return $child->getAmountOfPoints();
573  };
574 
575  $achieved_points = array_reduce(array_map($get_points, $this->getChildrenProgress()), $add);
576  if (!$achieved_points) {
577  $achieved_points = 0;
578  }
579  $successful = $achieved_points >= $this->getAmountOfPoints() && $this->hasSuccessfullChildren();
580  $status = $this->getStatus();
581 
582  $this->progress->setCurrentAmountOfPoints($achieved_points);
583  if ($successful) {
584  $this->progress->setStatus(ilStudyProgrammeProgress::STATUS_COMPLETED);
585  require_once("Modules/StudyProgramme/classes/class.ilStudyProgrammeEvents.php");
587  } else {
588  $this->progress->setStatus(ilStudyProgrammeProgress::STATUS_IN_PROGRESS);
589  }
590 
591  $this->progress->update();
592  $this->refreshLPStatus();
593  $this->updateParentStatus();
594  }
595 
596  protected function hasSuccessfullChildren()
597  {
598  foreach($this->getChildrenProgress() as $child) {
599  if($child->isSuccessful()) {
600  return true;
601  }
602  }
603  return false;
604  }
605 
609  protected function updateParentStatus() {
610  $parent = $this->getParentProgress();
611  if ($parent) {
612  $parent->updateStatus();
613  }
614  }
615 
626  public function setLPCompleted($a_obj_id, $a_usr_id) {
627  if ($this->isSuccessful() || !$this->isRelevant()) {
628  return true;
629  }
630 
631  $prg = $this->getStudyProgramme();
632  if ($prg->getLPMode() != ilStudyProgramme::MODE_LP_COMPLETED) {
633  throw new ilException("ilStudyProgrammeUserProgress::setLPCompleted: "
634  ."The node '".$prg->getId()."' is not in LP_COMPLETED mode.");
635  }
636  if ($this->getUserId() != $a_usr_id) {
637  throw new ilException("ilStudyProgrammeUserProgress::setLPCompleted: "
638  ."This progress does belong to user '".$this->getUserId()
639  ."' and not to user '$a_usr_id'");
640  }
641  if (!in_array($a_obj_id, $prg->getLPChildrenIds())) {
642  throw new ilException("ilStudyProgrammeUserProgress::setLPCompleted: "
643  ."Object '$a_obj_id' is no child of node '".$prg->getId()."'.");
644  }
645 
646  $this->progress->setStatus(ilStudyProgrammeProgress::STATUS_COMPLETED)
647  ->setCompletionBy($a_obj_id)
648  ->update();
649 
650  require_once("Modules/StudyProgramme/classes/class.ilStudyProgrammeEvents.php");
652 
653  $this->refreshLPStatus();
654  $this->updateParentStatus();
655  }
656 
661  protected function getParentProgress() {
662  $prg = $this->getStudyProgramme();
663  $parent = $prg->getParent();
664  if (!$parent) {
665  return null;
666  }
667 
668  if($this->getStudyProgramme()->getId() == $this->getAssignment()->getStudyProgramme()->getId()) {
669  return null;
670  }
671 
672  return $parent->getProgressForAssignment($this->progress->getAssignmentId());
673  }
674 
681  public function getChildrenProgress() {
682  $prg = $this->getStudyProgramme();
683  if ($prg->getLPMode() == ilStudyProgramme::MODE_LP_COMPLETED) {
684  throw new ilException("ilStudyProgrammeUserProgress::getChildrenProgress: "
685  ."There is some problem in the implementation. This "
686  ."method should only be callled for nodes in points "
687  ."mode.");
688  }
689 
690  $ass_id = $this->progress->getAssignmentId();
691  return array_map(function($child) use ($ass_id) {
692  return $child->getProgressForAssignment($ass_id);
693  }, $prg->getChildren());
694  }
695 
704  $prg = $this->getStudyProgramme();
705  $children = $prg->getChildren();
706  $ass_id = $this->progress->getAssignmentId();
707  $names = array();
708  foreach ($children as $child) {
709  $prgrs = $child->getProgressForAssignment($ass_id);
710  if (!$prgrs->isSuccessful()) {
711  continue;
712  }
713  $names[] = $child->getTitle();
714  }
715  return $names;
716  }
717 
718  const ACTION_MARK_ACCREDITED = "mark_accredited";
719  const ACTION_UNMARK_ACCREDITED = "unmark_accredited";
720  const ACTION_SHOW_INDIVIDUAL_PLAN = "show_individual_plan";
721  const ACTION_REMOVE_USER = "remove_user";
722 
730  static public function getPossibleActions($a_node_id, $a_root_prg_id, $a_status) {
731  $actions = array();
732  if ($a_node_id == $a_root_prg_id) {
733  $actions[] = self::ACTION_SHOW_INDIVIDUAL_PLAN;
734  $actions[] = self::ACTION_REMOVE_USER;
735  }
737  $actions[] = self::ACTION_UNMARK_ACCREDITED;
738  }
739  else if ($a_status == ilStudyProgrammeProgress::STATUS_IN_PROGRESS) {
740  $actions[] = self::ACTION_MARK_ACCREDITED;
741  }
742  return $actions;
743  }
744 
745  protected function refreshLPStatus() {
746  require_once("Services/Tracking/classes/class.ilLPStatusWrapper.php");
748  }
749 }
750 
751 ?>
getChildrenProgress()
Get the progresses on the child nodes of this node for the same assignment this progress belongs to...
static getInstance($a_assignment_id, $a_program_id, $a_user_id)
Get an instance.
Base class for ILIAS Exception handling.
static statusToRepr($a_status)
Get a user readable representation of a status.
static userSuccessful(ilStudyProgrammeUserProgress $a_progress)
getCurrentAmountOfPoints()
Get the amount of points the user currently achieved.
isRelevant()
Check whether this node is relevant for the user.
static getInstanceForAssignment($a_program_id, $a_assignment_id)
Get the instance for the assignment on the program.
updateParentStatus()
Update the status of the parent of this node.
setRequiredAmountOfPoints($a_points, $a_user_id)
Set the amount of points the user is required to have to complete this node.
getStudyProgramme()
Get the program node where this progress belongs to was made.
unmarkAccredited()
Set the node to in progress.
isSuccessful()
Check whether the user was successful on this node.
getStatus()
Get the status of the progress.
static _refreshStatus($a_obj_id, $a_users=null)
Set dirty.
getNodeId()
Get the id of the program node the progress belongs to.
isAccredited()
Check whether the user was accredited on this node.
Exception is thrown when a progress for some programme node and assignment is missing.
static where($where, $operator=null)
static getInstancesForUser($a_program_id, $a_user_id)
Get the instances that user has on program.
getAssignment()
Get the assignment this progress belongs to.
getParentProgress()
Get the progress on the parent node for the same assignment this progress belongs to...
static _getAllReferences($a_id)
get all reference ids of object
static getInstanceByRefId($a_ref_id)
Get an instance of ilObjStudyProgramme, use cache.
canBeCompleted()
Check whether the user can achieve enough points on the subnodes to be able to complete this node...
markNotRelevant($a_user_id)
Set the node to be not relevant for the user.
markAccredited($a_user_id)
Mark this progress as accredited.
getNamesOfCompletedOrAccreditedChildren()
Get a list with the names of the children of this node that a were completed or accredited for the gi...
static getInstancesForAssignment($a_assignment_id)
Get the instance for an assignment.
getLastChange()
Get the timestamp when the last change was made on this progress.
static getPossibleActions($a_node_id, $a_root_prg_id, $a_status)
Get a list with possible actions on a progress record.
getUserId()
Get the id of the user who is assigned.
getAmountOfPoints()
Get the amount of points needed to complete the node.
hasIndividualModifications()
Check whether there are individual modifications for the user on this program.
Create styles array
The data for the language used.
Class ilStudyProgrammeProgress.
getLastChangeBy()
Get the id of the user who did the last change on this progress.
setLPCompleted($a_obj_id, $a_usr_id)
Set this node to be completed due to a completed learning progress.
global $lng
Definition: privfeed.php:17
updateStatus()
Updates the status of this progress based on the status of the progress on the sub nodes...
getMaximumPossibleAmountOfPoints($only_relevant=false)
Get the maximum possible amount of points a user can achieve for the completion of this node...
global $DIC
markRelevant($a_user_id)
Set the node to be relevant for the user.
updateFromProgramNode()
Update the progress from its program node.
getCompletionBy()
Get the id of the user or course that lead to completion of this node.
__construct($a_ids_or_model)
Throws when id does not refer to a study programme progress.
static getInstancesForProgram($a_program_id)
Get the instances for a program node.
Represents the progress of a user at one node of a study programme.
static getInstanceById($a_prgrs_id)
Get an instance by progress id.