public function LearningPathStepsController::start in Opigno Learning path 3.x
Same name and namespace in other branches
- 8 src/Controller/LearningPathStepsController.php \Drupal\opigno_learning_path\Controller\LearningPathStepsController::start()
Start the learning path.
This page will redirect the user to the first learning path content.
1 string reference to 'LearningPathStepsController::start'
File
- src/
Controller/ LearningPathStepsController.php, line 149
Class
- LearningPathStepsController
- Class LearningPathStepsController.
Namespace
Drupal\opigno_learning_path\ControllerCode
public function start(Group $group, $type = 'group') {
// Create empty result attempt if current attempt doesn't exist.
// Will be used to detect if user already started LP or not.
$current_attempt = opigno_learning_path_started($group, \Drupal::currentUser());
$this->source_type = $type;
$this->group = $group;
if (!$current_attempt) {
$result = LPResult::createWithValues($group
->id(), \Drupal::currentUser()
->id(), FALSE, 0);
$result
->save();
}
$user = $this
->currentUser();
$uid = $user
->id();
$gid = $group
->id();
$is_owner = $uid === $group
->getOwnerId();
$is_ajax = \Drupal::request()
->isXmlHttpRequest();
// Load group steps.
$steps = LearningPathContent::getAllStepsOnlyModules($gid, $uid);
foreach ($steps as $step) {
if (in_array($step['typology'], [
'Meeting',
'ILT',
])) {
// If training starts with a mandatory live meeting
// or instructor-led training, check requirements.
$is_mandatory = $step['mandatory'] === 1;
if ($step['typology'] === 'Meeting') {
/** @var \Drupal\opigno_moxtra\MeetingInterface $entity */
$entity = $this
->entityTypeManager()
->getStorage('opigno_moxtra_meeting')
->load($step['id']);
if (!$entity
->isMember($uid)) {
$is_mandatory = FALSE;
}
}
elseif ($step['typology'] === 'ILT') {
/** @var \Drupal\opigno_ilt\ILTInterface $entity */
$entity = $this
->entityTypeManager()
->getStorage('opigno_ilt')
->load($step['id']);
if (!$entity
->isMember($uid)) {
$is_mandatory = FALSE;
}
}
if ($is_mandatory) {
$name = $step['name'];
$required = $step['required score'];
if ($required >= 0 || $step['typology'] == 'Meeting' && !$is_owner) {
if ($step['best score'] < $required || OpignoGroupManagerController::mustBeVisitedMeeting($step, $group)) {
$course_entity = OpignoGroupManagedContent::load($step['cid']);
$course_content_type = $this->content_type_manager
->createInstance($course_entity
->getGroupContentTypeId());
$current_step_url = $course_content_type
->getStartContentUrl($course_entity
->getEntityId(), $gid);
return $this
->failedStep('none', $is_ajax, $this
->requiredStepMessage($name, $required, $current_step_url
->toString()));
}
}
else {
if ($step['attempts'] === 0) {
return $this
->failedStep('none', $is_ajax, $this
->requiredStepMessage($name));
}
}
}
}
else {
break;
}
}
// Skip live meetings and instructor-led trainings from the group steps.
$steps = array_filter($steps, function ($step) {
return !in_array($step['typology'], [
'Meeting',
'ILT',
]);
});
// Check that training is completed.
$is_completed = (int) $this->database
->select('opigno_learning_path_achievements', 'a')
->fields('a')
->condition('uid', $user
->id())
->condition('gid', $group
->id())
->condition('status', 'completed')
->countQuery()
->execute()
->fetchField() > 0;
if ($is_completed) {
// Load steps from cache table.
$results = $this->database
->select('opigno_learning_path_step_achievements', 'a')
->fields('a', [
'id',
'typology',
'entity_id',
'parent_id',
'position',
])
->condition('uid', $user
->id())
->condition('gid', $group
->id())
->execute()
->fetchAllAssoc('id');
if (!empty($results)) {
// Check training structure.
$is_valid = TRUE;
$steps_mandatory = array_filter($steps, function ($step) {
return $step['mandatory'];
});
foreach ($steps_mandatory as $step) {
$filtered = array_filter($results, function ($result) use ($results, $step) {
if (isset($step['parent'])) {
$step_parent = $step['parent'];
$result_parent = isset($results[$result->parent_id]) ? $results[$result->parent_id] : NULL;
if (!isset($result_parent) || $result_parent->typology !== $step_parent['typology'] || (int) $result_parent->entity_id !== (int) $step_parent['id'] || (int) $result_parent->position !== (int) $step_parent['position']) {
return FALSE;
}
}
return $result->typology === $step['typology'] && (int) $result->entity_id === (int) $step['id'] && (int) $result->position === (int) $step['position'];
});
if (count($filtered) !== 1) {
$is_valid = FALSE;
break;
}
}
// If training is changed.
if (!$is_valid) {
$form = $this
->formBuilder()
->getForm('Drupal\\opigno_learning_path\\Form\\DeleteAchievementsForm', $group);
if ($is_ajax) {
$redirect = $this
->redirectToHome('', TRUE);
if ($redirect) {
return $redirect;
}
else {
return (new AjaxResponse())
->addCommand(new OpenModalDialogCommand('', $form));
}
}
else {
return $form;
}
}
}
}
// Get training guided navigation option.
$freeNavigation = !OpignoGroupManagerController::getGuidedNavigation($group);
if ($freeNavigation) {
$content = OpignoGroupManagedContent::getFirstStep($group
->id());
if ($content
->getGroupContentTypeId() != 'ContentTypeCourse') {
$content_type = $this->content_type_manager
->createInstance($content
->getGroupContentTypeId());
$step_url = $content_type
->getStartContentUrl($content
->getEntityId(), $group
->id());
if ($is_ajax) {
return (new AjaxResponse())
->addCommand(new RedirectCommand($step_url
->toString()));
}
else {
return $this
->redirect($step_url
->getRouteName(), $step_url
->getRouteParameters(), $step_url
->getOptions());
}
}
}
// Check if there is resumed step. If is - redirect.
$step_resumed_cid = opigno_learning_path_resumed_step($steps);
if ($step_resumed_cid) {
$content = OpignoGroupManagedContent::load($step_resumed_cid);
// Find and load the content type linked to this content.
$content_type = $this->content_type_manager
->createInstance($content
->getGroupContentTypeId());
$step_url = $content_type
->getStartContentUrl($content
->getEntityId(), $group
->id());
// Before redirecting, keep the content ID in context.
OpignoGroupContext::setCurrentContentId($step_resumed_cid);
OpignoGroupContext::setGroupId($group
->id());
// Finally, redirect the user to the first step.
if ($is_ajax) {
return (new AjaxResponse())
->addCommand(new RedirectCommand($step_url
->toString()));
}
else {
return $this
->redirect($step_url
->getRouteName(), $step_url
->getRouteParameters(), $step_url
->getOptions());
}
}
// Get the first step of the learning path. If no steps, show a message.
$first_step = reset($steps);
if ($first_step === FALSE) {
return $this
->failedStep('no_first', $is_ajax);
}
// Load first step entity.
$first_step = OpignoGroupManagedContent::load($first_step['cid']);
// Find and load the content type linked to this content.
$content_type = $this->content_type_manager
->createInstance($first_step
->getGroupContentTypeId());
// Finally, get the "start" URL
// If no URL, show a message.
$step_url = $content_type
->getStartContentUrl($first_step
->getEntityId(), $group
->id());
if (empty($step_url)) {
return $this
->failedStep('no_url', $is_ajax);
}
// Before redirecting, keep the content ID in context.
OpignoGroupContext::setCurrentContentId($first_step
->id());
OpignoGroupContext::setGroupId($group
->id());
// Finally, redirect the user to the first step.
if ($is_ajax) {
return (new AjaxResponse())
->addCommand(new RedirectCommand($step_url
->toString()));
}
else {
return $this
->redirect($step_url
->getRouteName(), $step_url
->getRouteParameters(), $step_url
->getOptions());
}
}