PluginProbe
Jetpack – WP Security, Backup, Speed, & Growth / 16.3
Jetpack – WP Security, Backup, Speed, & Growth v16.3
16.3 16.3-beta 16.3-a.5 16.3-a.7 16.3-a.3 16.3-a.1 16.2 16.2-beta 12.0.3 12.1.3 12.2.3 12.3.2 12.4.2 12.5.2 12.6.4 12.7.3 12.8.3 12.9.5 13.0.2 13.1.5 13.2.4 13.3.3 13.4.5 13.5.2 13.6.2 All 508 releases
← All changes | jetpack_vendor/automattic/jetpack-search/src/class-plan.php +189 -0 16.2-beta → 16.3 View file →
@@ -1,0 +1,189 @@
1 +<?php
2 +/**
3 + * The Search Plan class.
4 + * Registers the REST routes for Search.
5 + *
6 + * @package automattic/jetpack-search
7 + */
8 +
9 +namespace Automattic\Jetpack\Search;
10 +
11 +use Automattic\Jetpack\Connection\Client;
12 +use Jetpack_Options;
13 +use WP_Error;
14 +
15 +if ( ! defined( 'ABSPATH' ) ) {
16 + exit( 0 );
17 +}
18 +
19 +/**
20 + * Registers the REST routes for Search.
21 + */
22 +class Plan {
23 + const JETPACK_SEARCH_PLAN_INFO_OPTION_KEY = 'jetpack_search_plan_info';
24 + const JETPACK_SEARCH_EVER_SUPPORTED_SEARCH = 'jetpack_search_ever_supported_search';
25 +
26 + // The pricing update starting from August 2022.
27 + const JETPACK_SEARCH_NEW_PRICING_VERSION = '202208';
28 + const JETPACK_SEARCH_FREE_PRODUCT_SLUG = 'jetpack_search_free';
29 +
30 + /**
31 + * Whether we have hooked the actions.
32 + *
33 + * @var boolean
34 + */
35 + protected static $update_plan_hook_initialized = false;
36 +
37 + /**
38 + * Init hooks for updating plan info
39 + */
40 + public function init_hooks() {
41 + // Update plan info from WPCOM on Jetpack heartbeat.
42 + // TODO: implement heartbeart for search.
43 + if ( ! static::$update_plan_hook_initialized ) {
44 + add_action( 'jetpack_heartbeat', array( $this, 'get_plan_info_from_wpcom' ) );
45 + static::$update_plan_hook_initialized = true;
46 + }
47 + }
48 +
49 + /**
50 + * Refresh plan info stored in options
51 + */
52 + public function get_plan_info_from_wpcom() {
53 + $blog_id = Jetpack_Options::get_option( 'id' );
54 + // An unregistered site (or a stale cache view hiding the registration) has no
55 + // blog ID: bail rather than requesting the malformed `/sites//…` path.
56 + if ( ! $blog_id ) {
57 + return new WP_Error( 'site_not_registered', 'Site not registered.' );
58 + }
59 + $response = Client::wpcom_json_api_request_as_blog(
60 + '/sites/' . $blog_id . '/jetpack-search/plan',
61 + '2',
62 + array(),
63 + null,
64 + 'wpcom'
65 + );
66 +
67 + // store plan in options.
68 + $this->update_search_plan_info( $response );
69 +
70 + return $response;
71 + }
72 +
73 + /**
74 + * Get plan info.
75 + *
76 + * @param bool $force_refresh - Default to false. Set true to load from WPCOM.
77 + */
78 + public function get_plan_info( $force_refresh = false ) {
79 + if ( $force_refresh ) {
80 + $this->get_plan_info_from_wpcom();
81 + }
82 + $plan_info = get_option( self::JETPACK_SEARCH_PLAN_INFO_OPTION_KEY );
83 + if ( false === $plan_info && ! $force_refresh ) {
84 + $plan_info = $this->get_plan_info( true );
85 + }
86 + return $plan_info;
87 + }
88 +
89 + /**
90 + * Please use `supports_instant_search` instead.
91 + *
92 + * @deprecated
93 + */
94 + public function has_jetpack_search_product() {
95 + return (bool) get_option( 'has_jetpack_search_product' );
96 + }
97 +
98 + /**
99 + * Returns true if plan supports Instant Search.
100 + */
101 + public function supports_instant_search() {
102 + $plan_info = $this->get_plan_info();
103 + return ( isset( $plan_info['supports_instant_search'] ) && $plan_info['supports_instant_search'] );
104 + }
105 +
106 + /**
107 + * Returns true if the plan support either Instant Search or Classic Search.
108 + */
109 + public function supports_search() {
110 + $plan_info = $this->get_plan_info();
111 + return ( isset( $plan_info['supports_search'] ) && $plan_info['supports_search'] );
112 + }
113 +
114 + /**
115 + * Returns true if the plan usage is exceeded and search should no longer work.
116 + */
117 + public function must_upgrade() {
118 + $plan_info = $this->get_plan_info();
119 + return isset( $plan_info['plan_usage']['must_upgrade'] ) && $plan_info['plan_usage']['must_upgrade'];
120 + }
121 +
122 + /**
123 + * Returns true if the plan only supports Classic Search.
124 + */
125 + public function supports_only_classic_search() {
126 + $plan_info = $this->get_plan_info();
127 + return isset( $plan_info['supports_only_classic_search'] ) && $plan_info['supports_only_classic_search'];
128 + }
129 +
130 + /**
131 + * Whether the plan(s) ever supported search.
132 + */
133 + public function ever_supported_search() {
134 + return (bool) get_option( self::JETPACK_SEARCH_EVER_SUPPORTED_SEARCH ) || $this->supports_search();
135 + }
136 +
137 + /**
138 + * Returns true if the site is on free plan.
139 + */
140 + public function is_free_plan() {
141 + $plan_info = $this->get_plan_info();
142 + return Helper::is_forced_free_plan() || ( isset( $plan_info['effective_subscription']['product_slug'] ) && $plan_info['effective_subscription']['product_slug'] === self::JETPACK_SEARCH_FREE_PRODUCT_SLUG );
143 + }
144 +
145 + /**
146 + * Update `has_jetpack_search_product` regarding the plan information
147 + *
148 + * @param array|WP_Error $response - Resopnse from WPCOM.
149 + * @return bool - true on success, false on failure.
150 + */
151 + public function update_search_plan_info( $response ) {
152 + if ( is_wp_error( $response ) ) {
153 + return false;
154 + }
155 + $body = json_decode( wp_remote_retrieve_body( $response ), true );
156 + $status_code = wp_remote_retrieve_response_code( $response );
157 +
158 + if ( 200 !== $status_code ) {
159 + return false;
160 + }
161 +
162 + return $this->set_plan_options( $body );
163 + }
164 +
165 + /**
166 + * Set plan info to options table
167 + *
168 + * @param array $plan_info - the decoded plan info array.
169 + */
170 + public function set_plan_options( $plan_info ) {
171 + if ( isset( $plan_info['swap_classic_to_inline_search'] ) && is_bool( $plan_info['swap_classic_to_inline_search'] ) ) {
172 + update_option( Module_Control::SEARCH_MODULE_SWAP_CLASSIC_TO_INLINE_OPTION_KEY, (bool) $plan_info['swap_classic_to_inline_search'] );
173 + }
174 + if ( ! isset( $plan_info['supports_instant_search'] ) ) {
175 + return false;
176 + }
177 + // set option whether has Jetpack Search plan for capability reason.
178 + if ( get_option( 'has_jetpack_search_product' ) !== (bool) $plan_info['supports_instant_search'] ) {
179 + update_option( 'has_jetpack_search_product', (bool) $plan_info['supports_instant_search'] );
180 + }
181 + // We use this option to determine the visibility of search submenu.
182 + // If the site ever had search subscription, then we record it and show the menu after.
183 + if ( $plan_info['supports_instant_search'] ) {
184 + update_option( self::JETPACK_SEARCH_EVER_SUPPORTED_SEARCH, true, false );
185 + }
186 + update_option( self::JETPACK_SEARCH_PLAN_INFO_OPTION_KEY, $plan_info );
187 + return true;
188 + }
189 +}