From 677416fcf2066b7913ce58521a89ca6eceadca58 Mon Sep 17 00:00:00 2001 From: Nima Date: Wed, 28 Dec 2022 13:25:51 +0000 Subject: [PATCH] Add `marketing/recommendations` API --- plugins/woocommerce/src/Admin/API/Init.php | 1 + .../Admin/API/MarketingRecommendations.php | 235 ++++++++++++++++++ 2 files changed, 236 insertions(+) create mode 100644 plugins/woocommerce/src/Admin/API/MarketingRecommendations.php diff --git a/plugins/woocommerce/src/Admin/API/Init.php b/plugins/woocommerce/src/Admin/API/Init.php index 42b2bac82e7..45ef28bd4b9 100644 --- a/plugins/woocommerce/src/Admin/API/Init.php +++ b/plugins/woocommerce/src/Admin/API/Init.php @@ -64,6 +64,7 @@ class Init { 'Automattic\WooCommerce\Admin\API\Experiments', 'Automattic\WooCommerce\Admin\API\Marketing', 'Automattic\WooCommerce\Admin\API\MarketingOverview', + 'Automattic\WooCommerce\Admin\API\MarketingRecommendations', 'Automattic\WooCommerce\Admin\API\Options', 'Automattic\WooCommerce\Admin\API\Orders', 'Automattic\WooCommerce\Admin\API\PaymentGatewaySuggestions', diff --git a/plugins/woocommerce/src/Admin/API/MarketingRecommendations.php b/plugins/woocommerce/src/Admin/API/MarketingRecommendations.php new file mode 100644 index 00000000000..a64fcce02d7 --- /dev/null +++ b/plugins/woocommerce/src/Admin/API/MarketingRecommendations.php @@ -0,0 +1,235 @@ +namespace, + '/' . $this->rest_base, + [ + [ + 'methods' => \WP_REST_Server::READABLE, + 'callback' => [ $this, 'get_items' ], + 'permission_callback' => [ $this, 'get_items_permissions_check' ], + 'args' => [ + 'category' => [ + 'type' => 'string', + 'validate_callback' => 'rest_validate_request_arg', + 'sanitize_callback' => 'sanitize_title_with_dashes', + 'enum' => [ 'channels', 'extensions' ], + 'required' => true, + ], + ], + ], + 'schema' => [ $this, 'get_public_item_schema' ], + ] + ); + } + + /** + * Check whether a given request has permission to view marketing recommendations. + * + * @param WP_REST_Request $request Full details about the request. + * + * @return WP_Error|boolean + */ + public function get_items_permissions_check( $request ) { + if ( ! current_user_can( 'install_plugins' ) ) { + return new WP_Error( 'woocommerce_rest_cannot_view', __( 'Sorry, you cannot view marketing channels.', 'woocommerce' ), array( 'status' => 400 ) ); + } + + return true; + } + + /** + * Retrieves a collection of recommendations. + * + * @param WP_REST_Request $request Full details about the request. + * + * @return WP_REST_Response|WP_Error Response object on success, or WP_Error object on failure. + */ + public function get_items( $request ) { + /** + * MarketingSpecs class. + * + * @var MarketingSpecs $marketing_specs + */ + $marketing_specs = wc_get_container()->get( MarketingSpecs::class ); + + $category = $request->get_param( 'category' ); + if ( 'channels' === $category ) { + $items = $marketing_specs->get_recommended_marketing_channels(); + } elseif ( 'extensions' === $category ) { + $items = $marketing_specs->get_recommended_marketing_extensions_excluding_channels(); + } else { + return new WP_Error( 'woocommerce_rest_invalid_category', __( 'The specified category for recommendations is invalid. Allowed values: "channels", "extensions".', 'woocommerce' ), array( 'status' => 400 ) ); + } + + $responses = []; + foreach ( $items as $item ) { + $response = $this->prepare_item_for_response( $item, $request ); + $responses[] = $this->prepare_response_for_collection( $response ); + } + + return rest_ensure_response( $responses ); + } + + /** + * Prepares the item for the REST response. + * + * @param array $item WordPress representation of the item. + * @param WP_REST_Request $request Request object. + * + * @return WP_REST_Response|WP_Error Response object on success, or WP_Error object on failure. + */ + public function prepare_item_for_response( $item, $request ) { + $context = ! empty( $request['context'] ) ? $request['context'] : 'view'; + $data = $this->add_additional_fields_to_object( $item, $request ); + $data = $this->filter_response_by_context( $data, $context ); + + return rest_ensure_response( $data ); + } + + /** + * Retrieves the item's schema, conforming to JSON Schema. + * + * @return array Item schema data. + */ + public function get_item_schema() { + $schema = [ + '$schema' => 'http://json-schema.org/draft-04/schema#', + 'title' => 'marketing_recommendation', + 'type' => 'object', + 'properties' => [ + 'title' => [ + 'type' => 'string', + 'context' => [ 'view' ], + 'readonly' => true, + ], + 'description' => [ + 'type' => 'string', + 'context' => [ 'view' ], + 'readonly' => true, + ], + 'url' => [ + 'type' => 'string', + 'context' => [ 'view' ], + 'readonly' => true, + ], + 'direct_install' => [ + 'type' => 'string', + 'context' => [ 'view' ], + 'readonly' => true, + ], + 'icon' => [ + 'type' => 'string', + 'context' => [ 'view' ], + 'readonly' => true, + ], + 'product' => [ + 'type' => 'string', + 'context' => [ 'view' ], + 'readonly' => true, + ], + 'plugin' => [ + 'type' => 'string', + 'context' => [ 'view' ], + 'readonly' => true, + ], + 'categories' => [ + 'type' => 'array', + 'context' => [ 'view' ], + 'readonly' => true, + 'items' => [ + 'type' => 'string', + ], + ], + 'subcategories' => [ + 'type' => 'array', + 'context' => [ 'view' ], + 'readonly' => true, + 'items' => [ + 'type' => 'object', + 'context' => [ 'view' ], + 'readonly' => true, + 'properties' => [ + 'slug' => [ + 'type' => 'string', + 'context' => [ 'view' ], + 'readonly' => true, + ], + 'name' => [ + 'type' => 'string', + 'context' => [ 'view' ], + 'readonly' => true, + ], + ], + ], + ], + 'tags' => [ + 'type' => 'array', + 'context' => [ 'view' ], + 'readonly' => true, + 'items' => [ + 'type' => 'object', + 'context' => [ 'view' ], + 'readonly' => true, + 'properties' => [ + 'slug' => [ + 'type' => 'string', + 'context' => [ 'view' ], + 'readonly' => true, + ], + 'name' => [ + 'type' => 'string', + 'context' => [ 'view' ], + 'readonly' => true, + ], + ], + ], + ], + ], + ]; + + return $this->add_additional_fields_schema( $schema ); + } +}