Authoring AuthZ: User Stories
This is for scope alignment. Feedback is welcome.
M1 - Parity with legacy roles
M1.1 Studio parity for Staff and Admin
User story As a platform administrator, I want course Staff and course Admin to keep the same authoring access in Studio as today.
Acceptance criteria
Course Staff effective access in Studio matches the permissions defined for Course Staff in the Authoring Roles and Permissions catalog.
Course Admin effective access in Studio matches the permissions defined for Course Admin in the Authoring Roles and Permissions catalog.
AuthZ is the enforcement path for the Studio authoring actions covered in M1.
No new UI or Administrative Console flows are introduced in M1.
Super Admin, Global Staff, and Course Creator behave as they do today.
Notes
A permission outcomes spec is needed for the permissions in scope for M1, describing expected behavior when each permission is granted vs not granted, including UI behavior and backend enforcement behavior.
Some behaviors are still TBD, especially around taxonomies and reruns.
M1.2 Migration tooling
User story As a platform administrator, I want existing course role assignments to work under AuthZ during rollout.
Acceptance criteria
Existing Course Staff and Course Admin assignments are represented in AuthZ.
The system can detect mismatches between legacy assignments and AuthZ data.
A reconciliation mechanism exists to sync AuthZ from the current source of role assignments, without relying on a new UI.
M2 - Unfiltered view + bulk actions
Entry points
M2.1 Open the console from Studio home, unfiltered view
User story As a platform member with at least one role assignment on any course or library, I want to open the Roles and Permissions console from the Studio home, so I can review access across all resources I can see.
Acceptance criteria
There is an entry point on the Studio home that opens the Roles and Permissions console.
The console opens in a new tab.
The console opens in an unfiltered state, showing all users with at least one role assignment on any resource the current user has access to.
The screen is titled "Roles and Permissions Management."
Any user with a role assignment on at least one resource can access this view. All current new roles include this access.
Test cases
Setup
User A has at least one role assignment on any course or library.
Scenarios
User with a role assignment sees the entry point Given: I am logged in as User A When: I open the Studio home Then: I see the Roles and Permissions entry point
Clicking the entry point opens the console in a new tab Given: I am User A on the Studio home When: I click the Roles and Permissions entry point Then: a new tab opens And: the console loads in an unfiltered state And: the Team Members tab is selected by default And: the screen title is "Roles and Permissions Management"
Out of scope
The behavior of the console once opened is covered in M2.4, M2.5, M2.6, and M2.7.
Notes
This entry point is global and not tied to any specific course or library context.
The unfiltered view is the same UI as the filtered views, with no pre-applied query string.
M2.2 Open the console from a library, prefiltered view
User story As a library team member, I want to open the Roles and Permissions console from the library sidebar, so I can review the team for that library without leaving the library context.
Acceptance criteria
There is a "Manage Library Team" entry point in the library sidebar, in the library detail view.
Selecting it opens the Roles and Permissions console in a new tab, prefiltered to that library via a query string applied to the Scope filter.
The resulting view is the same Team Members tab as the global console, with the library scope pre-applied as a filter.
The filter state is visible and consistent with manually applying that scope filter from within the console.
Test cases
Setup
User A is a Library User in Library 1 (lowest role, still has access to the library).
Scenarios
Any library team member sees the entry point Given: I am logged in as User A When: I open Library 1 Then: I see the "Manage Library Team" entry point in the library sidebar
Clicking the entry point opens the console prefiltered to that library Given: I am User A on Library 1 When: I click "Manage Library Team" Then: a new tab opens And: the console loads with the Scope filter pre-applied to Library 1 And: the Team Members tab is selected by default And: the filter state is visible and consistent with manually applying that scope filter
Out of scope
The behavior of the console once opened is covered in M2.4, M2.5, M2.6, and M2.7.
Notes
This entry point replaces the existing "Manage Library Team" behavior. The individual library views previously available within the console are fully replaced by the new UI.
The entry point opens the same console as the global entry point, scoped via a query string. There is no separate UI for library management.
M2.3 Open the console from a course in Studio, prefiltered view
User story As a course team member, I want to open the Roles and Permissions console from Studio Settings for a specific course, so I can review the team for that course without losing the course context.
Acceptance criteria
There is a "Roles and Permissions" entry point in Studio Settings for a course.
Selecting it opens the Roles and Permissions console in a new tab, prefiltered to that course via a query string applied to the Scope filter.
The resulting view is the same Team Members tab as the global console, with the course scope pre-applied as a filter.
The filter state is visible and consistent with manually applying that scope filter from within the console.
Test cases
Setup
User A is a Course Staff member in Course 1.
Scenarios
Any course team member sees the entry point Given: I am logged in as User A When: I open Course 1 in Studio and go to Settings Then: I see the Roles and Permissions entry point
Clicking the entry point opens the console prefiltered to that course Given: I am User A on Course 1 in Studio Settings When: I click the Roles and Permissions entry point Then: a new tab opens And: the console loads with the Scope filter pre-applied to Course 1 And: the Team Members tab is selected by default And: the filter state is visible and consistent with manually applying that scope filter
Out of scope
The behavior of the console once opened is covered in M2.4, M2.5, M2.6, and M2.7.
Notes
The entry point opens the same console as the global entry point, scoped via a query string. There is no separate UI for course team management.
Console — Team Members tab
M2.4 Team Members tab
User story As a platform member with console access, I want to see a list of users in the Team Members tab, so I can get an overview of who has access across the resources I can manage.
Acceptance criteria
The Team Members tab shows a paginated table with 10 rows per page.
The table has six columns: Name, Email, Organization, Scope, Role, Actions.
Each row represents one role assignment. A user with multiple assignments appears once per assignment.
The logged-in user is identified with a "(me)" label next to their username in the table.
A counter above the table shows the number of results currently displayed out of the total, for example "Showing 10 of 100 users."
Rows corresponding to Super Admin or Global Staff users are visually highlighted with a distinct row color.
Name, Email, Organization, Scope, and Role columns can be sorted A to Z and Z to A.
Pagination includes previous/next arrows and a page selector using the Paragon "reduce" variant.
Test cases
Setup
The platform has 2 organizations: Organization 1 and Organization 2.
Organization 1 has 2 courses and 1 library.
Organization 2 has 1 course.
User A has permissions across both organizations (global scope).
User B has permissions on Organization 1 only.
User C is Super Admin.
User D has 3 role assignments across different courses in Organization 1.
The logged-in user has 2 role assignments in Organization 1.
Scenarios
Logged-in user is identified with a "(me)" label Given: I open the Team Members tab Then: I see "(me)" next to my username in the table
User with multiple assignments appears once per assignment Given: User D has 3 role assignments When: I open the Team Members tab Then: I see 3 separate rows for User D
User with global scope sees users from all organizations Given: I am logged in as User A When: I open the Team Members tab Then: I see users from both Organization 1 and Organization 2
User with limited scope sees only users from their organization Given: I am logged in as User B When: I open the Team Members tab Then: I see only users from Organization 1 And: I do not see users from Organization 2
Super Admin row is visually highlighted Given: User C is Super Admin When: I open the Team Members tab Then: User C's row is displayed with a distinct row color
Counter reflects current results Given: the table has 45 role assignments total When: I open the Team Members tab Then: I see "Showing 10 of 45 users"
Columns can be sorted A to Z and Z to A Given: I am on the Team Members tab When: I click a sortable column header once Then: the table sorts A to Z by that column When: I click it again Then: the table sorts Z to A
Pagination controls work correctly Given: the table has more than 10 rows Then: I see previous and next arrows And: I see a page selector using the Paragon reduce variant When: I click the next arrow Then: the next page of results is shown When: I click the previous arrow Then: the previous page of results is shown
Out of scope
Search and filter behavior is covered in M2.5.
Grouping users by person (collapsing multiple assignments into one row) is out of scope for this iteration and planned for a later phase.
M2.5 Search and filters in the Team Members tab
User story As a platform member with console access, I want to search and filter the Team Members list, so I can quickly find specific users or narrow down by role, organization, or scope.
Acceptance criteria
There is a search bar that filters by user name and email.
There are three filters: Organization, Role, and Scope.
Organization: dropdown with a search bar, checkbox list, selected items pin to top, shows X of Y count. Loads up to 10 elements from the backend. If the results shown are fewer than the total, a "Search to show more" label is displayed.
Role: dropdown with checkbox list, results grouped by global, course, and library. Shows all current available roles. No search bar. Supports multi-select. If the results shown are fewer than the total, a "Search to show more" label is displayed.
Scope: the dropdown loads 5 courses and 5 libraries from the backend. The frontend organizes results by courses and libraries. If there are no results under a category, that category is not shown. If the results shown are fewer than the total, a "Search to show more" label is displayed.
Active filters change color and show a count badge with the number of selected options.
Applied filters appear as tags below the filter row, up to a maximum of 10.
A "clear all filters" button is available. Each tag has an X to remove it individually.
When the user reaches the 10-filter limit, an alert appears below the filter tags explaining that the limit has been reached and that a filter must be removed before adding a new one.
Columns that are being filtered show an icon in their header.
Test cases
Setup
The platform has at least 11 organizations.
Organization 1 has 2 courses and 1 library.
Organization 2 has 1 course.
User A has a Course Staff role in Course 1 (Organization 1) and a Library Author role in Library 1 (Organization 1).
User B has a Course Admin role in Course 2 (Organization 1).
User C has a Course Staff role in Course 1 (Organization 2).
User D is Super Admin.
Scenarios
Search by name filters the table Given: I type a name in the search bar Then: the table updates to show only users matching that name
Search by email filters the table Given: I type an email in the search bar Then: the table updates to show only users matching that email
Organization filter loads up to 10 elements with search Given: I open the Organization filter dropdown Then: I see up to 10 organizations And: there is a search bar to find more When: I select an organization Then: it pins to the top of the list And: the filter badge shows a count of 1 And: a tag appears below the filter row
Role filter shows all roles grouped by type, no search bar Given: I open the Role filter dropdown Then: I see all available roles grouped by global, course, and library And: there is no search bar When: I select multiple roles Then: the filter badge shows the count of selected roles And: a tag appears per selected role below the filter row
Scope filter shows 5 courses and 5 libraries Given: I open the Scope filter dropdown Then: I see up to 5 courses and up to 5 libraries And: results are organized by courses and libraries And: categories with no results are not shown When: I select a scope Then: a tag appears below the filter row
Filtered columns show an icon in the header Given: I have applied a filter on Organization Then: the Organization column header shows a filter icon
Reaching the 10-filter limit shows an alert Given: I have 10 filters applied When: I try to add an eleventh filter Then: an alert appears below the filter tags explaining the limit And: I cannot add more filters until I remove one
Removing a tag removes that filter Given: I have filters applied When: I click the X on a filter tag Then: that filter is removed And: the table updates accordingly
Clear all removes all filters Given: I have multiple filters applied When: I click "clear all filters" Then: all filters are removed And: the table returns to its unfiltered state
Notes
The exact number of elements loaded by the Organization and Scope filters is pending alignment with the development team.
Console — User audit view
M2.6 View the audit detail for a specific user
User story As a platform member with console access, I want to open a user's detail view from the Team Members table, so I can see all role assignments for that user in one place.
Acceptance criteria
The role assignments shown in the user audit view are limited to the scopes the viewing user has access to. A viewing user with global permissions sees all assignments. A viewing user with access to only one scope sees only the assignments related to that scope.
Each row in the Team Members table has an eye icon in the Actions column. Selecting it opens the user audit view.
The user audit view shows a breadcrumb: "Roles and Permissions Management > [User name]."
Selecting the first breadcrumb element returns to the Team Members table.
The view shows the audited user's name and email above the table.
The table in this view has the following columns: Role, Organization, Scope, (unnamed accordion column), Actions.
Each row represents one role assignment for that user.
Rows corresponding to Super Admin or Global Staff assignments are visually highlighted with a distinct row color.
The table can be filtered by Organization and Role. No Scope filter in this view.
The unnamed column contains a "View All Permissions" control. Selecting it expands an accordion showing all permissions associated with that role, grouped by category. Each permission group has an info icon with a tooltip describing the permissions it includes. The tooltip text per group is the same as defined in M2.7. Opening one accordion closes the previously open one.
The Actions column shows a trash icon to remove that role assignment, if the viewing user has
manage_course_teamormanage_library_teamon the relevant scope.If the viewing user is looking at their own admin assignment, the trash icon is grayed out. Hovering or clicking it shows a tooltip: "You can't remove your own admin role. This prevents a resource from being left without an admin. Another user with the required permissions can revoke it."
Super Admin and Global Staff entries show a different icon instead of the trash (icon TBD). Hovering or clicking it shows a tooltip: "This role is managed at the platform level and cannot be changed from here. To modify it, go to Django Admin."
The table is paginated with 10 rows per page, with previous/next arrows and a page selector using the Paragon "reduce" variant.
Role, Organization, and Scope columns can be sorted A to Z and Z to A.
Test cases
Setup
The platform has 2 organizations: Organization 1 and Organization 2.
Viewing User A has permissions across both organizations (global scope).
Viewing User B has permissions on Organization 1 only.
Audited User has role assignments in both Organization 1 and Organization 2.
Audited User C is Super Admin.
Audited User D has only one role assignment.
The logged-in user is Course Admin in Course 1 (Organization 1).
Scenarios
Viewing user with global scope sees all assignments Given: I am logged in as Viewing User A When: I open the audit view for Audited User Then: I see assignments from both Organization 1 and Organization 2
Viewing user with limited scope sees only relevant assignments Given: I am logged in as Viewing User B When: I open the audit view for Audited User Then: I see only assignments from Organization 1
Breadcrumb navigates back correctly Given: I am on the user audit view Then: the breadcrumb shows "Roles and Permissions Management > [User name]" When: I click "Roles and Permissions Management" Then: I return to the Team Members table
Super Admin row is visually highlighted Given: I open the audit view for Audited User C Then: their row is displayed with a distinct row color
View All Permissions expands the accordion Given: I am on the user audit view When: I click "View All Permissions" on a row Then: the accordion expands showing all permissions grouped by category And: each permission group shows an info icon with a tooltip describing the permissions it includes
Opening a second accordion closes the first Given: I have one accordion open When: I click "View All Permissions" on a different row Then: the first accordion closes and the new one opens
Trash icon visible when I have the right permissions Given: I am Course Admin in Course 1 When: I view a Course Staff assignment for Course 1 Then: I see a trash icon in the Actions column
Trash icon grayed out for my own admin assignment Given: I am viewing my own audit page When: I look at my Course Admin assignment for Course 1 Then: the trash icon is grayed out When: I hover or click it Then: a tooltip reads "You can't remove your own admin role. This prevents a resource from being left without an admin. Another user with the required permissions can revoke it."
Super Admin and Global Staff show a different icon Given: Audited User C has a Super Admin assignment When: I view that row Then: I see a non-trash icon (icon TBD) When: I hover or click it Then: a tooltip reads "This role is managed at the platform level and cannot be changed from here. To modify it, go to Django Admin."
Removing a role with remaining assignments updates the table Given: Audited User has more than one role assignment When: I click the trash icon Then: a confirmation modal appears When: I confirm Then: the role is removed, a success toast appears, and the table updates
Removing the last role assignment redirects to Team Members Given: Audited User D has only one role assignment When: I click the trash icon and confirm Then: the role is removed, a success toast appears, and I am redirected to the Team Members table
Error during removal shows error toast Given: I confirm a role removal When: the removal fails Then: an error toast appears and the role assignment remains in the table
Columns can be sorted A to Z and Z to A Given: I am on the user audit view When: I click a sortable column header once Then: the table sorts A to Z by that column When: I click it again Then: the table sorts Z to A
Pagination controls work correctly Given: the audited user has more than 10 role assignments Then: I see previous and next arrows And: I see a page selector using the Paragon reduce variant When: I click the next arrow Then: the next page of results is shown
Out of scope
API error handling for 401, 403, 404 is handled at the platform level.
Notes
The Actions column header may need a label for consistency. Currently unnamed in the design.
The icon for Super Admin and Global Staff entries in the Actions column is still TBD.
The "can't remove own admin" rule is intentional to prevent resources from becoming ownerless.
Console — Roles and Permissions tab
M2.7 View the Roles and Permissions tab
User story As a platform member with console access, I want to view the Roles and Permissions tab, so I can understand what each role can and cannot do across courses and libraries.
Acceptance criteria
The console has a second tab labeled "Roles and Permissions," alongside the Team Members tab.
The tab contains a selector to switch between course roles and library roles. The default selection is always course roles, regardless of the current user's access.
The tab title updates to reflect the current selection: "Course Roles" or "Library Roles."
The view shows a permission matrix table. The first column lists permissions grouped by functional area. The remaining columns represent the available roles for the selected resource type.
For course roles, the columns are: Course Admin, Course Staff, Course Editor, and Course Auditor.
For library roles, the columns are: Library Admin, Library Author, Library Collaborator, and Library User.
Each cell shows a checkmark if the role has that permission, or an X if it does not.
Course Editor and Course Auditor columns are grayed out and marked as "coming soon." They are not selectable. A tooltip on hover explains that these roles are not yet available in this version.
The permission list is long, so the table is scrollable vertically.
The role column headers are sticky and remain visible while scrolling down.
The row headers of the permission matrix are sticky and remain visible while scrolling horizontally.
A button is available to scroll back to the top of the page.
Each permission group has an info icon that shows a tooltip listing the permissions included in that group on hover.
Each checkmark and X has an accessibility tag indicating "available" or "not available" for screen readers.
A copy block below the table title reads: "Note: This list shows the permissions currently available in Authoring Studio. Some roles may grant additional permissions managed outside this interface." A "See full documentation" link points to https://docs.openedx.org/en/latest/educators/references/course_development/course_team_roles.html
Role descriptions shown in the tab
Super Admin: Super Admins have full access to all areas of the platform, including content, settings, and user management. This role is managed at the platform level and cannot be changed from here. To modify it, go to Django Admin.
Global Staff: Global Staff have access to all areas of the platform, similar to Super Admin, but cannot grant or revoke Super Admin or Global Staff roles to other users. This role is managed at the platform level and cannot be changed from here. To modify it, go to Django Admin.
Permission group tooltips — Course roles
Course access & content: View course: See the course in the Studio home and access the course outline in read-only mode. Includes the "View Live" option to preview the course as a learner in the LMS. / Create course: Create a new course in Studio. / Edit course content: Edit the course outline, units, and components. / Publish course content: Make course content visible to learners.
Library updates: Manage library updates: Accept or reject pending updates from content libraries linked to this course.
Course updates & handouts: View course updates: See course announcements and handouts visible to learners. / Manage course updates: Create, edit, and delete course announcements and handouts.
Pages & Resources: View pages & resources: See the Pages & Resources section in Studio. / Manage pages & resources: Enable or disable course features such as Discussions, the Wiki, Notes, Calculator, and Live. Create and edit Textbooks and Custom pages, and manage their configurations.
Files: View files: See the list of files and assets uploaded to the course. / Create files: Upload new files and assets to the course. / Edit files: Perform non-destructive actions on files, such as locking or unlocking them. / Delete files: Permanently remove files and assets from the course.
Schedule & details: View schedule: See the course start and end dates, enrollment dates, and pacing settings. / Edit schedule: Update course start and end dates, enrollment dates, and pacing settings. / View course details: See course information including the course summary, pacing, and prerequisites. / Edit course details: Update course information including the course summary, pacing, and prerequisites.
Grading: View grading settings: See the grading configuration for the course, including assignment types and grading scale. / Edit grading settings: Update the grading configuration for the course, including assignment types and grading scale.
Course team & groups: View course team: See the list of users with a role assigned to this course. / Manage course team: Add, change, or remove role assignments for this course from the Roles and Permissions console. / Manage group configurations: Create and manage content groups used to target course content to specific learners.
Tags & taxonomies: Manage tags: Create, edit, and delete tags on this course. / Manage taxonomies: Create, edit, and delete taxonomies used to organize course content.
Advanced & certificates: Manage advanced settings: Access and edit the Advanced Settings page in Studio. This covers a wide range of technical course configurations, including proctoring, timed exams, LTI tools, enrollment limits, and custom display options. / Manage certificates: Create and edit course certificates, including certificate design and eligibility settings.
Import / export: Import course: Import course content from a file. This is a high-privilege action that can overwrite most course content and settings. / Export course: Download the course content as a file for backup or reuse in another platform. / Export tags: Download the tag data associated with this course.
Other: View checklists: See the course launch checklist in Studio. / View global staff & super admins: See the list of users with platform-wide roles such as Global Staff and Super Admin.
Permission group tooltips — Library roles
Library: View: See the library in Studio and access its content in read-only mode. / Manage tag: Create, edit, and delete tags on this library. / Publish: Publish the library to make it available for use in courses.
Content: Create: Create new content items in the library. / Edit: Edit existing content items in the library. / Delete: Permanently remove content items from the library. / Publish: Publish individual content items to make them available for reuse in courses. / Reuse: Add published content from this library to a course. / Import Content from Course: Import content from an existing course into this library.
Team: View: See the list of users with a role assigned to this library. / Manage: Add, change, or remove role assignments for this library from the Roles and Permissions console.
Collections: Create: Create new collections to organize content within the library. / Edit: Update the name and contents of existing collections. / Delete: Permanently remove collections from the library.
Test cases
Setup
This tab is static and shows the same content to all users regardless of their permissions.
Scenarios
Default selection is Course Roles Given: I open the Roles and Permissions tab Then: the Course Roles view is shown by default
Switching to Library Roles updates the table Given: I am on the Roles and Permissions tab showing Course Roles When: I select Library Roles Then: the table updates to show library roles and their permissions
Permission matrix shows checkmarks and X correctly Given: I am viewing Course Roles Then: each cell shows a checkmark if the role has that permission And: each cell shows an X if the role does not have that permission
Course Editor and Course Auditor are grayed out with coming soon tooltip Given: I am viewing Course Roles Then: Course Editor and Course Auditor columns are grayed out And: they are marked as "coming soon" When: I hover over either column Then: a tooltip explains these roles are not yet available in this version
Column headers are sticky while scrolling Given: I am on the Roles and Permissions tab When: I scroll down through the permission list Then: the role column headers remain visible at the top
Scroll to top button works Given: I have scrolled down on the Roles and Permissions tab When: I click the scroll to top button Then: the page scrolls back to the top
Permission group tooltip appears on hover Given: I am viewing the permission matrix When: I hover over the info icon of a permission group Then: a tooltip appears listing the permissions included in that group
Checkmarks and X have accessibility tags Given: I am viewing the permission matrix Then: each checkmark has an accessibility tag indicating "available" And: each X has an accessibility tag indicating "not available"
Row headers are sticky while scrolling horizontally Given: I am on the Roles and Permissions tab When: I scroll horizontally through the permission matrix Then: the row headers remain visible
Copy block explains partial permissions list Given: I am on the Roles and Permissions tab Then: I see the note about the partial permissions list And: there is a "See full documentation" link
Out of scope
This tab is read-only. Role assignment is handled through the assign role wizard.
Notes
Course Editor and Course Auditor are visible in the matrix but not yet available. This gives users visibility into the upcoming role model without enabling assignment.
The "coming soon" treatment also applies in the role assignment wizard: these roles are not available as options.
Assign role wizard
M2.8 Assign role wizard
User story As a platform member with the right permissions, I want to assign a role to one or more users across one or more scopes, so I can grant access without leaving the console.
Acceptance criteria
General
The "Assign Role" CTA is always visible in the console, both in the Team Members tab and in the Roles and Permissions tab.
When accessing the wizard from the user audit view, the user input in Step 1 is pre-populated with that user.
The wizard has a breadcrumb that exits the flow and returns to the previous view at any point.
A Cancel button is available at the bottom of both steps. Clicking it returns to the previous view.
Step 1 — Who and Role
Step 1 is titled "Who and Role."
There is a text input to add one or more usernames or emails, separated by commas.
Users must have an existing account. If any user in the batch does not exist, the input shows an error in red for the invalid entries and the flow is blocked until all entries are valid.
Below the input there is a role selector using radio buttons. Only one role can be selected at a time. Selecting a new role deselects the previous one.
Roles are grouped by courses and libraries. A user only sees the groups they have permissions to assign. If they have no library scopes, they do not see libraries. If they have no course scopes, they do not see courses.
Course Editor and Course Auditor are grayed out and not selectable.
There is a link to documentation for roles not available in the list.
Clicking Next validates the users. If all users exist, the wizard moves to Step 2. If any do not exist, the flow is blocked.
Step 2 — Where It Applies
Step 2 is titled "Where It Applies."
There is a search bar to search scopes by name.
Next to the search bar there is an Organization filter with the same behavior as in M2.5.
Scopes are organized by organization, with a header showing the organization name.
Each scope item has a checkbox. Multiple scopes can be selected.
Users with
manage_course_teamat the organization level see an additional option "All courses in this organization" at the top of that organization's section.Users with
manage_library_teamat the organization level see an equivalent "All libraries in this organization" option.Users with platform-wide permissions see equivalent global scope options.
Users without these higher-scope permissions do not see these options.
The scope list uses infinite scroll.
Selections are preserved when the user searches or filters. Selections are not preserved when scrolling.
Clicking Save shows a loading state while the request is in flight.
On success, a toast appears and the user is redirected to the previous view.
On error, the existing error toast logic is reused. The user remains in Step 2 to retry.
Test cases
Setup
User A has
manage_course_teamon at least one scope.User B has
manage_library_teamon at least one scope.User C has both
manage_course_teamandmanage_library_team.User D has
manage_course_teamon Organization 1 only.User E has
manage_course_teamplatform-wide.Existing User is a registered platform user.
Nonexistent User has no platform account.
Scenarios
CTA is always visible in the console Given: I am on the Team Members tab or the Roles and Permissions tab Then: I see the Assign Role CTA
Wizard opens with user pre-populated from audit view Given: I am on the user audit view for Existing User When: I click Assign Role Then: the wizard opens with Existing User pre-populated in the user input
Breadcrumb exits the flow at any point Given: I am anywhere in the wizard When: I click the breadcrumb Then: I return to the view I came from
Cancel returns to the previous view from Step 1 Given: I am on Step 1 When: I click Cancel Then: I return to the view I came from with no changes
Cancel returns to the previous view from Step 2 Given: I am on Step 2 When: I click Cancel Then: I return to the view I came from with no changes
User A only sees course roles Given: I am logged in as User A When: I open the wizard Then: I see only course roles in the role selector
User B only sees library roles Given: I am logged in as User B When: I open the wizard Then: I see only library roles in the role selector
User C sees both course and library roles Given: I am logged in as User C When: I open the wizard Then: I see both course and library roles in the role selector
Selecting a role deselects the previous one Given: I have selected a role When: I select a different role Then: the previous role is deselected And: only the new role is selected
All users in the batch must exist to proceed Given: I have entered Existing User and Nonexistent User in the input When: I click Next Then: the input shows an error in red for Nonexistent User And: the flow is blocked
All users valid, proceed to Step 2 Given: I have entered only valid users and selected a role When: I click Next Then: the wizard moves to Step 2
Scopes are organized by organization Given: I am on Step 2 Then: I see scopes grouped under organization headers
User D sees "All courses in Organization 1" option Given: I am logged in as User D When: I open Step 2 after selecting a course role Then: I see "All courses in this organization" at the top of Organization 1's section
User E sees a global scope option Given: I am logged in as User E When: I open Step 2 Then: I see a global scope option for all courses
Multiple scopes can be selected Given: I am on Step 2 When: I select multiple scope checkboxes Then: all selected scopes remain checked
Selections are preserved after searching Given: I have selected a scope When: I type in the search bar Then: my previous selection remains checked in the results
Save shows loading state and redirects on success Given: I have selected one or more scopes When: I click Save Then: the Save button shows a loading state And: on success a toast appears confirming the assignment And: I am redirected to the previous view
Save shows error toast on failure and keeps me in Step 2 Given: I have selected one or more scopes When: I click Save and the request fails Then: an error toast appears And: I remain on Step 2
Out of scope
Error toast copy and logic reuses existing implementation. No new toast patterns are introduced.
Notes
Course Editor and Course Auditor are not available in this version. They appear grayed out in the role selector.