Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
98.99% covered (success)
98.99%
196 / 198
92.31% covered (success)
92.31%
12 / 13
CRAP
0.00% covered (danger)
0.00%
0 / 1
Boost
99.49% covered (success)
99.49%
195 / 196
92.31% covered (success)
92.31%
12 / 13
15
0.00% covered (danger)
0.00%
0 / 1
 get_name
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 get_title
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 get_description
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 get_long_description
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 get_features
100.00% covered (success)
100.00%
5 / 5
100.00% covered (success)
100.00%
1 / 1
1
 get_tiers
100.00% covered (success)
100.00%
4 / 4
100.00% covered (success)
100.00%
1 / 1
1
 get_features_by_tier
100.00% covered (success)
100.00%
155 / 155
100.00% covered (success)
100.00%
1 / 1
1
 get_post_checkout_url
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 get_pricing_for_ui
100.00% covered (success)
100.00%
15 / 15
100.00% covered (success)
100.00%
1 / 1
1
 get_manage_url
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 do_product_specific_activation
80.00% covered (warning)
80.00%
4 / 5
0.00% covered (danger)
0.00%
0 / 1
3.07
 get_paid_plan_product_slugs
100.00% covered (success)
100.00%
5 / 5
100.00% covered (success)
100.00%
1 / 1
1
 is_upgradable_by_bundle
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
1<?php
2/**
3 * Boost product
4 *
5 * @package my-jetpack
6 */
7
8namespace Automattic\Jetpack\My_Jetpack\Products;
9
10use Automattic\Jetpack\My_Jetpack\Product;
11use Automattic\Jetpack\My_Jetpack\Wpcom_Products;
12use WP_Error;
13
14if ( ! defined( 'ABSPATH' ) ) {
15    exit( 0 );
16}
17
18/**
19 * Class responsible for handling the Boost product
20 */
21class Boost extends Product {
22
23    const FREE_TIER_SLUG             = 'free';
24    const UPGRADED_TIER_SLUG         = 'upgraded';
25    const UPGRADED_TIER_PRODUCT_SLUG = 'jetpack_boost_yearly';
26
27    /**
28     * The product slug
29     *
30     * @var string
31     */
32    public static $slug = 'boost';
33
34    /**
35     * The filename (id) of the plugin associated with this product.
36     *
37     * @var string
38     */
39    public static $plugin_filename = array(
40        'jetpack-boost/jetpack-boost.php',
41        'boost/jetpack-boost.php',
42        'jetpack-boost-dev/jetpack-boost.php',
43    );
44    /**
45     * The slug of the plugin associated with this product.
46     *
47     * @var string
48     */
49    public static $plugin_slug = 'jetpack-boost';
50
51    /**
52     * The category of the product
53     *
54     * @var string
55     */
56    public static $category = 'performance';
57
58    /**
59     * Boost has a standalone plugin
60     *
61     * @var bool
62     */
63    public static $has_standalone_plugin = true;
64
65    /**
66     * Whether this product requires a user connection
67     *
68     * @var string
69     */
70    public static $requires_user_connection = false;
71
72    /**
73     * Whether this product has a free offering
74     *
75     * @var bool
76     */
77    public static $has_free_offering = true;
78
79    /**
80     * The feature slug that identifies the paid plan
81     *
82     * @var string
83     */
84    public static $feature_identifying_paid_plan = 'cloud-critical-css';
85
86    /**
87     * Get the product name
88     *
89     * @return string
90     */
91    public static function get_name() {
92        return 'Boost';
93    }
94
95    /**
96     * Get the product title
97     *
98     * @return string
99     */
100    public static function get_title() {
101        return 'Jetpack Boost';
102    }
103
104    /**
105     * Get the internationalized product description
106     *
107     * @return string
108     */
109    public static function get_description() {
110        return __( 'Improves your site speed and performance.', 'jetpack-my-jetpack' );
111    }
112
113    /**
114     * Get the internationalized product long description
115     *
116     * @return string
117     */
118    public static function get_long_description() {
119        return __( 'Fast sites get more page visits, more conversions, and better SEO rankings. Boost speeds up your site in seconds.', 'jetpack-my-jetpack' );
120    }
121
122    /**
123     * Get the internationalized features list
124     *
125     * @return array Boost features list
126     */
127    public static function get_features() {
128        return array(
129            __( 'Check your site performance', 'jetpack-my-jetpack' ),
130            __( 'Enable improvements in one click', 'jetpack-my-jetpack' ),
131            __( 'Standalone free plugin for those focused on speed', 'jetpack-my-jetpack' ),
132        );
133    }
134
135    /**
136     * Get the product's available tiers
137     *
138     * @return string[] Slugs of the available tiers
139     */
140    public static function get_tiers() {
141        return array(
142            self::UPGRADED_TIER_SLUG,
143            self::FREE_TIER_SLUG,
144        );
145    }
146
147    /**
148     * Get the internationalized comparison of free vs upgraded features
149     *
150     * The Jetpack Boost plugin calls this for its own pricing table.
151     *
152     * @return array[] Boost features comparison
153     */
154    public static function get_features_by_tier() {
155        return array(
156            array(
157                'name'  => __( 'Auto CSS Optimization', 'jetpack-my-jetpack' ),
158                'info'  => array(
159                    'content' => __(
160                        'Move important styling information to the start of the page, which helps pages display your content sooner, so your users don’t have to wait for the entire page to load. Commonly referred to as Critical CSS.',
161                        'jetpack-my-jetpack'
162                    ),
163                ),
164                'tiers' => array(
165                    self::FREE_TIER_SLUG     => array(
166                        'included'    => false,
167                        'description' => __( 'Manual', 'jetpack-my-jetpack' ),
168                        'info'        => array(
169                            'title'   => __( 'Manual Critical CSS regeneration', 'jetpack-my-jetpack' ),
170                            'content' => __(
171                                '<p>To enhance the speed of your site, with this plan you will need to optimize CSS by using the Manual Critical CSS generation feature whenever you:</p>
172                                <ul>
173                                    <li>Make theme changes.</li>
174                                    <li>Write a new post/page.</li>
175                                    <li>Edit a post/page.</li>
176                                    <li>Activate, deactivate, or update plugins that impact your site layout or HTML structure.</li>
177                                    <li>Change settings of plugins that impact your site layout or HTML structure.</li>
178                                    <li>Upgrade your WordPress version if the new release includes core CSS changes.</li>
179                                </ul>',
180                                'jetpack-my-jetpack'
181                            ),
182                        ),
183                    ),
184                    self::UPGRADED_TIER_SLUG => array(
185                        'included'    => true,
186                        'description' => __( 'Included', 'jetpack-my-jetpack' ),
187                        'info'        => array(
188                            'title'   => __( 'Automatic Critical CSS regeneration', 'jetpack-my-jetpack' ),
189                            'content' => __(
190                                '<p>It’s essential to regenerate Critical CSS to optimize your site speed whenever your HTML or CSS structure changes. Being on top of this can be tedious and time-consuming.</p>
191                                 <p>Boost’s cloud service can automatically detect when your site needs the Critical CSS regenerated, and perform this function behind the scenes without requiring you to monitor it manually.</p>',
192                                'jetpack-my-jetpack'
193                            ),
194                        ),
195                    ),
196                ),
197            ),
198            array(
199                'name'  => __( 'Historical performance scores', 'jetpack-my-jetpack' ),
200                'info'  => array(
201                    'content' => __(
202                        'Get access to your historical performance scores and see advanced Core Web Vitals data.',
203                        'jetpack-my-jetpack'
204                    ),
205                ),
206                'tiers' => array(
207                    self::FREE_TIER_SLUG     => array( 'included' => false ),
208                    self::UPGRADED_TIER_SLUG => array( 'included' => true ),
209                ),
210            ),
211            array(
212                'name'  => __( 'Dedicated email support', 'jetpack-my-jetpack' ),
213                'info'  => array(
214                    'content' => __(
215                        '<p>Paid customers get dedicated email support from our world-class Happiness Engineers to help with any issue.</p>
216                         <p>All other questions are handled by our team as quickly as we are able to go through the WordPress support forum.</p>',
217                        'jetpack-my-jetpack'
218                    ),
219                ),
220                'tiers' => array(
221                    self::FREE_TIER_SLUG     => array( 'included' => false ),
222                    self::UPGRADED_TIER_SLUG => array( 'included' => true ),
223                ),
224            ),
225            array(
226                'name'  => __( 'Page Cache', 'jetpack-my-jetpack' ),
227                'info'  => array(
228                    'content' => __(
229                        'Page caching speeds up load times by storing a copy of each web page on the first visit, allowing subsequent visits to be served instantly. This reduces server load and improves user experience by delivering content faster, without waiting for the page to be generated again.',
230                        'jetpack-my-jetpack'
231                    ),
232                ),
233                'tiers' => array(
234                    self::FREE_TIER_SLUG     => array( 'included' => true ),
235                    self::UPGRADED_TIER_SLUG => array( 'included' => true ),
236                ),
237            ),
238            array(
239                'name'  => __( 'Image CDN Quality Settings', 'jetpack-my-jetpack' ),
240                'info'  => array(
241                    'content' => __(
242                        'Fine-tune image quality settings to your liking.',
243                        'jetpack-my-jetpack'
244                    ),
245                ),
246                'tiers' => array(
247                    self::FREE_TIER_SLUG     => array( 'included' => false ),
248                    self::UPGRADED_TIER_SLUG => array( 'included' => true ),
249                ),
250            ),
251            array(
252                'name'  => __( 'Image CDN Auto-Resize Lazy Images', 'jetpack-my-jetpack' ),
253                'info'  => array(
254                    'content' => __(
255                        'Optimizes lazy-loaded images by dynamically serving perfectly sized images for each device.',
256                        'jetpack-my-jetpack'
257                    ),
258                ),
259                'tiers' => array(
260                    self::FREE_TIER_SLUG     => array( 'included' => false ),
261                    self::UPGRADED_TIER_SLUG => array( 'included' => true ),
262                ),
263            ),
264            array(
265                'name'  => __( 'Image CDN', 'jetpack-my-jetpack' ),
266                'info'  => array(
267                    'content' => __(
268                        'Deliver images from Jetpack\'s Content Delivery Network. Automatically resizes your images to an appropriate size, converts them to modern efficient formats like WebP, and serves them from a worldwide network of servers.',
269                        'jetpack-my-jetpack'
270                    ),
271                ),
272                'tiers' => array(
273                    self::FREE_TIER_SLUG     => array( 'included' => true ),
274                    self::UPGRADED_TIER_SLUG => array( 'included' => true ),
275                ),
276            ),
277            array(
278                'name'  => __( 'Image guide', 'jetpack-my-jetpack' ),
279                'info'  => array(
280                    'content' => __(
281                        'Discover and fix images with a suboptimal resolution, aspect ratio, or file size, improving user experience and page speed.',
282                        'jetpack-my-jetpack'
283                    ),
284                ),
285                'tiers' => array(
286                    self::FREE_TIER_SLUG     => array( 'included' => true ),
287                    self::UPGRADED_TIER_SLUG => array( 'included' => true ),
288                ),
289            ),
290            array(
291                'name'  => __( 'Defer non-essential JavaScript', 'jetpack-my-jetpack' ),
292                'info'  => array(
293                    'content' => __(
294                        'Run non-essential JavaScript after the page has loaded so that styles and images can load more quickly.',
295                        'jetpack-my-jetpack'
296                    ),
297                ),
298                'tiers' => array(
299                    self::FREE_TIER_SLUG     => array( 'included' => true ),
300                    self::UPGRADED_TIER_SLUG => array( 'included' => true ),
301                ),
302            ),
303            array(
304                'name'  => __( 'Concatenate JS and CSS', 'jetpack-my-jetpack' ),
305                'info'  => array(
306                    'content' => __(
307                        'Boost your website performance by merging and compressing JavaScript and CSS files, reducing site loading time and number of requests.',
308                        'jetpack-my-jetpack'
309                    ),
310                ),
311                'tiers' => array(
312                    self::FREE_TIER_SLUG     => array( 'included' => true ),
313                    self::UPGRADED_TIER_SLUG => array( 'included' => true ),
314                ),
315            ),
316        );
317    }
318
319    /**
320     * Get the URL the user is taken after purchasing the product through the checkout
321     *
322     * @return ?string
323     */
324    public static function get_post_checkout_url() {
325        return self::get_manage_url();
326    }
327
328    /**
329     * Get the product princing details
330     *
331     * @return array Pricing details
332     */
333    public static function get_pricing_for_ui() {
334        return array(
335            'tiers' => array(
336                self::FREE_TIER_SLUG     => array(
337                    'available' => true,
338                    'is_free'   => true,
339                ),
340                self::UPGRADED_TIER_SLUG => array_merge(
341                    array(
342                        'available'          => true,
343                        'wpcom_product_slug' => self::UPGRADED_TIER_PRODUCT_SLUG,
344                    ),
345                    Wpcom_Products::get_product_pricing( self::UPGRADED_TIER_PRODUCT_SLUG )
346                ),
347            ),
348        );
349    }
350
351    /**
352     * Get the URL where the user manages the product
353     *
354     * @return ?string
355     */
356    public static function get_manage_url() {
357        return admin_url( 'admin.php?page=jetpack-boost' );
358    }
359
360    /**
361     * Activates the product by installing and activating its plugin
362     *
363     * @param bool|WP_Error $current_result Is the result of the top level activation actions. You probably won't do anything if it is an WP_Error.
364     * @return boolean|WP_Error
365     */
366    public static function do_product_specific_activation( $current_result ) {
367
368        $product_activation = parent::do_product_specific_activation( $current_result );
369
370        if ( is_wp_error( $product_activation ) && 'module_activation_failed' === $product_activation->get_error_code() ) {
371            // A bundle is not a module. There's nothing in the plugin to be activated, so it's ok to fail to activate the module.
372            $product_activation = true;
373        }
374
375        // We just "got started" in My Jetpack, so skip the in-plugin experience.
376        update_option( 'jb_get_started', false );
377
378        return $product_activation;
379    }
380
381    /**
382     * Get the product-slugs of the paid plans for this product.
383     * (Do not include bundle plans, unless it's a bundle plan itself).
384     *
385     * @return array
386     */
387    public static function get_paid_plan_product_slugs() {
388        return array(
389            'jetpack_boost_yearly',
390            'jetpack_boost_monthly',
391            'jetpack_boost_bi_yearly',
392        );
393    }
394
395    /**
396     * Return product bundles list
397     * that supports the product.
398     *
399     * @return boolean|array Products bundle list.
400     */
401    public static function is_upgradable_by_bundle() {
402        return array( 'complete' );
403    }
404}