__( 'Find a setting or feature', 'ai-eshop-optimizer' ), 'description' => __( 'Answer "where do I set up / find X" AND "what does this button do" for anything in Rooster One. Searches every admin destination by label, id, description and live registry terms (courier carriers: ACS, BOX NOW, Courier Center, ELTA, Geniki, Speedex, DHL Express, DHL Paket, FedEx, UPS, USPS, Royal Mail, Colissimo, BRT, Correos Express, Sendcloud; marketplace feeds; order providers) and also every described operator ACTION. Results carry kind=page or kind=action. An action result tells you which screen it is on, whether pressing it emails the customer (informs_customer) and the confirmation question it asks. Use this before answering any "where is", "how do I enable" or "what happens if I click" question, and prefer it to guessing a URL. Never state that a control emails a customer unless informs_customer says so.', 'ai-eshop-optimizer' ), 'category' => \AIEO\Claude\Bootstrap::CATEGORY, 'input_schema' => self::input_schema(), 'output_schema' => array( 'type' => 'object' ), 'execute_callback' => array( __CLASS__, 'execute' ), 'permission_callback' => array( __CLASS__, 'permission_check' ), 'meta' => array( 'annotations' => array( 'readonly' => true, 'idempotent' => true, ), 'show_in_rest' => true, ), ) ); } public static function permission_check( $input = null ) { unset( $input ); return current_user_can( defined( 'AIEO_CAPABILITY' ) ? AIEO_CAPABILITY : 'manage_woocommerce' ); } private static function input_schema() { return array( 'default' => array(), 'type' => 'object', 'properties' => array( 'query' => array( 'type' => 'string', 'description' => __( 'What the operator is looking for — a carrier name, a feature, a noun they used. Any language, accents optional.', 'ai-eshop-optimizer' ), ), 'limit' => array( 'type' => 'integer', 'minimum' => 1, 'maximum' => 25, 'default' => 6, ), ), 'required' => array( 'query' ), ); } private static function action_hits( $needle, $base ) { if ( ! class_exists( '\AIEO_Capability_Registry' ) ) { return array(); } $out = array(); foreach ( \AIEO_Capability_Registry::described_actions() as $row ) { $label = isset( $row['label'] ) ? trim( (string) $row['label'] ) : ''; $page = isset( $row['page'] ) ? (string) $row['page'] : ''; if ( $label === '' || $page === '' ) { continue; } $aid = isset( $row['id'] ) ? (string) $row['id'] : ''; $desc = isset( $row['description'] ) ? (string) $row['description'] : ''; $ajax = isset( $row['ajax'] ) ? (string) $row['ajax'] : ''; $from_id = str_replace( array( '_', '-', '.' ), ' ', $aid ); $haystack = self::fold( $label . ' ' . $from_id . ' ' . $desc . ' ' . $ajax ); if ( strpos( $haystack, $needle ) === false ) { continue; } $score = 15; if ( strpos( self::fold( $label ), $needle ) !== false ) { $score = 90; } elseif ( strpos( self::fold( $from_id ), $needle ) !== false ) { $score = 70; } elseif ( strpos( self::fold( $desc ), $needle ) !== false ) { $score = 35; } $tier = 'free'; if ( class_exists( '\AIEO_Capability_Registry' ) ) { $resolved = \AIEO_Capability_Registry::tier_for( $page, self::group_of( $page ) ); $tier = $resolved['tier']; } $out[] = array( 'id' => $aid, 'label' => $label, 'kind' => 'action', 'description' => $desc, 'url' => $base . '&dmm_tab=' . rawurlencode( $page ), 'on_page' => $page, 'tier' => $tier, 'score' => $score, 'informs_customer' => ! empty( $row['informs_customer'] ), 'confirm' => isset( $row['confirm'] ) ? (string) $row['confirm'] : '', ); } return $out; } public static function execute( $input ) { $input = is_array( $input ) ? $input : array(); $query = isset( $input['query'] ) ? trim( (string) $input['query'] ) : ''; $limit = isset( $input['limit'] ) ? max( 1, min( 25, (int) $input['limit'] ) ) : 6; if ( $query === '' ) { return new \WP_Error( 'aieo_bad_input', __( 'Give me something to look for.', 'ai-eshop-optimizer' ) ); } if ( ! class_exists( 'AIEO_DMM' ) ) { return new \WP_Error( 'aieo_unavailable', __( 'AIEO_DMM not loaded.', 'ai-eshop-optimizer' ) ); } $needle = self::fold( $query ); $base = admin_url( 'admin.php?page=' . \AIEO_DMM::MENU_SLUG ); $hits = array(); foreach ( (array) \AIEO_DMM::instance()->get_subtabs() as $tab ) { $id = isset( $tab['id'] ) ? (string) $tab['id'] : ''; $label = isset( $tab['label'] ) ? (string) $tab['label'] : ''; if ( $id === '' ) { continue; } $desc = class_exists( 'AIEO_Menu_Descriptions' ) ? (string) \AIEO_Menu_Descriptions::for_subtab( $id ) : ''; $terms = ''; if ( class_exists( 'AIEO_Welcome_Search_Index' ) ) { $terms = (string) \AIEO_Welcome_Search_Index::terms_for( $id ); } $from_id = str_replace( array( '_', '-' ), ' ', $id ); $haystack = self::fold( $label . ' ' . $from_id . ' ' . $desc . ' ' . $terms ); if ( strpos( $haystack, $needle ) === false ) { continue; } $score = 20; if ( strpos( self::fold( $label ), $needle ) !== false ) { $score = 100; } elseif ( strpos( self::fold( $from_id ), $needle ) !== false ) { $score = 80; } elseif ( strpos( self::fold( $desc ), $needle ) !== false ) { $score = 40; } $tier = 'free'; if ( class_exists( 'AIEO_Capability_Registry' ) ) { $resolved = \AIEO_Capability_Registry::tier_for( $id, self::group_of( $id ) ); $tier = $resolved['tier']; } $hits[] = array( 'id' => $id, 'label' => $label, 'kind' => 'page', 'description' => $desc, 'url' => $base . '&dmm_tab=' . rawurlencode( $id ), 'tier' => $tier, 'score' => $score, ); } foreach ( self::action_hits( $needle, $base ) as $hit ) { $hits[] = $hit; } usort( $hits, static function ( $a, $b ) { if ( $a['score'] === $b['score'] ) { return strcmp( $a['label'], $b['label'] ); } return $b['score'] - $a['score']; } ); $total = count( $hits ); $hits = array_slice( $hits, 0, $limit ); return array( 'query' => $query, 'matches' => $hits, 'total' => $total, 'truncated' => $total > count( $hits ), 'site_tier' => class_exists( 'AIEO_Capability_Registry' ) ? \AIEO_Capability_Registry::site_tier() : 'free', 'note' => $total === 0 ? __( 'Nothing in the admin index matches. Say so plainly rather than guessing a URL — the feature may not exist, or may live in WooCommerce or WordPress core rather than in Rooster One.', 'ai-eshop-optimizer' ) : '', ); } private static function group_of( $id ) { if ( ! class_exists( 'AIEO_DMM' ) ) { return ''; } foreach ( (array) \AIEO_DMM::instance()->get_subtabs() as $tab ) { if ( isset( $tab['id'] ) && (string) $tab['id'] === (string) $id ) { return isset( $tab['group'] ) ? (string) $tab['group'] : ''; } } return ''; } private static function fold( $s ) { $s = (string) $s; $s = function_exists( 'mb_strtolower' ) ? mb_strtolower( $s, 'UTF-8' ) : strtolower( $s ); if ( class_exists( 'AIEO_DMM' ) && method_exists( 'AIEO_DMM', 'load_search_index' ) && \AIEO_DMM::load_search_index() ) { return \AIEO_Welcome_Search_Index::fold( $s ); } return $s; } }