<?php
/**
 * List Capabilities Tool.
 *
 * Lists all known capabilities registered in the system. Aggregates from
 * all roles and includes WordPress core capabilities.
 *
 * @package   Agenistrator
 * @since     1.0.0
 * @author    Alex Ruban <alex@maximum.guru>
 * @author    Maximum Software Inc <contact@maximum.software>
 * @license   GPL-3.0-only
 * @link      https://agenistrator.com/
 *
 * SPDX-FileCopyrightText: 2025-2026 Alex Ruban <alex@maximum.guru>
 * SPDX-FileCopyrightText: 2025-2026 Maximum Software Inc <contact@maximum.software>
 * SPDX-License-Identifier: GPL-3.0-only
 */

namespace Agenistrator;

// Direct access prevention
if ( ! defined( 'ABSPATH' ) ) {
	exit;
}

/**
 * List_Capabilities_Tool class.
 */
class List_Capabilities_Tool extends Tool {

	/**
	 * Get the tool ID.
	 *
	 * @return string The tool ID.
	 * @since     1.0.0
	 */
	public function get_id() {
		return 'list_capabilities';
	}

	/**
	 * Get the tool name.
	 *
	 * @return string The tool name.
	 * @since     1.0.0
	 */
	public function get_name() {
		return __( 'List Capabilities', 'agenistrator' );
	}

	/**
	 * Get the tool description.
	 *
	 * @return string The tool description.
	 * @since     1.0.0
	 */
	public function get_description() {
		return 'List all known capabilities registered in the system across all roles.';
	}

	/**
	 * Get the parameters schema for this tool.
	 *
	 * @return array Parameters schema in JSON Schema format.
	 * @since     1.0.0
	 */
	public function get_parameters() {
		return array(
			'type'       => 'object',
			'properties' => array(
				'group_by_category' => array(
					'type'        => 'boolean',
					'description' => 'Whether to group capabilities by category (posts, pages, users, etc.)',
					'default'     => false,
				),
				'limit'             => array(
					'type'        => 'integer',
					'description' => 'Maximum number of capabilities to return. Default: 100.',
				),
				'offset'            => array(
					'type'        => 'integer',
					'description' => 'Number of capabilities to skip before returning results. Default: 0.',
				),
			),
			'required'   => array(),
		);
	}

	/**
	 * Check if the current user can execute this tool.
	 *
	 * @return bool True if the current user has permission.
	 * @since     1.0.0
	 */
	public function current_user_can_execute() {
		return current_user_can( 'list_users' );
	}

	/**
	 * Check if this tool is read-only.
	 *
	 * @return bool True if the tool only reads data.
	 * @since     1.0.0
	 */
	public function is_read_only() {
		return true;
	}

	/**
	 * Execute the tool with the given arguments.
	 *
	 * @param array $args The tool arguments.
	 *
	 * @return array The tool execution result.
	 * @since     1.0.0
	 */
	protected function execute( $args ) {
		$wp_roles         = wp_roles();
		$all_capabilities = array();

		// Collect all capabilities from all roles
		foreach ( $wp_roles->roles as $role_data ) {
			foreach ( array_keys( $role_data['capabilities'] ) as $cap ) {
				$all_capabilities[ $cap ] = true;
			}
		}

		$capabilities = array_keys( $all_capabilities );
		sort( $capabilities );

		$group_by_category = isset( $args['group_by_category'] ) && $args['group_by_category'];
		$limit             = max( 1, $args['limit'] ?? 100 );
		$offset            = max( 0, $args['offset'] ?? 0 );

		if ( $group_by_category ) {
			$grouped = $this->group_capabilities( $capabilities );
			// Note: Pagination doesn't apply to grouped view as structure is different
			return $this->success_response(
				'Capabilities retrieved successfully',
				array(
					'grouped_capabilities' => $grouped,
					'total'                => count( $capabilities ),
					'limit'                => $limit,
					'offset'               => $offset,
					'has_more'             => false,
				)
			);
		}

		// Apply pagination to flat list
		$total     = count( $capabilities );
		$paginated = array_slice( $capabilities, $offset, $limit );
		$has_more  = $total > ( $offset + $limit );

		return $this->success_response(
			'Capabilities retrieved successfully',
			array(
				'capabilities' => $paginated,
				'count'        => count( $paginated ),
				'total'        => $total,
				'limit'        => $limit,
				'offset'       => $offset,
				'has_more'     => $has_more,
			)
		);
	}

	private function group_capabilities( $capabilities ) {
		$groups = array(
			'posts'    => array(),
			'pages'    => array(),
			'users'    => array(),
			'plugins'  => array(),
			'themes'   => array(),
			'comments' => array(),
			'options'  => array(),
			'files'    => array(),
			'other'    => array(),
		);

		foreach ( $capabilities as $cap ) {
			if ( strpos( $cap, 'post' ) !== false || strpos( $cap, 'publish' ) !== false ) {
				$groups['posts'][] = $cap;
			} elseif ( strpos( $cap, 'page' ) !== false ) {
				$groups['pages'][] = $cap;
			} elseif ( strpos( $cap, 'user' ) !== false || strpos( $cap, 'role' ) !== false ) {
				$groups['users'][] = $cap;
			} elseif ( strpos( $cap, 'plugin' ) !== false ) {
				$groups['plugins'][] = $cap;
			} elseif ( strpos( $cap, 'theme' ) !== false ) {
				$groups['themes'][] = $cap;
			} elseif ( strpos( $cap, 'comment' ) !== false ) {
				$groups['comments'][] = $cap;
			} elseif ( strpos( $cap, 'option' ) !== false ) {
				$groups['options'][] = $cap;
			} elseif ( strpos( $cap, 'file' ) !== false || strpos( $cap, 'upload' ) !== false ) {
				$groups['files'][] = $cap;
			} else {
				$groups['other'][] = $cap;
			}
		}

		return array_filter( $groups );
	}
}
