public static function CanUserViewLessonAsPublic($arParams) { // Parse options (user_id from $arParams will be automaticaly resolved) $options = self::ParseParamsWithUser($arParams, array('COURSE_ID' => array('type' => 'strictly_castable_to_integer', 'mandatory' => true), 'LESSON_ID' => array('type' => 'strictly_castable_to_integer', 'mandatory' => true))); // Is it course? $linkedLessonId = CCourse::CourseGetLinkedLesson($options['COURSE_ID']); if ($linkedLessonId === false) { return false; } // Access denied $lessonId = $options['LESSON_ID']; $breakOnLessonId = $linkedLessonId; // save resources // Is lesson included into given course? $isLessonChildOfCourse = false; $arOPathes = CLearnLesson::GetListOfParentPathes($lessonId, $breakOnLessonId); foreach ($arOPathes as $oPath) { $topLessonId = $oPath->GetTop(); if ($topLessonId !== false && $topLessonId == $linkedLessonId) { $isLessonChildOfCourse = true; break; } } if (!$isLessonChildOfCourse) { return false; } // Access denied // Check permissions for course $isCourseAccessible = self::CanUserViewLessonContent(array('lesson_id' => $linkedLessonId)); // Permissions for all lessons/chapters in public are equivalent to course permissions return $isCourseAccessible; }
protected static function GetDataWoCache($courseId) { $rsContent = CCourse::GetCourseContent($courseId, array(), array('LESSON_ID', 'NAME')); $arContents = array(); while ($arContent = $rsContent->GetNext()) { $arContents[] = $arContent; } return $arContents; }
function CheckFields(&$arFields, $ID = false) { global $DB, $APPLICATION; if ($ID === false && !is_set($arFields, "STUDENT_ID")) { $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_USER_ID"), "EMPTY_STUDENT_ID"); return false; } elseif (is_set($arFields, "STUDENT_ID")) { $dbResult = CUser::GetByID($arFields["STUDENT_ID"]); if (!$dbResult->Fetch()) { $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_USER_ID_EX"), "ERROR_NO_STUDENT_ID"); return false; } } if ($ID === false && !is_set($arFields, "COURSE_ID")) { $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_COURSE_ID"), "ERROR_EMPTY_COURSE_ID"); return false; } elseif (is_set($arFields, "COURSE_ID")) { if ($bCheckRights) { $r = CCourse::GetByID($arFields["COURSE_ID"]); } else { $r = CCourse::GetList(array(), array("ID" => $arFields["COURSE_ID"], 'CHECK_PERMISSIONS' => 'N')); } if (!$r->Fetch()) { $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_COURSE_ID_EX"), "ERROR_NO_COURSE_ID"); return false; } } if (is_set($arFields, "STUDENT_ID") && is_set($arFields, "COURSE_ID")) { $res = CCertification::GetList(array(), array("STUDENT_ID" => $arFields["STUDENT_ID"], "COURSE_ID" => $arFields["COURSE_ID"])); if ($res->Fetch()) { $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_CERTIFICATE_DUPLICATE"), "ERROR_CERTIFICATE_DUPLICATE"); return false; } } if (is_set($arFields, "DATE_CREATE") && !$DB->IsDate($arFields["DATE_CREATE"], false, LANG, "FULL")) { $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_DATE_CREATE"), "EMPTY_DATE_CREATE"); return false; } if (is_set($arFields, "PUBLIC_PROFILE") && $arFields["PUBLIC"] != "N") { $arFields["PUBLIC_PROFILE"] = "Y"; } if (is_set($arFields, "ACTIVE") && $arFields["ACTIVE"] != "N") { $arFields["ACTIVE"] = "Y"; } if (is_set($arFields, "FROM_ONLINE") && $arFields["FROM_ONLINE"] != "N") { $arFields["FROM_ONLINE"] = "Y"; } return true; }
function CCoursePackage($COURSE_ID) { global $DB; $this->ID = intval($COURSE_ID); //Course exists? $res = CCourse::GetByID($this->ID); if (!($this->arCourse = $res->Fetch())) { $this->LAST_ERROR = GetMessage("LEARNING_BAD_COURSE_ID_EX"); return false; } $res = CCourse::GetSite($this->ID); if ($arSite = $res->GetNext()) { $charset = $arSite["CHARSET"]; } else { $this->LAST_ERROR = GetMessage("LEARNING_BAD_SITE_ID_EX"); return false; } //Define charset if (strlen($charset) <= 0) { if (defined("SITE_CHARSET") && strlen(SITE_CHARSET) > 0) { $charset = SITE_CHARSET; } else { $charset = "windows-1251"; } } $this->charset = $charset; //Get chapters, lessons, questions $this->_GetCourseContent($this->arCourse['LESSON_ID']); //Get tests $strSql = "SELECT T.*, " . $DB->DateToCharFunction("T.TIMESTAMP_X") . " as TIMESTAMP_X " . "FROM b_learn_test T " . "WHERE T.COURSE_ID = " . intval($this->ID) . " " . "ORDER BY SORT ASC "; $res = $DB->Query($strSql, false, "File: " . __FILE__ . "<br>Line: " . __LINE__); while ($arRes = $res->Fetch()) { $r = ++$this->RefID; $this->arItems[$r] = $this->_CreateContent("TES", $arRes, $r); $this->strItems .= '<item identifier="TES' . $r . '" identifierref="RES' . $r . '"><title>' . htmlspecialcharsbx($arRes["NAME"]) . '</title>'; $marksRes = $DB->Query("SELECT * FROM b_learn_test_mark WHERE TEST_ID = '" . (string) (int) $arRes['ID'] . "'", false, "File: " . __FILE__ . "<br>Line: " . __LINE__); while ($arMarksRes = $marksRes->Fetch()) { $r = ++$this->RefID; $this->arItems[$r] = $this->CreateTMK($arMarksRes, $r); $this->strItems .= '<item identifier="TMK' . $r . '" identifierref="RES' . $r . '">' . '<title>' . htmlspecialcharsbx($arMarksRes['MARK'] . ' (' . $arMarksRes['DESCRIPTION'] . ')') . '</title>' . '</item>'; } $this->strItems .= '</item>'; $this->strResourses .= '<resource identifier="RES' . $r . '" type="webcontent" href="res' . $r . '.xml">' . $this->_GetResourceFiles($r) . '</resource>'; } }
public static function GetFilter($arFilter) { global $DBType; if (!is_array($arFilter)) { $arFilter = array(); } $arSqlSearch = array(); foreach ($arFilter as $key => $val) { $res = CLearnHelper::MkOperationFilter($key); $key = $res["FIELD"]; $cOperationType = $res["OPERATION"]; $key = strtoupper($key); switch ($key) { case "ID": case "SORT": case "LESSON_ID": case "POINT": $arSqlSearch[] = CLearnHelper::FilterCreate("CQ." . $key, $val, "number", $bFullJoin, $cOperationType); break; case "COURSE_ID": // was: $arSqlSearch[] = CLearnHelper::FilterCreate("C.".$key, $val, "number", $bFullJoin, $cOperationType); $courseLessonId = CCourse::CourseGetLinkedLesson($val); if ($courseLessonId === false) { break; } // it is not a course, so skipping if ($DBType === 'oracle') { // This subquery gets ids of all childs lesson for given $courseLessonId $subQuery = "\n\t\t\t\t\t\t\tSELECT TLE.TARGET_NODE\n\t\t\t\t\t\t\tFROM b_learn_lesson_edges TLE\n\t\t\t\t\t\t\tSTART WITH TLE.SOURCE_NODE=" . ($courseLessonId + 0) . "\n\t\t\t\t\t\t\tCONNECT BY NOCYCLE PRIOR TLE.TARGET_NODE = TLE.SOURCE_NODE"; // But we need also $courseLessonId itself, so final clause will be: $arSqlSearch[] = '(CQ.LESSON_ID IN (' . $subQuery . ') OR CQ.LESSON_ID = ' . ($courseLessonId + 0) . ')'; } elseif ($DBType === 'mysql' || $DBType === 'mssql') { // MySQL & MSSQL supports "WHERE IN(...)" clause for more than 10 000 elements // add to sql "WHERE" constraint: lessons id only from given array $sqlCourseLessonsIdsList = ''; $oTree = CLearnLesson::GetTree($courseLessonId); $arChildLessonForCourse = $oTree->GetLessonsIdListInTree(); // root lesson not in tree, so add it $arChildLessonForCourse[] = $courseLessonId; // We need escape data for SQL $arChildLessonForCourseEscaped = array_map('intval', $arChildLessonForCourse); $sqlCourseLessonsIdsList = implode(', ', $arChildLessonForCourseEscaped); if (strlen($sqlCourseLessonsIdsList) > 0) { $arSqlSearch[] = 'CQ.LESSON_ID IN (' . $sqlCourseLessonsIdsList . ')'; } } else { throw new LearnException('Unsupported DB engine: ' . $DBType, LearnException::EXC_ERR_ALL_GIVEUP); } break; case "NAME": $arSqlSearch[] = CLearnHelper::FilterCreate("CQ." . $key, $val, "string", $bFullJoin, $cOperationType); break; case "QUESTION_TYPE": case "ACTIVE": case "SELF": case "CORRECT_REQUIRED": $arSqlSearch[] = CLearnHelper::FilterCreate("CQ." . $key, $val, "string_equal", $bFullJoin, $cOperationType); break; } } return $arSqlSearch; }
protected static function _CreateAttemptQuestions($arCallbackSqlFormer, $ATTEMPT_ID) { global $APPLICATION, $DB, $DBType; $ATTEMPT_ID = intval($ATTEMPT_ID); $attempt = CTestAttempt::GetByID($ATTEMPT_ID); if (!($arAttempt = $attempt->Fetch())) { $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_ATTEMPT_ID_EX"), "ERROR_NO_ATTEMPT_ID"); return false; } $test = CTest::GetByID($arAttempt["TEST_ID"]); if (!($arTest = $test->Fetch())) { $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_TEST_ID_EX"), "ERROR_NO_TEST_ID"); return false; } $strSql = "DELETE FROM b_learn_test_result WHERE ATTEMPT_ID = " . $ATTEMPT_ID; if (!$DB->Query($strSql, false, "File: " . __FILE__ . "<br>Line: " . __LINE__)) { return false; } /** * QUESTIONS_FROM values: * 'L' - X questions from every lesson in course * 'C' - X questions from every lesson from every chapter in the course * In this case questions taken from immediate lessons of all chapters (X per chapter) in the course. * In new data model it means, get X questions from every lesson in the course, except * 1) immediate lessons-childs of the course and * 2) lessons, contains other lessons (because, in old data model chapters doesn't contains questions) * * 'H' - all questions from the selected chapter (recursive) in the course * This case must be ignored, because converter to new data model updates 'H' to 'R', but in case * when chapter is not exists updates didn't become. So QUESTIONS_FROM stayed in 'H' value. And it means, * that there is no chapter exists with QUESTIONS_FROM_ID, so we can't do work. And we should just * ignore, for backward compatibility (so, don't throw an error). * 'S' - all questions from the selected lesson (unilesson_id in QUESTIONS_FROM_ID) * 'A' - all questions of the course (nothing interesting in QUESTIONS_FROM_ID) * * new values: * 'R' - all questions from the tree with root at selected lesson (include questions of selected lesson) * in the course (unilesson_id in QUESTIONS_FROM_ID) */ if ($arTest["QUESTIONS_FROM"] == "C" || $arTest["QUESTIONS_FROM"] == "L") { $courseId = $arTest['COURSE_ID'] + 0; $courseLessonId = CCourse::CourseGetLinkedLesson($courseId); if ($courseLessonId === false) { $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_TEST_IS_EMPTY"), "ERROR_TEST_IS_EMPTY"); return false; } $clauseAllChildsLessons = CLearnHelper::SQLClauseForAllSubLessons($courseLessonId); if ($arTest["QUESTIONS_FROM"] == "C") { $strSql = "SELECT Q.ID as QUESTION_ID, TLEUP.SOURCE_NODE as FROM_ID\n\t\t\t\tFROM b_learn_lesson L\n\t\t\t\tINNER JOIN b_learn_question Q ON L.ID = Q.LESSON_ID\n\t\t\t\tINNER JOIN b_learn_lesson_edges TLEUP ON L.ID = TLEUP.TARGET_NODE\n\t\t\t\tLEFT OUTER JOIN b_learn_lesson_edges TLEDOWN ON L.ID = TLEDOWN.SOURCE_NODE " . "WHERE L.ID IN (" . $clauseAllChildsLessons . ") \n" . " AND TLEDOWN.SOURCE_NODE IS NULL \n" . " AND TLEUP.SOURCE_NODE IN (" . $clauseAllChildsLessons . ") \n" . " AND Q.ACTIVE = 'Y' " . ($arTest["INCLUDE_SELF_TEST"] != "Y" ? "AND Q.SELF = 'N' " : "") . "ORDER BY " . ($arTest["RANDOM_QUESTIONS"] == "Y" ? CTest::GetRandFunction() : "L.SORT, Q.SORT"); } else { $strSql = "SELECT Q.ID as QUESTION_ID, L.ID as FROM_ID " . "FROM b_learn_lesson L " . "INNER JOIN b_learn_question Q ON L.ID = Q.LESSON_ID " . "WHERE L.ID IN (" . $clauseAllChildsLessons . ") AND Q.ACTIVE = 'Y' " . ($arTest["INCLUDE_SELF_TEST"] != "Y" ? "AND Q.SELF = 'N' " : "") . "ORDER BY " . ($arTest["RANDOM_QUESTIONS"] == "Y" ? CTest::GetRandFunction() : "L.SORT, Q.SORT"); } if (!($res = $DB->Query($strSql, false, "File: " . __FILE__ . "<br>Line: " . __LINE__))) { return false; } $Values = array(); $tmp = array(); while ($arRecord = $res->Fetch()) { if (is_set($tmp, $arRecord["FROM_ID"])) { if ($tmp[$arRecord["FROM_ID"]] < $arTest["QUESTIONS_AMOUNT"]) { $tmp[$arRecord["FROM_ID"]]++; } else { continue; } } else { $tmp[$arRecord["FROM_ID"]] = 1; } $Values[] = $arRecord["QUESTION_ID"]; } if (empty($Values)) { $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_TEST_IS_EMPTY"), "ERROR_TEST_IS_EMPTY"); return false; } $DB->StartTransaction(); foreach ($Values as $ID) { $strSql = "INSERT INTO b_learn_test_result (ATTEMPT_ID, QUESTION_ID) VALUES (" . $ATTEMPT_ID . "," . $ID . ")"; if (!$DB->Query($strSql, false, "File: " . __FILE__ . "<br>Line: " . __LINE__)) { $DB->Rollback(); return false; } } $DB->Commit(); } elseif (($arTest["QUESTIONS_FROM"] == "H" || $arTest["QUESTIONS_FROM"] == "S" || $arTest["QUESTIONS_FROM"] == "R") && $arTest["QUESTIONS_FROM_ID"]) { $WHERE = ''; if ($arTest["QUESTIONS_FROM"] == "H") { /** * 'H' - all questions from the selected chapter (recursive) in the course * This case must be ignored, because converter to new data model updates 'H' to 'R', but in case * when chapter is not exists updates didn't become. So QUESTIONS_FROM stayed in 'H' value. And it means, * that there is no chapter exists with QUESTIONS_FROM_ID, so we can't do work. And we should just * ignore, for backward compatibility (so, don't throw an error). */ $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_TEST_IS_EMPTY"), "ERROR_TEST_IS_EMPTY"); return false; } elseif ($arTest["QUESTIONS_FROM"] == 'R') { $clauseAllChildsLessons = CLearnHelper::SQLClauseForAllSubLessons($arTest['QUESTIONS_FROM_ID']); $WHERE = " (L.ID IN(" . $clauseAllChildsLessons . ") OR (L.ID = " . ($arTest['QUESTIONS_FROM_ID'] + 0) . ")) "; } elseif ($arTest["QUESTIONS_FROM"] == 'S') { $clauseAllChildsLessons = $arTest["QUESTIONS_FROM_ID"] + 0; $WHERE = " (L.ID IN(" . $clauseAllChildsLessons . ") OR (L.ID = " . ($arTest['QUESTIONS_FROM_ID'] + 0) . ")) "; } else { return false; } $strSql = "INSERT INTO b_learn_test_result (ATTEMPT_ID, QUESTION_ID) " . "SELECT " . $ATTEMPT_ID . " ,Q.ID " . "FROM b_learn_lesson L " . "INNER JOIN b_learn_question Q ON L.ID = Q.LESSON_ID " . "WHERE " . $WHERE . " AND Q.ACTIVE = 'Y' " . ($arTest["INCLUDE_SELF_TEST"] != "Y" ? "AND Q.SELF = 'N' " : "") . "ORDER BY " . ($arTest["RANDOM_QUESTIONS"] == "Y" ? CTest::GetRandFunction() : "Q.SORT ") . ($arTest["QUESTIONS_AMOUNT"] > 0 ? "LIMIT " . $arTest["QUESTIONS_AMOUNT"] : ""); //echo $strSql;exit; $q = $DB->Query($strSql, false, "File: " . __FILE__ . "<br>Line: " . __LINE__); if (!$q || intval($q->AffectedRowsCount()) <= 0) { $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_TEST_IS_EMPTY"), "ERROR_TEST_IS_EMPTY"); return false; } } elseif ($arTest["QUESTIONS_FROM"] == 'A') { $courseId = $arTest['COURSE_ID'] + 0; $courseLessonId = CCourse::CourseGetLinkedLesson($courseId); if ($courseLessonId === false) { $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_TEST_IS_EMPTY"), "ERROR_TEST_IS_EMPTY"); return false; } $clauseAllChildsLessons = CLearnHelper::SQLClauseForAllSubLessons($courseLessonId); $strSql = call_user_func($arCallbackSqlFormer, $ATTEMPT_ID, $arTest, $clauseAllChildsLessons, $courseLessonId); //echo $strSql; exit; $q = $DB->Query($strSql, false, "File: " . __FILE__ . "<br>Line: " . __LINE__); if (!$q || intval($q->AffectedRowsCount()) <= 0) { $APPLICATION->ThrowException(GetMessage("LEARNING_BAD_TEST_IS_EMPTY"), "ERROR_TEST_IS_EMPTY"); return false; } } else { return false; } $strSql = "UPDATE b_learn_attempt SET QUESTIONS = '" . CTestResult::GetCount($ATTEMPT_ID) . "' WHERE ID = " . $ATTEMPT_ID; $DB->Query($strSql, false, "File: " . __FILE__ . "<br>Line: " . __LINE__); return true; }
function __learning_admin_get_menu($THIS, $arPath = array(), $deep = 0, &$immediateChildsIds, $loadOnlySpecialEntities = false) { $immediateChildsIds = array(); // puts here ids of all immediate childs $deep = (int) $deep; // Index in path for current parentLessonId $indexInPath = $deep - 1; // Path doesn't include top root element ('all courses' or 'all unilessons') $arMenu = array(); //$urlPath = $oPath->ExportUrlencoded(); // current lesson id (not exists only for top root) if (isset($arPath[$deep])) { $currentLessonIdInPath = (int) $arPath[$deep]; } else { $currentLessonIdInPath = false; } // Path to current element $arCurrentDeepPath = array(); foreach ($arPath as $key => $value) { if ($key === $deep) { break; } $arCurrentDeepPath[] = $value; } if ($deep === 0) { // We are at the top level, so we must get list of all courses $CDBResult = CCourse::GetList(array('COURSE_SORT' => 'ASC')); } else { // If not parent with such indexInPath => we are deep too much. if (!isset($arPath[$indexInPath])) { return $arMenu; } // no items $parentLessonId = $arPath[$indexInPath]; $oCurrentDeepPath = new CLearnPath(); $oCurrentDeepPath->SetPathFromArray(array_merge($arCurrentDeepPath)); $urlPath = $oCurrentDeepPath->ExportUrlencoded(); $arMenu[] = array("text" => GetMessage("LEARNING_QUESTION"), "url" => "learn_question_admin.php?lang=" . LANG . '&PARENT_LESSON_ID=' . ($parentLessonId + 0) . '&LESSON_PATH=' . $urlPath . "&from=learn_menu", "icon" => "learning_icon_question", "more_url" => array("learn_question_admin.php?lang=" . LANG . '&PARENT_LESSON_ID=' . ($parentLessonId + 0) . '&LESSON_PATH=' . $urlPath . "&from=learn_menu", "learn_question_edit.php?lang=" . LANG . '&LESSON_PATH=' . $urlPath . "&from=learn_menu", "learn_question_admin.php?lang=" . LANG . '&PARENT_LESSON_ID=' . ($parentLessonId + 0) . '&LESSON_PATH=' . $urlPath, "learn_question_edit.php?lang=" . LANG . '&LESSON_PATH=' . $urlPath, "learn_question_admin.php?lang=" . LANG . '&LESSON_PATH=' . $urlPath), "title" => GetMessage("LEARNING_QUESTION_LIST")); $CDBResult = CLearnLesson::GetListOfImmediateChilds($parentLessonId, array('EDGE_SORT' => 'ASC')); // determine, is parent a course (only for courses in subroot level)? if ($deep === 1) { $immediateParentCourse = CLearnLesson::GetLinkedCourse($parentLessonId); if ($immediateParentCourse !== false) { // immediate parent is a course, so we must add entity 'Tests' $arMenu[] = array('text' => GetMessage('LEARNING_TESTS'), 'url' => 'learn_test_admin.php?lang=' . LANG . '&filter=Y&set_filter=Y' . '&COURSE_ID=' . ($immediateParentCourse + 0) . '&PARENT_LESSON_ID=' . ($parentLessonId + 0) . '&LESSON_PATH=' . $urlPath, 'icon' => 'learning_icon_tests', 'more_url' => array('learn_test_admin.php?lang=' . LANG . '&set_filter=Y' . '&COURSE_ID=' . ($immediateParentCourse + 0) . '&PARENT_LESSON_ID=' . ($parentLessonId + 0) . '&LESSON_PATH=' . $urlPath, 'learn_test_edit.php?lang=' . LANG . '&filter=Y&set_filter=Y' . '&COURSE_ID=' . ($immediateParentCourse + 0) . '&PARENT_LESSON_ID=' . ($parentLessonId + 0) . '&LESSON_PATH=' . $urlPath), 'title' => GetMessage('LEARNING_TESTS_LIST')); unset($urlPath); unset($oCurrentDeepPath); } } } if ($loadOnlySpecialEntities) { return $arMenu; } // When listing courses, limit it's count if ($deep === 0) { $items = 0; $learning_menu_max_courses = (int) COption::GetOptionString("learning", "menu_max_courses", "10"); } while ($arData = $CDBResult->GetNext()) { // When listing courses, limit it's count if ($deep === 0) { if ($items >= $learning_menu_max_courses) { // add element 'other courses' $arMenu[] = array('text' => GetMessage('LEARNING_MENU_COURSES_OTHER'), 'url' => 'learn_unilesson_admin.php?lang=' . LANG . '&PARENT_LESSON_ID=-1', 'title' => GetMessage('LEARNING_MENU_COURSES_ALT'), 'more_url' => array('learn_test_admin.php', 'learn_test_edit.php', 'learn_unilesson_admin.php', 'learn_unilesson_edit.php', 'learn_question_admin.php', 'learn_question_edit.php')); // stop adding courses to menu break; } $items++; } $arSubImmediateChildsIds = false; $arCurItemPath = $arCurrentDeepPath; $arCurItemPath[] = $arData['LESSON_ID'] + 0; // Remember all immediate childs $immediateChildsIds[] = $arData['LESSON_ID'] + 0; $oCurItemPath = new CLearnPath(); $oCurItemPath->SetPathFromArray($arCurItemPath); $urlCurItemPath = $oCurItemPath->ExportUrlencoded(); $arItem = array('text' => $arData['NAME'], 'url' => 'learn_unilesson_admin.php?lang=' . LANG . '&PARENT_LESSON_ID=' . ($arData['LESSON_ID'] + 0) . '&LESSON_PATH=' . $oCurItemPath->ExportUrlencoded(), 'title' => $arData['NAME'], 'items_id' => 'menu_learning_courses_new_' . implode('_', $arCurItemPath), "icon" => "learning_icon_courses", 'module_id' => 'learning', 'more_url' => array('learn_unilesson_admin.php?lang=' . LANG . '&set_filter=Y' . '&PARENT_LESSON_ID=' . ($arData['LESSON_ID'] + 0) . '&LESSON_PATH=' . $urlCurItemPath, 'learn_unilesson_admin.php?lang=' . LANG . '&PARENT_LESSON_ID=' . ($arData['LESSON_ID'] + 0) . '&LESSON_PATH=' . $urlCurItemPath, 'learn_unilesson_admin.php?lang=' . LANG . '&set_filter=Y' . '&LESSON_PATH=' . $urlCurItemPath, 'learn_question_admin.php?lang=' . LANG . '&filter=Y&set_filter=Y' . '&LESSON_PATH=' . $urlCurItemPath, 'learn_question_edit.php?lang=' . LANG . '&set_filter=Y' . '&LESSON_PATH=' . $urlCurItemPath, 'learn_unilesson_edit.php?lang=' . LANG . '&LESSON_ID=' . ($arData['LESSON_ID'] + 0) . '&LESSON_PATH=' . $urlCurItemPath, 'learn_unilesson_edit.php?lang=' . LANG . '&PARENT_LESSON_ID=' . ($arData['LESSON_ID'] + 0) . '&LESSON_PATH=' . $urlCurItemPath)); $arItem['items'] = array(); if ($deep === 0 && isset($arData['LINKED_LESSON_ID']) && $arData['LINKED_LESSON_ID'] > 0) { $arItem['page_icon'] = $arItem['icon'] = 'learning_icon_courses'; $arItem['dynamic'] = true; $loadOnlySpecialEntities = false; // Load child items only for lesson in current path if ($arData['LESSON_ID'] == $currentLessonIdInPath) { $arItem['items'] = __learning_admin_get_menu($THIS, $arPath, $deep + 1, $arSubImmediateChildsIds); } } else { $loadOnlySpecialEntities = false; $childsCnt = CLearnLesson::CountImmediateChilds($arData['LESSON_ID']); $questionsCnt = CLQuestion::GetCount(array('LESSON_ID' => (int) $arData['LESSON_ID'])); if ($childsCnt > 0) { $arItem['page_icon'] = $arItem['icon'] = 'learning_icon_chapters'; } else { $arItem['page_icon'] = $arItem['icon'] = 'learning_icon_lessons'; } $arItem['dynamic'] = true; // Load child items only for lesson in current path if ($arData['LESSON_ID'] == $currentLessonIdInPath) { $arItem['items'] = __learning_admin_get_menu($THIS, $arPath, $deep + 1, $arSubImmediateChildsIds); } } // now, adds items into more_url (it needs when edit form for childs opened) if (is_array($arSubImmediateChildsIds)) { $oSubItemPath = new CLearnPath(); foreach ($arSubImmediateChildsIds as $k => $v) { // determine path for every child $arSubItemPath = $arCurItemPath; $arSubItemPath[] = $v; // child id added to current path $oSubItemPath->SetPathFromArray($arSubItemPath); $arItem['more_url'][] = 'learn_unilesson_edit.php?lang=' . LANG . '&filter=Y&set_filter=Y' . '&LESSON_ID=' . ($v + 0) . '&LESSON_PATH=' . $oSubItemPath->ExportUrlencoded(); } unset($oSubItemPath); $arSubImmediateChildsIds = false; } $arMenu[] = $arItem; unset($oCurItemPath, $arCurItemPath, $urlCurItemPath, $arItem); } return $arMenu; }
ShowError(GetMessage("LEARNING_MODULE_NOT_FOUND")); return; } //Chapter $rsChapter = CChapter::GetList(array(), array("ID" => $arParams["CHAPTER_ID"], "COURSE_ID" => $arParams["COURSE_ID"], "ACTIVE" => "Y", "CHECK_PERMISSIONS" => $arParams["CHECK_PERMISSIONS"])); if (!($arChapter = $rsChapter->GetNext())) { $this->AbortResultCache(); ShowError(GetMessage("LEARNING_CHAPTER_DENIED")); return; } //Images $arChapter["PREVIEW_PICTURE_ARRAY"] = CFile::GetFileArray($arChapter["PREVIEW_PICTURE"]); $arChapter["DETAIL_PICTURE_ARRAY"] = CFile::GetFileArray($arChapter["DETAIL_PICTURE"]); $arResult = array("CHAPTER" => $arChapter, "CONTENTS" => array()); //Included chapters and lessons $rsContent = CCourse::GetCourseContent($arChapter["COURSE_ID"], array()); $foundChapter = false; while ($arContent = $rsContent->GetNext()) { if ($foundChapter) { if ($arContent["DEPTH_LEVEL"] <= $baseDepthLevel) { break; } $arContent["DEPTH_LEVEL"] -= $baseDepthLevel; if ($arContent["TYPE"] == "CH") { $arContent["URL"] = CComponentEngine::MakePathFromTemplate($arParams["CHAPTER_DETAIL_TEMPLATE"], array("CHAPTER_ID" => $arContent["ID"], "COURSE_ID" => $arChapter["COURSE_ID"])); } else { $arContent["URL"] = CComponentEngine::MakePathFromTemplate($arParams["LESSON_DETAIL_TEMPLATE"], array("LESSON_ID" => $arContent["ID"], "COURSE_ID" => $arChapter["COURSE_ID"])); } $arResult["CONTENTS"][] = $arContent; } if ($arContent["ID"] == $arChapter["ID"] && $arContent["TYPE"] == "CH") {
/** * This code writed not by me, but I rely on it in good state */ public static function FilterCreate($fname, $vals, $type, &$bFullJoin, $cOperationType = false, $bSkipEmpty = true) { global $DB; if (!is_array($vals)) { $vals = array($vals); } if (count($vals) < 1) { return ""; } if (is_bool($cOperationType)) { if ($cOperationType === true) { $cOperationType = "N"; } else { $cOperationType = "E"; } } if ($cOperationType == "G") { $strOperation = ">"; } elseif ($cOperationType == "GE") { $strOperation = ">="; } elseif ($cOperationType == "LE") { $strOperation = "<="; } elseif ($cOperationType == "L") { $strOperation = "<"; } else { $strOperation = "="; } $bFullJoin = false; $bWasLeftJoin = false; $res = array(); for ($i = 0; $i < count($vals); $i++) { $val = $vals[$i]; if (!$bSkipEmpty || strlen($val) > 0 || is_bool($val) && $val === false) { switch ($type) { case "string_equal": if (strlen($val) <= 0) { $res[] = ($cOperationType == "N" ? "NOT" : "") . "(" . $fname . " IS NULL OR " . $DB->Length($fname) . "<=0)"; } else { $res[] = "(" . ($cOperationType == "N" ? " " . $fname . " IS NULL OR NOT (" : "") . CCourse::_Upper($fname) . $strOperation . CCourse::_Upper("'" . $DB->ForSql($val) . "'") . ($cOperationType == "N" ? ")" : "") . ")"; } break; case "string": if ($cOperationType == "?") { if (strlen($val) > 0) { $res[] = GetFilterQuery($fname, $val, "Y", array(), "N"); } } elseif (strlen($val) <= 0) { $res[] = ($cOperationType == "N" ? "NOT" : "") . "(" . $fname . " IS NULL OR " . $DB->Length($fname) . "<=0)"; } else { if ($strOperation == "=") { $res[] = "(" . ($cOperationType == "N" ? " " . $fname . " IS NULL OR NOT (" : "") . (strtoupper($DB->type) == "ORACLE" ? CCourse::_Upper($fname) . " LIKE " . CCourse::_Upper("'" . $DB->ForSqlLike($val) . "'") . " ESCAPE '\\'" : $fname . " " . ($strOperation == "=" ? "LIKE" : $strOperation) . " '" . $DB->ForSqlLike($val) . "'") . ($cOperationType == "N" ? ")" : "") . ")"; } else { $res[] = "(" . ($cOperationType == "N" ? " " . $fname . " IS NULL OR NOT (" : "") . (strtoupper($DB->type) == "ORACLE" ? CCourse::_Upper($fname) . " " . $strOperation . " " . CCourse::_Upper("'" . $DB->ForSql($val) . "'") . " " : $fname . " " . $strOperation . " '" . $DB->ForSql($val) . "'") . ($cOperationType == "N" ? ")" : "") . ")"; } } break; case "date": if (strlen($val) <= 0) { $res[] = ($cOperationType == "N" ? "NOT" : "") . "(" . $fname . " IS NULL)"; } else { $res[] = "(" . ($cOperationType == "N" ? " " . $fname . " IS NULL OR NOT (" : "") . $fname . " " . $strOperation . " " . $DB->CharToDateFunction($DB->ForSql($val), "FULL") . ($cOperationType == "N" ? ")" : "") . ")"; } break; case "number": if (strlen($val) <= 0) { $res[] = ($cOperationType == "N" ? "NOT" : "") . "(" . $fname . " IS NULL)"; } else { $res[] = "(" . ($cOperationType == "N" ? " " . $fname . " IS NULL OR NOT (" : "") . $fname . " " . $strOperation . " '" . DoubleVal($val) . ($cOperationType == "N" ? "')" : "'") . ")"; } break; /* case "number_above": if(strlen($val)<=0) $res[] = ($cOperationType=="N"?"NOT":"")."(".$fname." IS NULL)"; else $res[] = ($cOperationType=="N"?" ".$fname." IS NULL OR NOT ":"")."(".$fname." ".$strOperation." '".$DB->ForSql($val)."')"; break; */ } // INNER JOIN in this case if (strlen($val) > 0 && $cOperationType != "N") { $bFullJoin = true; } else { $bWasLeftJoin = true; } } } $strResult = ""; for ($i = 0; $i < count($res); $i++) { if ($i > 0) { $strResult .= $cOperationType == "N" ? " AND " : " OR "; } $strResult .= $res[$i]; } if (count($res) > 1) { $strResult = "(" . $strResult . ")"; } if ($bFullJoin && $bWasLeftJoin && $cOperationType != "N") { $bFullJoin = false; } return $strResult; }
" size="47"></td> </tr> <tr> <td><?php echo GetMessage("LEARNING_ADMIN_COURSE_ID"); ?> :</td> <td> <select name="filter_course_id"> <option value=""><?php echo GetMessage("LEARNING_ALL"); ?> </option> <?php $l = CCourse::GetList(array(), array()); while ($l->ExtractFields("l_")) { ?> <option value="<?php echo $l_ID; ?> "<?php if ($filter_course_id == $l_ID) { echo " selected"; } ?> ><?php echo $l_NAME; ?> </option><?php }
protected function _MakeItems($TITLE, $TYPE, $RES_ID, $PARENT_ID) { global $APPLICATION; if ($PARENT_ID === 0) { $linkToParentLessonId = CCourse::CourseGetLinkedLesson($this->COURSE_ID); } else { $linkToParentLessonId = (int) $PARENT_ID; } $createUnilesson = false; if ($TYPE == "LES") { $arFields = array('NAME' => $TITLE); $createUnilesson = true; } elseif ($TYPE == "CHA") { $arFields = array('NAME' => $TITLE); $createUnilesson = true; } elseif ($TYPE == "QUE") { $arFields = array("NAME" => $TITLE, "LESSON_ID" => $linkToParentLessonId); $cl = new CLQuestion(); } elseif ($TYPE == "TES") { $arFields = array("NAME" => $TITLE, "COURSE_ID" => $this->COURSE_ID); $cl = new CTest(); } elseif ($TYPE === 'TMK') { $arFields = array(); $cl = new CLTestMark(); } else { return $PARENT_ID; } $r = new CDataXML(); if (!$r->Load($this->package_dir . "/" . strtolower($RES_ID) . ".xml")) { $r = false; } if ($r !== false) { if ($TYPE == "QUE") { if (($data = $r->SelectNodes("/questestinterop/item/presentation/")) && ($resp = $r->SelectNodes("/questestinterop/item/resprocessing/"))) { $arQ = array(); $arData = $data->__toArray(); $arResp = $resp->__toArray(); if (is_set($arData["#"]["material"][0]["#"], "mattext")) { $arQ["NAME"] = $arData["#"]["material"][0]["#"]["mattext"][0]["#"]; } if (is_set($arData["#"]["material"][0]["#"], "matimage")) { $imageDescription = ''; if (is_set($arData["#"]["material"][0]["#"], 'image_description')) { $imageDescription = $arData["#"]["material"][0]["#"]['image_description'][0]['#']; } $arQ["FILE_ID"] = array("MODULE_ID" => "learning", "name" => basename($arData["#"]["material"][0]["#"]["matimage"][0]["@"]["uri"]), "tmp_name" => $this->package_dir . "/" . $arData["#"]["material"][0]["#"]["matimage"][0]["@"]["uri"], "size" => @filesize($this->package_dir . "/" . $arData["#"]["material"][0]["#"]["matimage"][0]["@"]["uri"]), "type" => $arData["#"]["material"][0]["#"]["matimage"][0]["@"]["imagtype"], 'description' => $imageDescription); } if (is_set($arData["#"]["response_lid"][0]["@"], "rcardinality")) { switch ($arData["#"]["response_lid"][0]["@"]["rcardinality"]) { case "Multiple": $arQ["QUESTION_TYPE"] = 'M'; break; case "Text": $arQ["QUESTION_TYPE"] = 'T'; break; case "Sort": $arQ["QUESTION_TYPE"] = 'R'; break; default: $arQ["QUESTION_TYPE"] = 'S'; break; } } if (is_set($arResp["#"]["respcondition"][0]["#"], "setvar")) { $arQ["POINT"] = $arResp["#"]["respcondition"][0]["#"]["setvar"][0]['#']; } //Additional if ($bx = $r->SelectNodes("/questestinterop/item/bitrix/")) { $arQ = array_merge($arQ, $this->_MakeFields($bx->__toArray(), $TYPE)); unset($bx); } $arFields = array_merge($arFields, $arQ); $cl = new CLQuestion(); $ID = $cl->Add($arFields); if ($ID > 0) { $PARENT_ID = $ID; $arCorrect = array(); if (is_set($arResp["#"]["respcondition"][0]["#"], "conditionvar") && is_set($arResp["#"]["respcondition"][0]["#"]["conditionvar"][0]["#"], "varequal")) { foreach ($arResp["#"]["respcondition"][0]["#"]["conditionvar"][0]["#"]["varequal"] as $ar) { $arCorrect[] = $ar["#"]; } } if (is_set($arData["#"]["response_lid"][0]["#"], "render_choice") && is_set($arData["#"]["response_lid"][0]["#"]["render_choice"][0]["#"], "response_label")) { $i = 0; foreach ($arData["#"]["response_lid"][0]["#"]["render_choice"][0]["#"]["response_label"] as $ar) { $i += 10; $cl = new CLAnswer(); $arFields = array("QUESTION_ID" => $PARENT_ID, "SORT" => $i, "CORRECT" => in_array($ar["@"]["ident"], $arCorrect) ? "Y" : "N", "ANSWER" => $ar["#"]["material"][0]["#"]["mattext"][0]["#"]); $AswerID = $cl->Add($arFields); $res = $AswerID > 0; if (!$res) { if ($e = $APPLICATION->GetException()) { $this->arWarnings[$TYPE][] = array("TITLE" => $TITLE, "TEXT" => $e->GetString()); } } } } } else { if ($e = $APPLICATION->GetException()) { $this->arWarnings[$TYPE][] = array("TITLE" => $TITLE, "TEXT" => $e->GetString()); } } unset($cl); unset($data); unset($arQ); unset($resp); unset($arData); unset($arResp); return $PARENT_ID; } } else { if ($data = $r->SelectNodes("/content/")) { $ar = $data->__toArray(); $arFields = array_merge($arFields, $this->_MakeFields($ar, $TYPE)); if ($TYPE === 'TMK') { $arFields['TEST_ID'] = (int) $PARENT_ID; } if (is_set($arFields, "COMPLETED_SCORE") && intval($arFields["COMPLETED_SCORE"]) <= 0) { unset($arFields["COMPLETED_SCORE"]); } if (is_set($arFields, "PREVIOUS_TEST_ID") && intval($arFields["PREVIOUS_TEST_ID"]) <= 0 || !CTest::GetByID($arFields["PREVIOUS_TEST_ID"])->Fetch()) { unset($arFields["PREVIOUS_TEST_ID"], $arFields["PREVIOUS_TEST_SCORE"]); } } } } if ($createUnilesson === false) { $ID = $cl->Add($arFields); unset($cl); } else { $bProhibitPublish = false; // properties (in context of parent) by default $arProperties = array('SORT' => 500); // Lesson's sort order in context of parent if (isset($arFields['EDGE_SORT'])) { $arFields['SORT'] = (int) $arFields['EDGE_SORT']; unset($arFields['EDGE_SORT']); } if (isset($arFields['SORT'])) { $arProperties['SORT'] = (int) $arFields['SORT']; // Lessons doesn't have more SORT field unset($arFields['SORT']); } if (isset($arFields['META_PUBLISH_PROHIBITED'])) { if ($arFields['META_PUBLISH_PROHIBITED'] === 'Y') { $bProhibitPublish = true; } unset($arFields['META_PUBLISH_PROHIBITED']); } // unset fields, that are absent in unilesson $arUnilessonFields = $arFields; $arFieldsNames = array_keys($arUnilessonFields); foreach ($arFieldsNames as $fieldName) { if (!in_array(strtoupper($fieldName), $this->arLessonWritableFields)) { unset($arUnilessonFields[$fieldName]); } } $ID = CLearnLesson::Add($arUnilessonFields, false, $linkToParentLessonId, $arProperties); if ($bProhibitPublish && $ID > 0) { CLearnLesson::PublishProhibitionSetTo($ID, $linkToParentLessonId, $bProhibitPublish); } } if ($ID > 0) { return $ID; } else { if ($e = $APPLICATION->GetException()) { $this->arWarnings[$TYPE][] = array("TITLE" => $TITLE, "TEXT" => $e->GetString()); } } }
} } unset($course); } if ($COURSE_ID > 0) { $APPLICATION->SetTitle(str_replace("#ID#", $COURSE_ID, GetMessage("LEARNING_EDIT_TITLE2"))); } else { $APPLICATION->SetTitle(GetMessage("LEARNING_EDIT_TITLE1")); } //Defaults $str_ACTIVE = "Y"; $str_SORT = "500"; $str_DETAIL_TEXT_TYPE = $str_PREVIEW_TEXT_TYPE = "text"; $res = false; if ($COURSE_ID > 0) { $course = new CCourse(); $linkedLessonId = CCourse::CourseGetLinkedLesson($COURSE_ID); if ($oAccess->IsLessonAccessible($linkedLessonId, CLearnAccess::OP_LESSON_READ)) { $res = $course->GetByID($COURSE_ID); } else { $APPLICATION->SetTitle(GetMessage('LEARNING_ACCESS_D')); require $_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/main/include/prolog_admin_after.php"; $aContext = array(array("ICON" => "btn_list", "TEXT" => GetMessage("LEARNING_BACK_TO_ADMIN"), "LINK" => "learn_unilesson_admin.php?lang=" . LANG . '&PARENT_LESSON_ID=-1' . GetFilterParams("filter_"), "TITLE" => GetMessage("LEARNING_BACK_TO_ADMIN"))); $context = new CAdminContextMenu($aContext); $context->Show(); CAdminMessage::ShowMessage(GetMessage("LEARNING_BAD_COURSE")); require $_SERVER["DOCUMENT_ROOT"] . "/bitrix/modules/main/include/epilog_admin.php"; die; } } if ($res === false || !$res->ExtractFields("str_")) {
//Module if (!CModule::IncludeModule("learning")) { ShowError(GetMessage("LEARNING_MODULE_NOT_FOUND")); return; } //Params $arParams["TESTS_LIST_TEMPLATE"] = strlen($arParams["TESTS_LIST_TEMPLATE"]) > 0 ? htmlspecialcharsbx($arParams["TESTS_LIST_TEMPLATE"]) : "course/test_list.php?COURSE_ID=#COURSE_ID#"; $arParams["COURSE_DETAIL_TEMPLATE"] = strlen($arParams["COURSE_DETAIL_TEMPLATE"]) > 0 ? htmlspecialcharsbx($arParams["COURSE_DETAIL_TEMPLATE"]) : "course/index.php?COURSE_ID=#COURSE_ID#"; $arResult = array("COURSES" => array(), "CERTIFICATES" => array()); //Certificates $rsCertificate = CCertification::GetList(array("ID" => "DESC"), array("STUDENT_ID" => intval($USER->GetID()), "ACTIVE" => "Y")); while ($arCertificate = $rsCertificate->GetNext()) { $arResult["CERTIFICATES"][$arCertificate["COURSE_ID"]] = $arCertificate; } //Courses $rsCourse = CCourse::GetList(array("SORT" => "ASC"), array("ACTIVE" => "Y", "ACTIVE_DATE" => "Y", "SITE_ID" => LANG)); while ($arCourse = $rsCourse->GetNext()) { //Test list Url $arCourse["TESTS_LIST_URL"] = CComponentEngine::MakePathFromTemplate($arParams["TESTS_LIST_TEMPLATE"], array("COURSE_ID" => $arCourse["ID"])); //Course Url $arCourse["COURSE_DETAIL_URL"] = CComponentEngine::MakePathFromTemplate($arParams["COURSE_DETAIL_TEMPLATE"], array("COURSE_ID" => $arCourse["ID"])); $arCourse["COMPLETED"] = array_key_exists($arCourse["ID"], $arResult["CERTIFICATES"]); if (!$arCourse["COMPLETED"]) { $rsTest = CTest::GetList(array(), array("COURSE_ID" => $arCourse["ID"], "ACTIVE" => "Y", 'CHECK_PERMISSIONS' => 'N')); $rsTest->NavStart(1); $arCourse["NO_TESTS"] = !$rsTest->SelectedRowsCount(); } // Resolve links "?COURSE_ID={SELF}". Don't relay on it, this behaviour // can be changed in future without any notifications. if (isset($arCourse['DETAIL_TEXT'])) { $arCourse['DETAIL_TEXT'] = CLearnHelper::PatchLessonContentLinks($arCourse['DETAIL_TEXT'], $arCourse['ID']);
if (sourceList.options[i].index == sourceList.selectedIndex) needSelectedIndex = iSelectIndex; test.options.add(newElem); } } if (needSelectedIndex !== false) test.selectedIndex = needSelectedIndex; } </script> <select name="PREVIOUS_TEST_COURSE_ID" id="PREVIOUS_TEST_COURSE_ID" onchange="filterTests()"> <?php // was: $course = CCourse::GetList(array("SORT" => "ASC"), array("MIN_PERMISSION" => "W")); $course = CCourse::GetList(array("SORT" => "ASC"), array("ACCESS_OPERATIONS" => CLearnAccess::OP_LESSON_READ)); while ($course->ExtractFields("f_")) { ?> <option value="<?php echo $f_ID; ?> " <?php if (IntVal($f_ID) == $PREVIOUS_TEST_COURSE_ID || !isset($PREVIOUS_TEST_COURSE_ID) && IntVal($f_ID) == $COURSE_ID) { echo "selected"; } ?> ><?php echo $f_NAME; ?> </option><?php }
protected function _MakeItems($TITLE, $TYPE, $LAUNCH, $PARENT_ID) { global $APPLICATION; if ($PARENT_ID === 0) { $linkToParentLessonId = CCourse::CourseGetLinkedLesson($this->COURSE_ID); } else { $linkToParentLessonId = (int) $PARENT_ID; } if ($TYPE == "LES") { $arFields = array('NAME' => $TITLE, 'LAUNCH' => $LAUNCH, 'DETAIL_TEXT_TYPE' => "file"); } elseif ($TYPE == "CHA") { $arFields = array('NAME' => $TITLE); } else { return $PARENT_ID; } // properties (in context of parent) by default $arProperties = array('SORT' => 500); $ID = CLearnLesson::Add($arFields, false, $linkToParentLessonId, $arProperties); if ($ID > 0) { return $ID; } else { if ($e = $APPLICATION->GetException()) { $this->arWarnings[$TYPE][] = array("TITLE" => $TITLE, "TEXT" => $e->GetString()); } } }
public function SaveInlineEditedItems() { if (!$this->IsNeedSaveInlineEditedItems()) { return $this; } if (check_bitrix_sessid() !== true) { throw new CLearnRenderAdminUnilessonListException('', CLearnRenderAdminUnilessonListException::C_ACCESS_DENIED); } foreach ($_POST['FIELDS'] as $lessonId => $arFields) { $arEdgeProperties = array(); $wasError = false; try { // skip not changed items if (!$this->oList->IsUpdated($lessonId)) { continue; } // throws exception if access denied $this->EnsureLessonUpdateAccess($lessonId); $courseId = CLearnLesson::GetLinkedCourse($lessonId); // Depends on current list mode, we must update sort index // of element (only for course) or sort index of relation between // child and parent lessons. // So, we must rename SORT to COURSE_SORT or EDGE_SORT if (array_key_exists('SORT', $arFields)) { if ($this->IsListAnyCoursesMode() && $courseId !== false) { $arFields['COURSE_SORT'] = $arFields['SORT']; } elseif ($this->IsListChildLessonsMode()) { $arFields['EDGE_SORT'] = $arFields['SORT']; } else { throw new CLearnRenderAdminUnilessonListException('', CLearnRenderAdminUnilessonListException::C_LOGIC | CLearnRenderAdminUnilessonListException::C_ACTION_UPDATE_FAIL); } unset($arFields['SORT']); } if (isset($arFields['EDGE_SORT'])) { if (isset($_GET['PARENT_LESSON_ID'])) { $arEdgeProperties['SORT'] = $arFields['EDGE_SORT']; } unset($arFields['EDGE_SORT']); } // PUBLISH_PROHIBITED if (array_key_exists('PUBLISH_PROHIBITED', $arFields)) { // PUBLISH_PROHIBITED available in context of most parent course only if ($this->contextCourseLessonId !== false && in_array($arFields['PUBLISH_PROHIBITED'], array('N', 'Y'), true)) { $isProhibited = true; if ($arFields['PUBLISH_PROHIBITED'] === 'N') { $isProhibited = false; } CLearnLesson::PublishProhibitionSetTo($lessonId, $this->contextCourseLessonId, $isProhibited); } unset($arFields['PUBLISH_PROHIBITED']); } // Courses must be updated throws CCourse::Update(); if ($courseId === false) { CLearnLesson::Update($lessonId, $arFields); } else { $ob = new CCourse(); if (!$ob->Update($courseId, $arFields)) { throw new CLearnRenderAdminUnilessonListException('', CLearnRenderAdminUnilessonListException::C_ACTION_UPDATE_FAIL); } unset($ob); } if (isset($_GET['PARENT_LESSON_ID']) && count($arEdgeProperties) > 0) { CLearnLesson::RelationUpdate($_GET['PARENT_LESSON_ID'], $lessonId, $arEdgeProperties); } } catch (CLearnRenderAdminUnilessonListException $e) { $wasError = true; $errorText = $e->getMessage(); $errorCode = $e->getCode(); } catch (Exception $e) { $wasError = true; $errorText = $e->getMessage(); $errorCode = 0; // Because we checks below only CLearnRenderAdminUnilessonListException codes } if ($wasError) { if ($errorCode & CLearnRenderAdminUnilessonListException::C_ACCESS_DENIED) { // Access denied $errmsg = GetMessage('LEARNING_SAVE_ERROR') . ': ' . GetMessage('LEARNING_ACCESS_D'); if (strlen($errorText) > 0) { $errmsg .= ': ' . $errorText; } } else { // Some error occured during update operation $errmsg = GetMessage('LEARNING_SAVE_ERROR') . $lessonId; if (strlen($errorText) > 0) { $errmsg .= ' (' . $errorText . ')'; } } $this->oList->AddUpdateError($errmsg, $lessonId); } } return $this; }
$arParams["COURSE_DETAIL_TEMPLATE"] = isset($arParams["COURSE_DETAIL_TEMPLATE"]) ? htmlspecialcharsbx($arParams["COURSE_DETAIL_TEMPLATE"]) : "course/index.php?COURSE_ID=#COURSE_ID#"; $arParams["COURSES_PER_PAGE"] = intval($arParams["COURSES_PER_PAGE"]) > 0 ? intval($arParams["COURSES_PER_PAGE"]) : 20; //Set Title $arParams["SET_TITLE"] = $arParams["SET_TITLE"] == "N" ? "N" : "Y"; if ($arParams["SET_TITLE"] == "Y") { $APPLICATION->SetTitle(GetMessage("LEARNING_COURSE_LIST")); } //arResult $arResult = array("COURSES" => array(), "NAV_SRTING" => "", "NAV_RESULT" => null); $arNavParams = array(); $arNavParams = array(); if ((int) $arParams["COURSES_PER_PAGE"] > 0) { $arNavParams['nPageSize'] = (int) $arParams["COURSES_PER_PAGE"]; $arNavParams['bDescPageNumbering'] = false; } $res = CCourse::GetList(array($arParams["SORBY"] => $arParams["SORORDER"]), array("ACTIVE" => "Y", "ACTIVE_DATE" => "Y", "SITE_ID" => LANG, "CHECK_PERMISSIONS" => $arParams["CHECK_PERMISSIONS"]), $arNavParams); $arResult["NAV_STRING"] = $res->GetPageNavString(GetMessage("LEARNING_COURSES_NAV")); $arResult["NAV_RESULT"] = $res; while ($arCourse = $res->GetNext()) { $arCourse["COURSE_DETAIL_URL"] = CComponentEngine::MakePathFromTemplate($arParams["COURSE_DETAIL_TEMPLATE"], array("COURSE_ID" => $arCourse["ID"])); $arCourse["PREVIEW_PICTURE_ARRAY"] = CFile::GetFileArray($arCourse["PREVIEW_PICTURE"]); // Resolve links "?COURSE_ID={SELF}". Don't relay on it, this behaviour // can be changed in future without any notifications. if (isset($arCourse['DETAIL_TEXT'])) { $arCourse['DETAIL_TEXT'] = CLearnHelper::PatchLessonContentLinks($arCourse['DETAIL_TEXT'], $arCourse['ID']); } if (isset($arCourse['PREVIEW_TEXT'])) { $arCourse['PREVIEW_TEXT'] = CLearnHelper::PatchLessonContentLinks($arCourse['PREVIEW_TEXT'], $arCourse['ID']); } $arResult["COURSES"][] = $arCourse; }
// Resolve links "?COURSE_ID={SELF}". Don't relay on it, this behaviour // can be changed in future without any notifications. if (isset($arResult["QUESTION"]['DESCRIPTION'])) { $arResult["QUESTION"]['DESCRIPTION'] = CLearnHelper::PatchLessonContentLinks($arResult["QUESTION"]['DESCRIPTION'], $arParams['COURSE_ID']); } $arResult["QUESTION"]["FILE"] = CFile::GetFileArray($arResult["QUESTION"]["FILE_ID"]); //Answers $arResult["QUESTION"]["ANSWERS"] = array(); $arSort = $arTest["RANDOM_ANSWERS"] == "Y" || $arResult["QUESTION"]["QUESTION_TYPE"] == "R" ? array("RAND" => "RAND", "SORT" => "ASC") : array("SORT" => "ASC"); $rsAnswer = CLAnswer::GetList($arSort, array("QUESTION_ID" => $arResult["QUESTION"]["ID"])); while ($arAnswer = $rsAnswer->GetNext()) { $arResult["QUESTION"]["ANSWERS"][] = $arAnswer; } } } $arResult["SAFE_REDIRECT_PAGE"] = htmlspecialcharsbx($arResult["REDIRECT_PAGE"]); } $linkedLessonId = CCourse::CourseGetLinkedLesson($arResult['TEST']['COURSE_ID']); $bCanEdit = $linkedLessonId !== false && (CLearnAccessMacroses::CanUserEditLesson(array('lesson_id' => $linkedLessonId)) || $USER->IsAdmin()); if ($bCanEdit) { $deleteReturnUrl = ""; if ($parent = $this->GetParent()) { $deleteReturnUrl = CComponentEngine::MakePathFromTemplate($parent->arResult["URL_TEMPLATES"]["test.list"], array("COURSE_ID" => $arResult["TEST"]["COURSE_ID"])); } $arAreaButtons = array(array("TEXT" => GetMessage("LEARNING_COURSES_TEST_EDIT"), "TITLE" => GetMessage("LEARNING_COURSES_TEST_EDIT"), "URL" => 'javascript:' . $APPLICATION->GetPopupLink(array("URL" => "/bitrix/admin/learn_test_edit.php?lang=" . LANGUAGE_ID . "&ID=" . $arResult["TEST"]["ID"] . "&COURSE_ID=" . $arResult["TEST"]["COURSE_ID"] . "&bxpublic=Y&from_module=learning", "PARAMS" => array("width" => 700, 'height' => 500, 'resize' => false))), "ICON" => "bx-context-toolbar-edit-icon", "ID" => "bx-context-toolbar-edit-test"), array("TEXT" => GetMessage("LEARNING_COURSES_TEST_DELETE"), "TITLE" => GetMessage("LEARNING_COURSES_TEST_DELETE"), "URL" => "javascript:if(confirm('" . GetMessage("LEARNING_COURSES_TEST_DELETE_CONF") . "'))jsUtils.Redirect([], '" . CUtil::JSEscape("/bitrix/admin/learn_test_admin.php?ID=" . $arParams["TEST_ID"] . "&action=delete&lang=" . LANGUAGE_ID . "&" . bitrix_sessid_get() . "&COURSE_ID=" . $arParams["COURSE_ID"]) . (strlen($deleteReturnUrl) ? "&return_url=" . urlencode($deleteReturnUrl) : "") . "')", "ICON" => "bx-context-toolbar-delete-icon", "ID" => "bx-context-toolbar-delete-test"), array("SEPARATOR" => "Y")); if ($arResult["QUESTION"]["ID"]) { array_unshift($arAreaButtons, array("TEXT" => GetMessage("LEARNING_COURSES_QUESTION_EDIT"), "TITLE" => GetMessage("LEARNING_COURSES_QUESTION_EDIT"), "URL" => 'javascript:' . $APPLICATION->GetPopupLink(array("URL" => "/bitrix/admin/learn_question_edit.php?lang=" . LANGUAGE_ID . "&ID=" . $arResult["QUESTION"]["ID"] . "&COURSE_ID=" . $arResult["TEST"]["COURSE_ID"] . "&LESSON_ID=" . $arResult["QUESTION"]["LESSON_ID"] . "&bxpublic=Y&from_module=learning", "PARAMS" => array("width" => 700, 'height' => 500, 'resize' => false))), "ICON" => "bx-context-toolbar-edit-icon", "ID" => "bx-context-toolbar-edit-question")); } $this->AddIncludeAreaIcons($arAreaButtons); } $this->IncludeComponentTemplate();
ShowError(GetMessage("LEARNING_COURSE_DENIED")); return; } //Images $arCourse["PREVIEW_PICTURE_ARRAY"] = CFile::GetFileArray($arCourse["PREVIEW_PICTURE"]); // Resolve links "?COURSE_ID={SELF}". Don't relay on it, this behaviour // can be changed in future without any notifications. if (isset($arCourse['DETAIL_TEXT'])) { $arCourse['DETAIL_TEXT'] = CLearnHelper::PatchLessonContentLinks($arCourse['DETAIL_TEXT'], $arParams["COURSE_ID"]); } if (isset($arCourse['PREVIEW_TEXT'])) { $arCourse['PREVIEW_TEXT'] = CLearnHelper::PatchLessonContentLinks($arCourse['PREVIEW_TEXT'], $arParams["COURSE_ID"]); } //arResult $arResult = array("COURSE" => $arCourse, "CONTENTS" => array()); $rsContent = CCourse::GetCourseContent($arParams["COURSE_ID"], array("DETAIL_TEXT", "DETAIL_TEXT_TYPE", "DETAIL_PICTURE", "PREVIEW_PICTURE")); while ($arContent = $rsContent->GetNext()) { $arContent["DETAIL_PICTURE_ARRAY"] = CFile::GetFileArray($arContent["DETAIL_PICTURE"]); $arContent["PREVIEW_PICTURE_ARRAY"] = CFile::GetFileArray($arContent["PREVIEW_PICTURE"]); // Resolve links "?COURSE_ID={SELF}". Don't relay on it, this behaviour // can be changed in future without any nitifications. if (isset($arContent['DETAIL_TEXT'])) { $arContent['DETAIL_TEXT'] = CLearnHelper::PatchLessonContentLinks($arContent['DETAIL_TEXT'], $arParams["COURSE_ID"]); } if (isset($arContent['PREVIEW_TEXT'])) { $arContent['PREVIEW_TEXT'] = CLearnHelper::PatchLessonContentLinks($arContent['PREVIEW_TEXT'], $arParams["COURSE_ID"]); } $arResult["CONTENTS"][] = $arContent; } unset($rsContent); unset($arContent);
/** * WARNING: don't use this method, it's for internal use only * * Convert course to non-course lesson (course will be removed, * but lesson will stay exists) * * WARNING: this method terminates (by die()/exit()) current execution flow * when SQL server error occured. It's due to bug in CDatabase::Update() in main * module (version info: * define("SM_VERSION","11.0.12"); * define("SM_VERSION_DATE","2012-02-21 17:00:00"); // YYYY-MM-DD HH:MI:SS * ) * * @param int $courseId (returned by GetLinkedCourse($lessonId) ) * * @access private */ protected static function CourseBecomeLesson($courseId) { global $DB; self::_EnsureArgsStrictlyCastableToIntegers($courseId); $linkedLessonId = CCourse::CourseGetLinkedLesson($courseId); if ($linkedLessonId === false) { return false; } // Check certificates (if exists => forbid removing course) $certificate = CCertification::GetList(array(), array("COURSE_ID" => $courseId, 'CHECK_PERMISSIONS' => 'N')); if ($certificate === false || $certificate->GetNext()) { return false; } // Remove tests $tests = CTest::GetList(array(), array("COURSE_ID" => $courseId)); if ($tests === false) { return false; } while ($arTest = $tests->Fetch()) { if (!CTest::Delete($arTest["ID"])) { return false; } } // Remove all prohibitions for lessons in context of course to be removed // and remove prohibitions for course to be removed in context of all other courses self::PublishProhibitionPurge($linkedLessonId, self::PUBLISH_PROHIBITION_PURGE_ALL_LESSONS_IN_COURSE_CONTEXT | self::PUBLISH_PROHIBITION_PURGE_LESSON_IN_ALL_COURSE_CONTEXT); $rc = $DB->Query("DELETE FROM b_learn_course\n\t\t\tWHERE ID=" . (string) (int) $courseId, true); // reload cache of LINKED_LESSON_ID -> COURSE_ID self::GetCourseToLessonMap_ReloadCache(); CLearnCacheOfLessonTreeComponent::MarkAsDirty(); /** * This code will be useful after bug in CDatabase::Update() * and CDatabase::Insert() will be solved and $ignore_errors setted * to true in Insert()/Update() call above. */ if ($rc === false) { throw new LearnException('EA_SQLERROR', LearnException::EXC_ERR_ALL_GIVEUP); } // If data not updated if ($rc === 0) { throw new LearnException('EA_OTHER: data not updated', LearnException::EXC_ERR_ALL_GIVEUP); } }
function CheckFields(&$arFields, $ID = false) { global $DB; $arMsg = array(); if ((is_set($arFields, "NAME") || $ID === false) && strlen($arFields["NAME"]) <= 0) { $arMsg[] = array("id" => "NAME", "text" => GetMessage("LEARNING_BAD_NAME")); } if ($ID === false && !is_set($arFields, "COURSE_ID")) { $arMsg[] = array("id" => "COURSE_ID", "text" => GetMessage("LEARNING_BAD_COURSE_ID")); } if (is_set($arFields, "COURSE_ID")) { $r = CCourse::GetByID($arFields["COURSE_ID"]); if (!$r->Fetch()) { $arMsg[] = array("id" => "COURSE_ID", "text" => GetMessage("LEARNING_BAD_COURSE_ID_EX")); } } if ($arFields["APPROVED"] == "Y" && is_set($arFields, "COMPLETED_SCORE") && (intval($arFields["COMPLETED_SCORE"]) <= 0 || intval($arFields["COMPLETED_SCORE"]) > 100)) { $arMsg[] = array("id" => "COMPLETED_SCORE", "text" => GetMessage("LEARNING_BAD_COMPLETED_SCORE")); } if (is_set($arFields, "PREVIOUS_TEST_ID") && intval($arFields["PREVIOUS_TEST_ID"]) != 0) { $r = CTest::GetByID($arFields["PREVIOUS_TEST_ID"]); if (!$r->Fetch()) { $arMsg[] = array("id" => "PREVIOUS_TEST_ID", "text" => GetMessage("LEARNING_BAD_PREVIOUS_TEST")); } } if (is_set($arFields, "PREVIOUS_TEST_SCORE") && (intval($arFields["PREVIOUS_TEST_SCORE"]) <= 0 || intval($arFields["PREVIOUS_TEST_SCORE"]) > 100) && intval($arFields["PREVIOUS_TEST_ID"]) != 0) { $arMsg[] = array("id" => "PREVIOUS_TEST_SCORE", "text" => GetMessage("LEARNING_BAD_COMPLETED_SCORE")); } if (!empty($arMsg)) { $e = new CAdminException($arMsg); $GLOBALS["APPLICATION"]->ThrowException($e); return false; } //Defaults if (is_set($arFields, "QUESTIONS_FROM") && !in_array($arFields["QUESTIONS_FROM"], array("A", "C", "L", "H", "S", 'R'))) { $arFields["QUESTIONS_FROM"] = "A"; } if (is_set($arFields, "QUESTIONS_AMOUNT") && intval($arFields["QUESTIONS_AMOUNT"]) <= 0) { $arFields["QUESTIONS_AMOUNT"] = "0"; } if (is_set($arFields, "QUESTIONS_FROM_ID") && intval($arFields["QUESTIONS_FROM_ID"]) <= 0) { $arFields["QUESTIONS_FROM_ID"] = "0"; } if (is_set($arFields, "ACTIVE") && $arFields["ACTIVE"] != "Y") { $arFields["ACTIVE"] = "N"; } if (is_set($arFields, "APPROVED") && $arFields["APPROVED"] != "Y") { $arFields["APPROVED"] = "N"; } if ($arFields["APPROVED"] == "N") { $arFields["COMPLETED_SCORE"] = ""; } if (is_set($arFields, "INCLUDE_SELF_TEST") && $arFields["INCLUDE_SELF_TEST"] != "Y") { $arFields["INCLUDE_SELF_TEST"] = "N"; } if (is_set($arFields, "RANDOM_QUESTIONS") && $arFields["RANDOM_QUESTIONS"] != "Y") { $arFields["RANDOM_QUESTIONS"] = "N"; } if (is_set($arFields, "RANDOM_ANSWERS") && $arFields["RANDOM_ANSWERS"] != "Y") { $arFields["RANDOM_ANSWERS"] = "N"; } if (is_set($arFields, "DESCRIPTION_TYPE") && $arFields["DESCRIPTION_TYPE"] != "html") { $arFields["DESCRIPTION_TYPE"] = "text"; } if (is_set($arFields, "PASSAGE_TYPE") && !in_array($arFields["PASSAGE_TYPE"], array("0", "1", "2"))) { $arFields["PASSAGE_TYPE"] = "0"; } if (is_set($arFields, "INCORRECT_CONTROL") && $arFields["INCORRECT_CONTROL"] != "Y") { $arFields["INCORRECT_CONTROL"] = "N"; } if (is_set($arFields, "SHOW_ERRORS") && $arFields["SHOW_ERRORS"] != "Y") { $arFields["SHOW_ERRORS"] = "N"; $arFields["NEXT_QUESTION_ON_ERROR"] = "Y"; } if (is_set($arFields, "NEXT_QUESTION_ON_ERROR") && $arFields["NEXT_QUESTION_ON_ERROR"] != "Y") { $arFields["NEXT_QUESTION_ON_ERROR"] = "N"; } return true; }
$dbResult = CCourse::GetList(array(), array("CODE" => "BX-ADM001")); $pathToService = str_replace("\\", "/", dirname(__FILE__)); if (!($arCourse = $dbResult->Fetch())) { $pathToCourse = $serviceRelativePath . "/" . LANGUAGE_ID . "/course/"; $package = new CCourseImport($pathToCourse, array("s1")); if (strlen($package->LAST_ERROR) > 0) { return; } $success = $package->ImportPackage(); if ($success) { $dbResult = CCourse::GetList(array(), array("CODE" => "BX-ADM001")); $arCourse = $dbResult->Fetch(); } } if (isset($arCourse["ID"])) { CCourse::SetPermission($arCourse["ID"], array("2" => "R")); } //Public files CopyDirFiles($pathToService . "/" . LANGUAGE_ID . "/public", $_SERVER["DOCUMENT_ROOT"] . "/communication/learning", $rewrite = false, $recursive = true); //Left menu DemoSiteUtil::AddMenuItem("/communication/.left.menu.php", array(GetMessage("SERVICE_LEARNING"), "/communication/learning/", array(), array(), "")); //Template CopyDirFiles($pathToService . "/" . LANGUAGE_ID . "/template", $_SERVER["DOCUMENT_ROOT"] . BX_PERSONAL_ROOT . "/templates/learning", $rewrite = true, $recursive = true); $obSite = CSite::GetByID("s1"); if (!($arSite = $obSite->Fetch())) { return; } $arTemplates = array(); $obTemplate = CSite::GetTemplateList("s1"); while ($arTemplate = $obTemplate->Fetch()) { $arTemplates[] = $arTemplate;
if ($arParams['CHECK_PERMISSIONS'] !== 'N') { $linkedLessonId = CCourse::CourseGetLinkedLesson($arParams["COURSE_ID"]); try { $arPermissionsParams = array('lesson_id' => $linkedLessonId); $isAccessible = CLearnAccessMacroses::CanUserViewLessonContent($arPermissionsParams); } catch (Exception $e) { $isAccessible = false; // access denied } if (!$isAccessible) { ShowError(GetMessage('LEARNING_COURSE_DENIED')); return; exit; } } $rsCourse = CCourse::GetList(array(), array("ID" => $arParams["COURSE_ID"], "ACTIVE" => "Y", "ACTIVE_DATE" => "Y", "SITE_ID" => LANG, "CHECK_PERMISSIONS" => 'N')); if (!($arCourse = $rsCourse->GetNext())) { ShowError(GetMessage("LEARNING_COURSE_DENIED")); return; } // Resolve links "?COURSE_ID={SELF}". Don't relay on it, this behaviour // can be changed in future without any nitifications. if (isset($arCourse['DETAIL_TEXT'])) { $arCourse['DETAIL_TEXT'] = CLearnHelper::PatchLessonContentLinks($arCourse['DETAIL_TEXT'], $arParams["COURSE_ID"]); } if (isset($arCourse['PREVIEW_TEXT'])) { $arCourse['PREVIEW_TEXT'] = CLearnHelper::PatchLessonContentLinks($arCourse['PREVIEW_TEXT'], $arParams["COURSE_ID"]); } //arResult $arResult = array("ITEMS" => array(), "COURSE" => $arCourse); //Set Title
?> </tr> <?php foreach ($arResult["ATTEMPTS"] as $arAttempt) { ?> <tr> <?php if (strlen($arAttempt["DATE_END"]) > 0) { ?> <td><?php echo $arAttempt["DATE_END"]; ?> </td> <td><?php echo CCourse::TimeToStr(MakeTimeStamp($arAttempt["DATE_END"]) - MakeTimeStamp($arAttempt["DATE_START"])); ?> </td> <?php } else { ?> <td><?php echo $arAttempt["DATE_START"]; ?> </td> <td><?php echo GetMessage("LEARNING_ATTEMPT_NOT_FINISHED"); ?> </td> <?php }
<?php if (!defined("B_PROLOG_INCLUDED") || B_PROLOG_INCLUDED !== true) { die; } if (!CModule::IncludeModule("learning")) { return; } $arCourses = array(); $courses = CCourse::GetList(array("SORT" => "ASC")); while ($arRes = $courses->Fetch()) { $arCourses[$arRes["ID"]] = $arRes["NAME"]; } $arYesNo = array("Y" => GetMessage("LEARNING_DESC_YES"), "N" => GetMessage("LEARNING_DESC_NO")); $arComponentParameters = array("PARAMETERS" => array("COURSE_ID" => array("NAME" => GetMessage("LEARNING_COURSE_ID"), "TYPE" => "LIST", "VALUES" => $arCourses, "PARENT" => "BASE", "ADDITIONAL_VALUES" => "Y", "DEFAULT" => '={$_REQUEST["COURSE_ID"]}'), "CHECK_PERMISSIONS" => array("NAME" => GetMessage("LEARNING_CHECK_PERMISSIONS"), "TYPE" => "LIST", "MULTIPLE" => "N", "DEFAULT" => "Y", "PARENT" => "ADDITIONAL_SETTINGS", "VALUES" => $arYesNo, "ADDITIONAL_VALUES" => "N"), "SET_TITLE" => array(), "CACHE_TIME" => array("DEFAULT" => "3600")));
public static function CanViewAdminMenu() { global $USER; if ($USER->IsAdmin()) { return true; } $oAccess = CLearnAccess::GetInstance($USER->GetID()); if ($oAccess->IsBaseAccess(CLearnAccess::OP_LESSON_READ) && ($oAccess->IsBaseAccess(CLearnAccess::OP_LESSON_CREATE) || $oAccess->IsBaseAccess(CLearnAccess::OP_LESSON_WRITE) || $oAccess->IsBaseAccess(CLearnAccess::OP_LESSON_REMOVE) || $oAccess->IsBaseAccess(CLearnAccess::OP_LESSON_CREATE) || $oAccess->IsBaseAccess(CLearnAccess::OP_LESSON_LINK_TO_PARENTS) || $oAccess->IsBaseAccess(CLearnAccess::OP_LESSON_UNLINK_FROM_PARENTS) || $oAccess->IsBaseAccess(CLearnAccess::OP_LESSON_LINK_DESCENDANTS) || $oAccess->IsBaseAccess(CLearnAccess::OP_LESSON_UNLINK_DESCENDANTS) || $oAccess->IsBaseAccess(CLearnAccess::OP_LESSON_MANAGE_RIGHTS))) { return true; } if ($oAccess->IsBaseAccess(CLearnAccess::OP_LESSON_CREATE)) { return true; } $db = CCourse::GetList(array(), array("CHECK_PERMISSIONS" => "Y", "ACCESS_OPERATIONS" => CLearnAccess::OP_LESSON_CREATE | CLearnAccess::OP_LESSON_WRITE | CLearnAccess::OP_LESSON_REMOVE | CLearnAccess::OP_LESSON_LINK_TO_PARENTS | CLearnAccess::OP_LESSON_UNLINK_FROM_PARENTS | CLearnAccess::OP_LESSON_LINK_DESCENDANTS | CLearnAccess::OP_LESSON_UNLINK_DESCENDANTS | CLearnAccess::OP_LESSON_MANAGE_RIGHTS), array("nTopCount" => 1)); return $db->Fetch() !== false; }
// Lesson is not given, so try get chapter_id if (isset($_REQUEST['CHAPTER_ID'])) { if (CLearnPath::IsUrlencodedPath($_REQUEST['CHAPTER_ID'])) { $LESSON_PATH = new CLearnPath(); $LESSON_PATH->ImportUrlencoded($_REQUEST['CHAPTER_ID']); $lessonID = (int) $LESSON_PATH->GetBottom(); } elseif (substr($_REQUEST['CHAPTER_ID'], 0, 1) === '0') { $lessonID = (int) substr($_REQUEST['CHAPTER_ID'], 1); } else { $lessonID = (int) CLearnLesson::LessonIdByChapterId($_REQUEST['CHAPTER_ID']); } } } $linkedLessonId = false; if ($arParams["COURSE_ID"] > 0) { $linkedLessonId = CCourse::CourseGetLinkedLesson($arParams["COURSE_ID"]); } if ($arParams["CHECK_PERMISSIONS"] !== 'N') { $isAccessible = false; try { if ($lessonID > 0) { $arPermissionsParams = array('COURSE_ID' => $arParams['COURSE_ID'], 'LESSON_ID' => $lessonID); $isAccessible = CLearnAccessMacroses::CanUserViewLessonAsPublic($arPermissionsParams, $allowAccessViaLearningGroups = false); } elseif ($linkedLessonId !== false) { $arPermissionsParams = array('lesson_id' => $linkedLessonId); $isAccessible = CLearnAccessMacroses::CanUserViewLessonContent($arPermissionsParams, $allowAccessViaLearningGroups = false); } } catch (Exception $e) { $isAccessible = false; // access denied }
CAdminMessage::ShowMessage(GetMessage('LEARNING_MODULE_NOT_FOUND')); } require $_SERVER['DOCUMENT_ROOT'] . '/bitrix/modules/main/include/epilog_admin.php'; // system's epilog exit; } require_once $_SERVER["DOCUMENT_ROOT"] . BX_ROOT . "/modules/learning/prolog.php"; IncludeModuleLangFile(__FILE__); $aContext = array(); $oAccess = CLearnAccess::GetInstance($USER->GetID()); $COURSE_ID = intval($COURSE_ID); $course = CCourse::GetByID($COURSE_ID); $bBadCourse = true; try { if ($arCourse = $course->Fetch()) { $linkedLessonId = CCourse::CourseGetLinkedLesson($COURSE_ID); if ($linkedLessonId !== false && $oAccess->IsLessonAccessible($linkedLessonId, CLearnAccess::OP_LESSON_READ)) { $bBadCourse = false; } else { $bBadCourse = true; } } else { $bBadCourse = true; } } catch (Exception $e) { $bBadCourse = true; } $isReadOnly = true; try { if ($oAccess->IsLessonAccessible($linkedLessonId, CLearnAccess::OP_LESSON_WRITE)) { $isReadOnly = false;
// Resolve links "?COURSE_ID={SELF}". Don't relay on it, this behaviour // can be changed in future without any notifications. if (isset($arChapter['DETAIL_TEXT'])) { $arChapter['DETAIL_TEXT'] = CLearnHelper::PatchLessonContentLinks($arChapter['DETAIL_TEXT'], $arParams['COURSE_ID']); } if (isset($arChapter['PREVIEW_TEXT'])) { $arChapter['PREVIEW_TEXT'] = CLearnHelper::PatchLessonContentLinks($arChapter['PREVIEW_TEXT'], $arParams['COURSE_ID']); } // Self test page URL $arChapter["SELF_TEST_URL"] = CComponentEngine::MakePathFromTemplate($arParams["SELF_TEST_TEMPLATE"], array("LESSON_ID" => $arParams["CHAPTER_ID"], "SELF_TEST_ID" => $arParams["CHAPTER_ID"], "COURSE_ID" => $arParams["COURSE_ID"])); //Self test exists? $rsQuestion = CLQuestion::GetList(array(), array("LESSON_ID" => $arParams["CHAPTER_ID"], "ACTIVE" => "Y", "SELF" => "Y")); $arChapter["SELF_TEST_EXISTS"] = (bool) $rsQuestion->Fetch(); $arResult = array("COURSE" => $arCourse, "CHAPTER" => $arChapter, "CONTENTS" => array()); //Included chapters and lessons $rsContent = CCourse::GetCourseContent($arParams["COURSE_ID"], array()); $foundChapter = false; while ($arContent = $rsContent->GetNext()) { if ($foundChapter) { if ($arContent["DEPTH_LEVEL"] <= $baseDepthLevel) { break; } $arContent["DEPTH_LEVEL"] -= $baseDepthLevel; if ($arContent["TYPE"] == "CH") { $arContent["URL"] = CComponentEngine::MakePathFromTemplate($arParams["CHAPTER_DETAIL_TEMPLATE"], array("CHAPTER_ID" => '0' . $arContent["ID"], "COURSE_ID" => $arParams["COURSE_ID"])); } else { $arContent["URL"] = CComponentEngine::MakePathFromTemplate($arParams["LESSON_DETAIL_TEMPLATE"], array("LESSON_ID" => $arContent["ID"], "COURSE_ID" => $arParams["COURSE_ID"])); } $arResult["CONTENTS"][] = $arContent; } if ($arContent["ID"] == $arParams["CHAPTER_ID"] && $arContent["TYPE"] == "CH") {
/** * <p>Возвращает право доступа к учебному курсу с идентификатором <i>courseId</i> для текущего пользователя.</p> * * * * * @param int $courseId Идентификатор курса. <br><br> До версии 12.0.0 параметр назывался COURSE_ID. * * * * @return string <p>Символ права доступа: "D" - запрещён, "R" - чтение, "W" - изменение, "X" - * полный доступ (изменение + право изменять права доступа). </p> * * * <h4>Example</h4> * <pre> * <? * $permission = CCourse::GetPermission($id); * if ($permission<"X") * return false; * ?> * </pre> * * * * <h4>See Also</h4> * <ul> <li> <a href="http://dev.1c-bitrix.ru/api_help/learning/classes/ccourse/index.php">CCourse</a>::<a * href="http://dev.1c-bitrix.ru/api_help/learning/classes/ccourse/setpermission.php">SetPermission</a> </li> <li> <a * href="http://dev.1c-bitrix.ru/api_help/learning/classes/ccourse/index.php">CCourse</a>::<a * href="http://dev.1c-bitrix.ru/api_help/learning/classes/ccourse/getgrouppermissions.php">GetGroupPermissions</a> </li> * </ul><a name="examples"></a> * * * @static * @link http://dev.1c-bitrix.ru/api_help/learning/classes/ccourse/getpermission.php * @author Bitrix */ public static function GetPermission($courseId) { global $USER; static $accessMatrix = false; $courseId = (int) $courseId; if (!($courseId > 0)) { return 'D'; } // access denied $linkedLessonId = CCourse::CourseGetLinkedLesson($courseId); if (!($linkedLessonId > 0)) { return 'D'; } // some troubles, access denied $oAccess = CLearnAccess::GetInstance($USER->GetID()); if ($accessMatrix === false) { $accessMatrix = array('X' => CLearnAccess::OP_LESSON_READ | CLearnAccess::OP_LESSON_CREATE | CLearnAccess::OP_LESSON_WRITE | CLearnAccess::OP_LESSON_REMOVE | CLearnAccess::OP_LESSON_LINK_TO_PARENTS | CLearnAccess::OP_LESSON_UNLINK_FROM_PARENTS | CLearnAccess::OP_LESSON_LINK_DESCENDANTS | CLearnAccess::OP_LESSON_UNLINK_DESCENDANTS | CLearnAccess::OP_LESSON_MANAGE_RIGHTS, 'W' => CLearnAccess::OP_LESSON_READ | CLearnAccess::OP_LESSON_CREATE | CLearnAccess::OP_LESSON_WRITE | CLearnAccess::OP_LESSON_REMOVE, 'R' => CLearnAccess::OP_LESSON_READ); } foreach ($accessMatrix as $oldAccessSymbol => $operations) { if ($oAccess->IsBaseAccess($operations) || $oAccess->IsLessonAccessible($linkedLessonId, $operations)) { return $oldAccessSymbol; } } // by default, access denied return 'D'; }