|
31 | 31 | get_visible_role_assignments_for_user, |
32 | 32 | get_visible_user_role_assignments_filtered_by_current_user, |
33 | 33 | is_user_allowed, |
| 34 | + is_user_allowed_in_any_scope, |
34 | 35 | unassign_all_roles_from_user, |
35 | 36 | unassign_role_from_user, |
36 | 37 | validate_users, |
@@ -605,6 +606,68 @@ def test_is_user_allowed(self, username, action, scope_name, expected_result): |
605 | 606 | ) |
606 | 607 | self.assertEqual(result, expected_result) |
607 | 608 |
|
| 609 | + @data( |
| 610 | + # alice is library_admin on lib:Org1:math_101, so she holds these in at least one scope. |
| 611 | + ("alice", permissions.DELETE_LIBRARY.identifier, True), |
| 612 | + ("alice", permissions.MANAGE_LIBRARY_TEAM.identifier, True), |
| 613 | + # jane is library_user on lib:Org1:english_101, which never grants these permissions. |
| 614 | + ("jane", permissions.DELETE_LIBRARY.identifier, False), |
| 615 | + ("jane", permissions.MANAGE_LIBRARY_TEAM.identifier, False), |
| 616 | + # daniel is course_staff on course-v1:TestOrg+TestCourse+2024_T1, so he holds the |
| 617 | + # staff course permissions in at least one scope. |
| 618 | + ("daniel", permissions.COURSES_VIEW_COURSE.identifier, True), |
| 619 | + ("daniel", permissions.COURSES_EDIT_COURSE_CONTENT.identifier, True), |
| 620 | + ("daniel", permissions.COURSES_PUBLISH_COURSE_CONTENT.identifier, True), |
| 621 | + # course_staff never grants team management, so daniel holds it in no scope. |
| 622 | + ("daniel", permissions.COURSES_MANAGE_COURSE_TEAM.identifier, False), |
| 623 | + # carlos is course_staff on three different courses; he still holds these in some scope. |
| 624 | + ("carlos", permissions.COURSES_VIEW_COURSE.identifier, True), |
| 625 | + ("carlos", permissions.COURSES_MANAGE_ADVANCED_SETTINGS.identifier, True), |
| 626 | + # jane only holds a library role, so she has no course permission in any scope. |
| 627 | + ("jane", permissions.COURSES_VIEW_COURSE.identifier, False), |
| 628 | + # A user without any assignment is not allowed in any scope. |
| 629 | + ("nonexistent_user", permissions.MANAGE_LIBRARY_TEAM.identifier, False), |
| 630 | + ("nonexistent_user", permissions.COURSES_VIEW_COURSE.identifier, False), |
| 631 | + ) |
| 632 | + @unpack |
| 633 | + def test_is_user_allowed_in_any_scope(self, username, action, expected_result): |
| 634 | + """Test checking if a user holds a permission in at least one scope. |
| 635 | +
|
| 636 | + Expected result: |
| 637 | + - The function returns True when the user has the permission in any scope, |
| 638 | + and False when the user has it in no scope. |
| 639 | + """ |
| 640 | + result = is_user_allowed_in_any_scope( |
| 641 | + user_external_key=username, |
| 642 | + action_external_key=action, |
| 643 | + ) |
| 644 | + self.assertEqual(result, expected_result) |
| 645 | + |
| 646 | + @data( |
| 647 | + # Staff-only user |
| 648 | + ("staff_member", {"is_staff": True}), |
| 649 | + # Superuser-only user |
| 650 | + ("superuser_member", {"is_superuser": True}), |
| 651 | + # Both staff and superuser |
| 652 | + ("staff_superuser_member", {"is_staff": True, "is_superuser": True}), |
| 653 | + ) |
| 654 | + @unpack |
| 655 | + def test_is_user_allowed_in_any_scope_staff_always_allowed(self, username, flags): |
| 656 | + """Staff/superusers are allowed for any action regardless of explicit assignments. |
| 657 | +
|
| 658 | + Expected result: |
| 659 | + - The function returns True for a staff and/or superuser user that has no |
| 660 | + role assignments. |
| 661 | + """ |
| 662 | + User = get_user_model() |
| 663 | + User.objects.create_user(username=username, email=f"{username}@example.com", **flags) |
| 664 | + |
| 665 | + result = is_user_allowed_in_any_scope( |
| 666 | + user_external_key=username, |
| 667 | + action_external_key=permissions.MANAGE_LIBRARY_TEAM.identifier, |
| 668 | + ) |
| 669 | + self.assertTrue(result) |
| 670 | + |
608 | 671 |
|
609 | 672 | @ddt |
610 | 673 | class TestValidateUsersAPI(UserAssignmentsSetupMixin): |
|
0 commit comments