Make WP admins instructors too, and add an Access toggle page
CI / No Debug Code (pull_request) Successful in 3s
CI / Tests (PHP 8.2) (pull_request) Successful in 41s
CI / Tests (PHP 8.3) (pull_request) Successful in 51s
CI / Tests (PHP 8.1) (pull_request) Successful in 54s
CI / Coding Standards (pull_request) Successful in 58s
CI / PHPStan (pull_request) Successful in 1m9s
CI / Build Plugin Zip (pull_request) Has been skipped
CI / No Debug Code (pull_request) Successful in 3s
CI / Tests (PHP 8.2) (pull_request) Successful in 41s
CI / Tests (PHP 8.3) (pull_request) Successful in 51s
CI / Tests (PHP 8.1) (pull_request) Successful in 54s
CI / Coding Standards (pull_request) Successful in 58s
CI / PHPStan (pull_request) Successful in 1m9s
CI / Build Plugin Zip (pull_request) Has been skipped
A WordPress administrator previously inherited the studio-admin capabilities but not `manage_availability`, so the studio owner running as an admin had no way to reach "My Availability" or act as the instructor — breaking single-instructor businesses. Grant the instructor capabilities to administrators as well (via the existing `user_has_cap` filter), and make both grants — studio-admin and instructor — independently toggleable from a new Access admin page. - RoleManager: extract `INSTRUCTOR_CAPS`; apply studio and instructor cap sets to administrators, each gated on a stored toggle (default on). - AccessSettings + templates/admin/access.php: two options (`us_admin_grant_studio` / `us_admin_grant_instructor`), gated on the core `manage_options` capability so disabling a grant can never lock an administrator out of re-enabling it. - AdminMenu: register the Access page after Studio Settings; keep the studio sidebar separator visible for any administrator. - Tests for the toggles and the new settings reader; docs updated. Co-Authored-By: Claude Opus 4.8 <[email protected]>
This commit is contained in:
+44
-14
@@ -42,6 +42,26 @@ class RoleManager {
|
||||
self::CAP_EXPORT_PAYMENTS,
|
||||
];
|
||||
|
||||
/**
|
||||
* Capabilities granted to the `us_instructor` role, and implicitly to any
|
||||
* WordPress administrator (see {@see grantStudioCapsToAdministrators()}) so a
|
||||
* single-instructor studio owner can both run the business and teach from one
|
||||
* account — managing their own availability and lessons without being assigned
|
||||
* a separate `us_instructor` role.
|
||||
*
|
||||
* @var list<string>
|
||||
*/
|
||||
public const INSTRUCTOR_CAPS = [
|
||||
self::CAP_MANAGE_AVAILABILITY,
|
||||
self::CAP_MANAGE_OFFERINGS,
|
||||
self::CAP_MANAGE_QUESTIONS,
|
||||
self::CAP_VIEW_LESSONS,
|
||||
self::CAP_VIEW_OWN_PAYMENTS,
|
||||
self::CAP_EXPORT_PAYMENTS,
|
||||
];
|
||||
|
||||
public function __construct( private AccessSettings $access = new AccessSettings() ) {}
|
||||
|
||||
public function register(): void {
|
||||
add_action( 'init', [ $this, 'createRoles' ] );
|
||||
add_filter( 'user_has_cap', [ $this, 'grantStudioCapsToAdministrators' ], 10, 1 );
|
||||
@@ -62,18 +82,15 @@ class RoleManager {
|
||||
}
|
||||
|
||||
if ( get_role( self::INSTRUCTOR ) === null ) {
|
||||
$instructorCaps = [ 'read' => true ];
|
||||
foreach ( self::INSTRUCTOR_CAPS as $cap ) {
|
||||
$instructorCaps[ $cap ] = true;
|
||||
}
|
||||
|
||||
add_role(
|
||||
self::INSTRUCTOR,
|
||||
__( 'Instructor', 'unsupervised-schedular' ),
|
||||
[
|
||||
'read' => true,
|
||||
self::CAP_MANAGE_AVAILABILITY => true,
|
||||
self::CAP_MANAGE_OFFERINGS => true,
|
||||
self::CAP_MANAGE_QUESTIONS => true,
|
||||
self::CAP_VIEW_LESSONS => true,
|
||||
self::CAP_VIEW_OWN_PAYMENTS => true,
|
||||
self::CAP_EXPORT_PAYMENTS => true,
|
||||
]
|
||||
$instructorCaps
|
||||
);
|
||||
}
|
||||
|
||||
@@ -95,9 +112,14 @@ class RoleManager {
|
||||
*
|
||||
* The studio owner runs the site as an administrator (`manage_options`) and
|
||||
* should manage offerings, questions, policies, billing, and reports without
|
||||
* being assigned the separate `us_studio_admin` role. Applied dynamically via
|
||||
* the `user_has_cap` filter, so nothing is persisted and the grant disappears
|
||||
* when the plugin is deactivated.
|
||||
* being assigned the separate `us_studio_admin` role. The instructor
|
||||
* capabilities are granted too, so a single-instructor studio owner can manage
|
||||
* their own availability and lessons and act as the instructor from the same
|
||||
* account. Applied dynamically via the `user_has_cap` filter, so nothing is
|
||||
* persisted and the grant disappears when the plugin is deactivated.
|
||||
*
|
||||
* Both grants are independently toggleable from the Access settings page (see
|
||||
* {@see AccessSettings}); they default on, preserving the single-account setup.
|
||||
*
|
||||
* @param array<string, bool> $allcaps All capabilities currently held by the user.
|
||||
* @return array<string, bool>
|
||||
@@ -107,8 +129,16 @@ class RoleManager {
|
||||
return $allcaps;
|
||||
}
|
||||
|
||||
foreach ( self::STUDIO_ADMIN_CAPS as $cap ) {
|
||||
$allcaps[ $cap ] = true;
|
||||
if ( $this->access->adminsAreStudioAdmins() ) {
|
||||
foreach ( self::STUDIO_ADMIN_CAPS as $cap ) {
|
||||
$allcaps[ $cap ] = true;
|
||||
}
|
||||
}
|
||||
|
||||
if ( $this->access->adminsAreInstructors() ) {
|
||||
foreach ( self::INSTRUCTOR_CAPS as $cap ) {
|
||||
$allcaps[ $cap ] = true;
|
||||
}
|
||||
}
|
||||
|
||||
return $allcaps;
|
||||
|
||||
Reference in New Issue
Block a user