Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
0.00% covered (danger)
0.00%
0 / 302
0.00% covered (danger)
0.00%
0 / 2
CRAP
0.00% covered (danger)
0.00%
0 / 1
Users
0.00% covered (danger)
0.00%
0 / 302
0.00% covered (danger)
0.00%
0 / 2
30
0.00% covered (danger)
0.00%
0 / 1
 __construct
0.00% covered (danger)
0.00%
0 / 1
0.00% covered (danger)
0.00%
0 / 1
2
 register_abilities
0.00% covered (danger)
0.00%
0 / 301
0.00% covered (danger)
0.00%
0 / 1
20
1<?php
2declare( strict_types=1 );
3
4namespace BLU\Abilities;
5
6/**
7 * Users abilities for WordPress user management.
8 */
9class Users {
10
11    /**
12     * Constructor - registers all user-related abilities.
13     */
14    public function __construct() {
15        $this->register_abilities();
16    }
17
18    /**
19     * Register user abilities.
20     */
21    private function register_abilities(): void {
22        // Search/list users
23        blu_register_ability(
24            'blu/users-search',
25            array(
26                'label'               => 'Search Users',
27                'description'         => 'Search and filter WordPress users with pagination',
28                'category'            => 'blu-mcp',
29                'input_schema'        => array(
30                    'type'       => 'object',
31                    'properties' => array(
32                        'search'   => array(
33                            'type'        => 'string',
34                            'description' => 'Search term',
35                        ),
36                        'page'     => array(
37                            'type'        => 'integer',
38                            'description' => 'Page number',
39                        ),
40                        'per_page' => array(
41                            'type'        => 'integer',
42                            'description' => 'Users per page',
43                        ),
44                        'roles'    => array(
45                            'type'        => 'array',
46                            'description' => 'Limit to users with at least one of these role slugs (WordPress REST collection param `roles`).',
47                            'items'       => array(
48                                'type' => 'string',
49                            ),
50                        ),
51                    ),
52                ),
53                'execute_callback'    => function ( $input = null ) {
54                    $request = new \WP_REST_Request( 'GET', '/wp/v2/users' );
55                    $query   = is_array( $input ) ? $input : array();
56                    unset( $query['context'] );
57                    $query['context'] = 'edit';
58                    $request->set_query_params( $query );
59                    $response = rest_do_request( $request );
60                    return blu_standardize_rest_response( $response );
61                },
62                'permission_callback' => fn() => current_user_can( 'list_users' ),
63                'meta'                => array(
64                    'annotations' => array(
65                        'readonly'    => true,
66                        'destructive' => false,
67                        'idempotent'  => true,
68                    ),
69                ),
70            )
71        );
72
73        // Get single user
74        blu_register_ability(
75            'blu/get-user',
76            array(
77                'label'               => 'Get User',
78                'description'         => 'Get a WordPress user by ID',
79                'category'            => 'blu-mcp',
80                'input_schema'        => array(
81                    'type'       => 'object',
82                    'properties' => array(
83                        'id' => array(
84                            'type'        => 'integer',
85                            'description' => 'User ID',
86                        ),
87                    ),
88                    'required'   => array( 'id' ),
89                ),
90                'execute_callback'    => function ( $input ) {
91                    $user_id = (int) $input['id'];
92                    $request = new \WP_REST_Request( 'GET', '/wp/v2/users/' . $user_id );
93                    $request->set_query_params( array( 'context' => 'edit' ) );
94                    $response = rest_do_request( $request );
95                    return blu_standardize_rest_response( $response );
96                },
97                'permission_callback' => fn() => current_user_can( 'list_users' ),
98                'meta'                => array(
99                    'annotations' => array(
100                        'readonly'    => true,
101                        'destructive' => false,
102                        'idempotent'  => true,
103                    ),
104                ),
105            )
106        );
107
108        // Add user
109        blu_register_ability(
110            'blu/add-user',
111            array(
112                'label'               => 'Add User',
113                'description'         => 'Add a new WordPress user',
114                'category'            => 'blu-mcp',
115                'input_schema'        => array(
116                    'type'       => 'object',
117                    'properties' => array(
118                        'username'   => array(
119                            'type'        => 'string',
120                            'description' => 'Username',
121                        ),
122                        'email'      => array(
123                            'type'        => 'string',
124                            'description' => 'Email address',
125                        ),
126                        'password'   => array(
127                            'type'        => 'string',
128                            'description' => 'Password',
129                        ),
130                        'first_name' => array(
131                            'type'        => 'string',
132                            'description' => 'First name',
133                        ),
134                        'last_name'  => array(
135                            'type'        => 'string',
136                            'description' => 'Last name',
137                        ),
138                        'roles'      => array(
139                            'type'        => 'array',
140                            'description' => 'WordPress REST `roles`: one or more role slugs (e.g. ["editor"], ["subscriber"]).',
141                            'items'       => array(
142                                'type' => 'string',
143                            ),
144                            'minItems'    => 1,
145                        ),
146                    ),
147                    'required'   => array( 'username', 'email', 'password', 'roles' ),
148                ),
149                'execute_callback'    => function ( $input ) {
150                    $request = new \WP_REST_Request( 'POST', '/wp/v2/users' );
151                    unset( $input['context'] );
152                    $request->set_body_params( $input );
153                    $request->set_query_params( array( 'context' => 'edit' ) );
154                    $response = rest_do_request( $request );
155                    return blu_standardize_rest_response( $response );
156                },
157                'permission_callback' => fn() => current_user_can( 'create_users' ),
158                'meta'                => array(
159                    'annotations' => array(
160                        'readonly'    => false,
161                        'destructive' => false,
162                        'idempotent'  => false,
163                    ),
164                ),
165            )
166        );
167
168        // Update user
169        blu_register_ability(
170            'blu/update-user',
171            array(
172                'label'               => 'Update User',
173                'description'         => 'Update a WordPress user by ID',
174                'category'            => 'blu-mcp',
175                'input_schema'        => array(
176                    'type'       => 'object',
177                    'properties' => array(
178                        'id'         => array(
179                            'type'        => 'integer',
180                            'description' => 'User ID',
181                        ),
182                        'email'      => array(
183                            'type'        => 'string',
184                            'description' => 'Email address',
185                        ),
186                        'first_name' => array(
187                            'type'        => 'string',
188                            'description' => 'First name',
189                        ),
190                        'last_name'  => array(
191                            'type'        => 'string',
192                            'description' => 'Last name',
193                        ),
194                        'roles'      => array(
195                            'type'        => 'array',
196                            'description' => 'WordPress REST `roles` when updating roles; omit if not changing roles.',
197                            'items'       => array(
198                                'type' => 'string',
199                            ),
200                        ),
201                    ),
202                    'required'   => array( 'id' ),
203                ),
204                'execute_callback'    => function ( $input ) {
205                    $user_id = (int) $input['id'];
206                    unset( $input['id'] );
207                    unset( $input['context'] );
208                    $request = new \WP_REST_Request( 'PUT', '/wp/v2/users/' . $user_id );
209                    $request->set_body_params( $input );
210                    $request->set_query_params( array( 'context' => 'edit' ) );
211                    $response = rest_do_request( $request );
212                    return blu_standardize_rest_response( $response );
213                },
214                'permission_callback' => fn() => current_user_can( 'edit_users' ),
215                'meta'                => array(
216                    'annotations' => array(
217                        'readonly'    => false,
218                        'destructive' => false,
219                        'idempotent'  => true,
220                    ),
221                ),
222            )
223        );
224
225        // Delete user
226        blu_register_ability(
227            'blu/delete-user',
228            array(
229                'label'               => 'Delete User',
230                'description'         => 'Delete a WordPress user by ID',
231                'category'            => 'blu-mcp',
232                'input_schema'        => array(
233                    'type'       => 'object',
234                    'properties' => array(
235                        'id'       => array(
236                            'type'        => 'integer',
237                            'description' => 'User ID',
238                        ),
239                        'reassign' => array(
240                            'type'        => 'integer',
241                            'description' => 'User ID to reassign posts to; omit or use 0 / false for no reassignment (the REST API always receives a `reassign` value).',
242                        ),
243                    ),
244                    'required'   => array( 'id' ),
245                ),
246                'execute_callback'    => function ( $input ) {
247                    $user_id = (int) $input['id'];
248                    $request = new \WP_REST_Request( 'DELETE', '/wp/v2/users/' . $user_id );
249                    $reassign = array_key_exists( 'reassign', $input ) ? $input['reassign'] : false;
250                    $request->set_param( 'reassign', $reassign );
251                    $request->set_param( 'force', true );
252                    $response = rest_do_request( $request );
253                    return blu_standardize_rest_response( $response );
254                },
255                'permission_callback' => fn() => current_user_can( 'delete_users' ),
256                'meta'                => array(
257                    'annotations' => array(
258                        'readonly'    => false,
259                        'destructive' => true,
260                        'idempotent'  => true,
261                    ),
262                ),
263            )
264        );
265
266        // Get current user
267        blu_register_ability(
268            'blu/get-current-user',
269            array(
270                'label'               => 'Get Current User',
271                'description'         => 'Get the current logged-in user',
272                'category'            => 'blu-mcp',
273                'input_schema'        => array(
274                    'type' => 'object',
275                ),
276                'execute_callback'    => function () {
277                    $request = new \WP_REST_Request( 'GET', '/wp/v2/users/me' );
278                    $request->set_query_params( array( 'context' => 'edit' ) );
279                    $response = rest_do_request( $request );
280                    return blu_standardize_rest_response( $response );
281                },
282                'permission_callback' => fn() => is_user_logged_in(),
283                'meta'                => array(
284                    'annotations' => array(
285                        'readonly'    => true,
286                        'destructive' => false,
287                        'idempotent'  => true,
288                    ),
289                ),
290            )
291        );
292
293        // Update current user
294        blu_register_ability(
295            'blu/update-current-user',
296            array(
297                'label'               => 'Update Current User',
298                'description'         => 'Update the current logged-in user',
299                'category'            => 'blu-mcp',
300                'input_schema'        => array(
301                    'type'       => 'object',
302                    'properties' => array(
303                        'email'      => array(
304                            'type'        => 'string',
305                            'description' => 'Email address',
306                        ),
307                        'first_name' => array(
308                            'type'        => 'string',
309                            'description' => 'First name',
310                        ),
311                        'last_name'  => array(
312                            'type'        => 'string',
313                            'description' => 'Last name',
314                        ),
315                    ),
316                ),
317                'execute_callback'    => function ( $input = null ) {
318                    $request = new \WP_REST_Request( 'PUT', '/wp/v2/users/me' );
319                    if ( is_array( $input ) ) {
320                        unset( $input['context'] );
321                        $request->set_body_params( $input );
322                    }
323                    $request->set_query_params( array( 'context' => 'edit' ) );
324                    $response = rest_do_request( $request );
325                    return blu_standardize_rest_response( $response );
326                },
327                'permission_callback' => fn() => is_user_logged_in(),
328                'meta'                => array(
329                    'annotations' => array(
330                        'readonly'    => false,
331                        'destructive' => false,
332                        'idempotent'  => true,
333                    ),
334                ),
335            )
336        );
337    }
338}