Exemple #1
0
    def test_get_masquerade_group(self):
        """
        Tests that a staff member can masquerade as being in a group in a user partition
        """
        # Verify there is no masquerading group initially
        group = get_masquerading_user_group(self.course.id, self.test_user, self.user_partition)
        assert group is None

        # Install a masquerading group
        self.ensure_masquerade_as_group_member(0, 1)

        # Verify that the masquerading group is returned
        group = get_masquerading_user_group(self.course.id, self.test_user, self.user_partition)
        assert group.id == 1
Exemple #2
0
 def has_full_access_role_in_masquerade(cls, user, course_key, course_masquerade, student_masquerade,
                                        user_partition):
     """
     The roles of the masquerade user are used to determine whether the content gate displays.
     The gate will not appear if the masquerade user has any of the following roles:
     Staff, Instructor, Beta Tester, Forum Community TA, Forum Group Moderator, Forum Moderator, Forum Administrator
     """
     if student_masquerade:
         # If a request is masquerading as a specific user, the user variable will represent the correct user.
         if user and user.id and has_staff_roles(user, course_key):
             return True
     elif user_partition:
         # If the current user is masquerading as a generic student in a specific group,
         # then return the value based on that group.
         masquerade_group = get_masquerading_user_group(course_key, user, user_partition)
         if masquerade_group is None:
             audit_mode_id = settings.COURSE_ENROLLMENT_MODES.get(CourseMode.AUDIT, {}).get('id')
             # We are checking the user partition id here because currently content
             # cannot have both the enrollment track partition and content gating partition
             # configured simultaneously. We may change this in the future and allow
             # configuring both partitions on content and selecting both partitions in masquerade.
             if course_masquerade.user_partition_id == ENROLLMENT_TRACK_PARTITION_ID:
                 return course_masquerade.group_id != audit_mode_id
         elif masquerade_group is FULL_ACCESS:
             return True
         elif masquerade_group is LIMITED_ACCESS:
             return False
Exemple #3
0
    def get_group_for_user(cls, course_key, user, user_partition, **kwargs):  # pylint: disable=unused-argument
        """
        Returns the Group for the specified user.
        """

        # First, check if we have to deal with masquerading.
        # If the current user is masquerading as a specific student, use the
        # same logic as normal to return that student's group. If the current
        # user is masquerading as a generic student in a specific group, then
        # return that group.
        if get_course_masquerade(user, course_key) and not is_masquerading_as_specific_student(user, course_key):
            return get_masquerading_user_group(course_key, user, user_partition)

        # For now, treat everyone as a Full-access user, until we have the rest of the
        # feature gating logic in place.

        if not CONTENT_TYPE_GATING_FLAG.is_enabled():
            return cls.FULL_ACCESS

        # If CONTENT_TYPE_GATING is enabled use the following logic to determine whether a user should have FULL_ACCESS
        # or LIMITED_ACCESS

        course_mode = apps.get_model('course_modes.CourseMode')
        modes = course_mode.modes_for_course(course_key, include_expired=True, only_selectable=False)
        modes_dict = {mode.slug: mode for mode in modes}

        # If there is no verified mode, all users are granted FULL_ACCESS
        if not course_mode.has_verified_mode(modes_dict):
            return cls.FULL_ACCESS

        course_enrollment = apps.get_model('student.CourseEnrollment')

        mode_slug, is_active = course_enrollment.enrollment_mode_for_user(user, course_key)

        if mode_slug and is_active:
            course_mode = course_mode.mode_for_course(
                course_key,
                mode_slug,
                modes=modes,
            )
            if course_mode is None:
                LOG.error(
                    "User %s is in an unknown CourseMode '%s'"
                    " for course %s. Granting full access to content for this user",
                    user.username,
                    mode_slug,
                    course_key,
                )
                return cls.FULL_ACCESS

            if mode_slug == CourseMode.AUDIT:
                return cls.LIMITED_ACCESS
            else:
                return cls.FULL_ACCESS
        else:
            # Unenrolled users don't get gated content
            return cls.LIMITED_ACCESS
Exemple #4
0
    def get_group_for_user(cls, course_key, user, user_partition, **kwargs):  # pylint: disable=unused-argument
        """
        Returns the Group from the specified user partition to which the user
        is assigned, via enrollment mode. If a user is in a Credit mode, the Verified or
        Professional mode for the course is returned instead.

        If a course is using the Verified Track Cohorting pilot feature, this method
        returns None regardless of the user's enrollment mode.
        """
        if is_course_using_cohort_instead(course_key):
            return None

        # First, check if we have to deal with masquerading.
        # If the current user is masquerading as a specific student, use the
        # same logic as normal to return that student's group. If the current
        # user is masquerading as a generic student in a specific group, then
        # return that group.
        if get_course_masquerade(
                user, course_key) and not is_masquerading_as_specific_student(
                    user, course_key):
            return get_masquerading_user_group(course_key, user,
                                               user_partition)

        mode_slug, is_active = CourseEnrollment.enrollment_mode_for_user(
            user, course_key)
        if mode_slug and is_active:
            course_mode = CourseMode.mode_for_course(
                course_key,
                mode_slug,
                modes=CourseMode.modes_for_course(course_key,
                                                  include_expired=True,
                                                  only_selectable=False),
            )
            if course_mode and CourseMode.is_credit_mode(course_mode):
                # We want the verified track even if the upgrade deadline has passed, since we
                # are determining what content to show the user, not whether the user can enroll
                # in the verified track.
                course_mode = CourseMode.verified_mode_for_course(
                    course_key, include_expired=True)
            if not course_mode:
                course_mode = CourseMode.DEFAULT_MODE
            return Group(ENROLLMENT_GROUP_IDS[course_mode.slug]["id"],
                         six.text_type(course_mode.name))
        else:
            return None
Exemple #5
0
    def get_group_for_user(cls, course_key, user, user_partition, **kwargs):  # pylint: disable=unused-argument
        """
        Returns the Group for the specified user.
        """

        # First, check if we have to deal with masquerading.
        # If the current user is masquerading as a specific student, use the
        # same logic as normal to return that student's group. If the current
        # user is masquerading as a generic student in a specific group, then
        # return that group.
        if get_course_masquerade(
                user, course_key) and not is_masquerading_as_specific_student(
                    user, course_key):
            return get_masquerading_user_group(course_key, user,
                                               user_partition)

        # For now, treat everyone as a Full-access user, until we have the rest of the
        # feature gating logic in place.
        return cls.FULL_ACCESS
Exemple #6
0
    def get_group_for_user(cls, course_key, user, user_partition, use_cached=True):
        """
        Returns the Group from the specified user partition to which the user
        is assigned, via their cohort membership and any mappings from cohorts
        to partitions / groups that might exist.

        If the user has not yet been assigned to a cohort, an assignment *might*
        be created on-the-fly, as determined by the course's cohort config.
        Any such side-effects will be triggered inside the call to
        cohorts.get_cohort().

        If the user has no cohort mapping, or there is no (valid) cohort ->
        partition group mapping found, the function returns None.
        """
        # First, check if we have to deal with masquerading.
        # If the current user is masquerading as a specific student, use the
        # same logic as normal to return that student's group. If the current
        # user is masquerading as a generic student in a specific group, then
        # return that group.
        if get_course_masquerade(user, course_key) and not is_masquerading_as_specific_student(user, course_key):
            return get_masquerading_user_group(course_key, user, user_partition)

        cohort = get_cohort(user, course_key, use_cached=use_cached)
        if cohort is None:
            # student doesn't have a cohort
            return None

        group_id, partition_id = get_group_info_for_cohort(cohort, use_cached=use_cached)
        if partition_id is None:
            # cohort isn't mapped to any partition group.
            return None

        if partition_id != user_partition.id:
            # if we have a match but the partition doesn't match the requested
            # one it means the mapping is invalid.  the previous state of the
            # partition configuration may have been modified.
            log.warn(
                u"partition mismatch in CohortPartitionScheme: %r",
                {
                    "requested_partition_id": user_partition.id,
                    "found_partition_id": partition_id,
                    "found_group_id": group_id,
                    "cohort_id": cohort.id,
                }
            )
            # fail silently
            return None

        try:
            return user_partition.get_group(group_id)
        except NoSuchUserPartitionGroupError:
            # if we have a match but the group doesn't exist in the partition,
            # it means the mapping is invalid.  the previous state of the
            # partition configuration may have been modified.
            log.warn(
                u"group not found in CohortPartitionScheme: %r",
                {
                    "requested_partition_id": user_partition.id,
                    "requested_group_id": group_id,
                    "cohort_id": cohort.id,
                },
                exc_info=True
            )
            # fail silently
            return None
Exemple #7
0
    def get_group_for_user(cls, course_key, user, user_partition, **kwargs):  # pylint: disable=unused-argument
        """
        Returns the Group for the specified user.
        """

        # First, check if we have to deal with masquerading.
        # If the current user is masquerading as a specific student, use the
        # same logic as normal to return that student's group. If the current
        # user is masquerading as a generic student in a specific group, then
        # return that group.
        course_masquerade = get_course_masquerade(user, course_key)
        if course_masquerade and not is_masquerading_as_specific_student(user, course_key):
            masquerade_group = get_masquerading_user_group(course_key, user, user_partition)
            if masquerade_group is not None:
                return masquerade_group
            else:
                audit_mode_id = settings.COURSE_ENROLLMENT_MODES.get(CourseMode.AUDIT, {}).get('id')
                if course_masquerade.user_partition_id == ENROLLMENT_TRACK_PARTITION_ID:
                    if course_masquerade.group_id != audit_mode_id:
                        return cls.FULL_ACCESS
                    else:
                        return cls.LIMITED_ACCESS

        # For now, treat everyone as a Full-access user, until we have the rest of the
        # feature gating logic in place.

        if not ContentTypeGatingConfig.enabled_for_enrollment(user=user, course_key=course_key):
            return cls.FULL_ACCESS

        # If CONTENT_TYPE_GATING is enabled use the following logic to determine whether a user should have FULL_ACCESS
        # or LIMITED_ACCESS

        course_mode = apps.get_model('course_modes.CourseMode')
        modes = course_mode.modes_for_course(course_key, include_expired=True, only_selectable=False)
        modes_dict = {mode.slug: mode for mode in modes}

        # If there is no verified mode, all users are granted FULL_ACCESS
        if not course_mode.has_verified_mode(modes_dict):
            return cls.FULL_ACCESS

        # If the user is a beta tester for this course they are granted FULL_ACCESS
        if CourseBetaTesterRole(course_key).has_user(user):
            return cls.FULL_ACCESS

        course_enrollment = apps.get_model('student.CourseEnrollment')

        mode_slug, is_active = course_enrollment.enrollment_mode_for_user(user, course_key)

        if mode_slug and is_active:
            course_mode = course_mode.mode_for_course(
                course_key,
                mode_slug,
                modes=modes,
            )
            if course_mode is None:
                LOG.error(
                    "User %s is in an unknown CourseMode '%s'"
                    " for course %s. Granting full access to content for this user",
                    user.username,
                    mode_slug,
                    course_key,
                )
                return cls.FULL_ACCESS

            if mode_slug == CourseMode.AUDIT:
                return cls.LIMITED_ACCESS
            else:
                return cls.FULL_ACCESS
        else:
            # Unenrolled users don't get gated content
            return cls.LIMITED_ACCESS