Exemple #1
0
        /* Instructor can view student if he is a course admin or if student is member of one of accessible for instructor group */
        public async Task <bool> CanInstructorViewStudentAsync(string instructorId, string studentId)
        {
            if (await courseRolesRepo.HasUserAccessTo_Any_Course(instructorId, CourseRoleType.CourseAdmin).ConfigureAwait(false))
            {
                return(true);
            }

            var coursesIds = (await courseManager.GetCoursesAsync()).Select(c => c.Id).ToList();
            var groups     = await GetAvailableForUserGroupsAsync(coursesIds, instructorId, false, actual : true, archived : false).ConfigureAwait(false);

            var members = await groupMembersRepo.GetGroupsMembersAsync(groups.Select(g => g.Id).ToList()).ConfigureAwait(false);

            return(members.Select(m => m.UserId).Contains(studentId));
        }
Exemple #2
0
        private async Task <GroupsListResponse> GetGroupsListResponseAsync(GroupsListParameters parameters)
        {
            var groups = await groupAccessesRepo.GetAvailableForUserGroupsAsync(parameters.CourseId, UserId, false, !parameters.Archived, parameters.Archived).ConfigureAwait(false);

            /* Order groups by (name, createTime) and get one page of data (offset...offset+count) */
            var groupIds = groups.OrderBy(g => g.Name, StringComparer.InvariantCultureIgnoreCase).ThenBy(g => g.Id)
                           .Skip(parameters.Offset)
                           .Take(parameters.Count)
                           .Select(g => g.Id)
                           .ToImmutableHashSet();
            var filteredGroups = groups.Where(g => groupIds.Contains(g.Id)).ToList();

            var groupMembers = await groupMembersRepo.GetGroupsMembersAsync(groupIds).ConfigureAwait(false);

            var membersCountByGroup = groupMembers.GroupBy(m => m.GroupId).ToDictionary(g => g.Key, g => g.Count()).ToDefaultDictionary();

            var groupAccessesByGroup = await groupAccessesRepo.GetGroupAccessesAsync(groupIds).ConfigureAwait(false);

            var groupInfos = filteredGroups.Select(g => BuildGroupInfo(
                                                       g,
                                                       membersCountByGroup[g.Id],
                                                       groupAccessesByGroup[g.Id],
                                                       addGroupApiUrl: true
                                                       )).ToList();

            return(new GroupsListResponse
            {
                Groups = groupInfos,
                Pagination = new PaginationResponse
                {
                    Offset = parameters.Offset,
                    Count = filteredGroups.Count,
                    TotalCount = groups.Count,
                }
            });
        }
Exemple #3
0
        public async Task <ActionResult <CodeReviewInstructorsStatisticsResponse> > InstructorsStatistics([FromQuery(Name = "course_id")][BindRequired]
                                                                                                          string courseId, int count = 10000, DateTime?from = null, DateTime?to = null)
        {
            var course = await courseManager.FindCourseAsync(courseId);

            if (course == null)
            {
                return(NotFound());
            }

            if (!from.HasValue)
            {
                from = DateTime.MinValue;
            }
            if (!to.HasValue)
            {
                to = DateTime.MaxValue;
            }

            count = Math.Min(count, 10000);

            var instructorIds = await courseRolesRepo.GetListOfUsersWithCourseRole(CourseRoleType.Instructor, course.Id, false).ConfigureAwait(false);

            var instructors = await usersRepo.GetUsersByIds(instructorIds).ConfigureAwait(false);

            var exerciseSlides = course.GetSlides(true).OfType <ExerciseSlide>().ToList();

            var allSlideCheckings = (await slideCheckingsRepo.GetManualCheckingQueue <ManualExerciseChecking>(new ManualCheckingQueueFilterOptions
            {
                CourseId = course.Id,
                Count = count,
                OnlyChecked = null,
                From = @from.Value,
                To = to.Value,
            }).ConfigureAwait(false)).ToList();

            var result = new CodeReviewInstructorsStatisticsResponse
            {
                AnalyzedCodeReviewsCount = allSlideCheckings.Count,
                Instructors = new List <CodeReviewInstructorStatistics>()
            };

            foreach (var instructor in instructors)
            {
                var checkingsCheckedByInstructor = allSlideCheckings.Where(c => c.IsChecked && (c.LockedById == instructor.Id || c.Reviews.Any(r => r.AuthorId == instructor.Id))).ToList();
                var instructorGroups             = await groupsRepo.GetMyGroupsFilterAccessibleToUserAsync(course.Id, instructor.Id).ConfigureAwait(false);

                var instructorGroupMemberIds = (await groupMembersRepo.GetGroupsMembersAsync(instructorGroups.Select(g => g.Id).ToList()).ConfigureAwait(false)).Select(m => m.UserId);
                var checkingQueue            = allSlideCheckings.Where(c => !c.IsChecked && instructorGroupMemberIds.Contains(c.UserId)).ToList();
                var comments             = checkingsCheckedByInstructor.SelectMany(c => c.NotDeletedReviews).ToList();
                var instructorStatistics = new CodeReviewInstructorStatistics
                {
                    Instructor = BuildShortUserInfo(instructor, discloseLogin: true),
                    Exercises  = exerciseSlides.Select(
                        slide => new CodeReviewExerciseStatistics
                    {
                        SlideId = slide.Id,
                        ReviewedSubmissionsCount = checkingsCheckedByInstructor.Where(c => c.SlideId == slide.Id).DistinctBy(c => c.SubmissionId).Count(),
                        QueueSize     = checkingQueue.Count(c => c.SlideId == slide.Id),
                        CommentsCount = comments.Count(c => c.ExerciseChecking.SlideId == slide.Id),
                    }
                        )
                                 .Where(s => s.ReviewedSubmissionsCount + s.QueueSize + s.CommentsCount > 0)                // Ignore empty (zeros) records
                                 .ToList()
                };
                result.Instructors.Add(instructorStatistics);
            }

            return(result);
        }