/**
  * Retrieve the current event queue
  *
  * @subcommand get-queue
  */
 public function get_queue($args, $assoc_args)
 {
     // Build and make request
     $queue_request = new \WP_REST_Request('POST', '/' . \Automattic\WP\Cron_Control\REST_API::API_NAMESPACE . '/' . \Automattic\WP\Cron_Control\REST_API::ENDPOINT_LIST);
     $queue_request->add_header('Content-Type', 'application/json');
     $queue_request->set_body(wp_json_encode(array('secret' => \WP_CRON_CONTROL_SECRET)));
     $queue_request = rest_do_request($queue_request);
     // Oh well
     if ($queue_request->is_error()) {
         \WP_CLI::error($queue_request->as_error()->get_error_message());
     }
     // Get the decoded JSON object returned by the API
     $queue_response = $queue_request->get_data();
     // No events, nothing more to do
     if (empty($queue_response['events'])) {
         \WP_CLI::warning(__('No events in the current queue', 'automattic-cron-control'));
         return;
     }
     // Prepare items for display
     $events_for_display = $this->format_events($queue_response['events']);
     $total_events_to_display = count($events_for_display);
     \WP_CLI::line(sprintf(_n('Displaying one event', 'Displaying %s events', $total_events_to_display, 'automattic-cron-control'), number_format_i18n($total_events_to_display)));
     // And reformat
     $format = 'table';
     if (isset($assoc_args['format'])) {
         if ('ids' === $assoc_args['format']) {
             \WP_CLI::error(__('Invalid output format requested', 'automattic-cron-control'));
         } else {
             $format = $assoc_args['format'];
         }
     }
     \WP_CLI\Utils\format_items($format, $events_for_display, array('timestamp', 'action', 'instance', 'scheduled_for', 'internal_event', 'schedule_name', 'event_args'));
 }
 function page_admin_scripts()
 {
     if ($this->is_redirecting) {
         return;
         // No need for scripts on a fallback page
     }
     $is_dev_mode = Jetpack::is_development_mode();
     // Enqueue jp.js and localize it
     wp_enqueue_script('react-plugin', plugins_url('_inc/build/admin.js', JETPACK__PLUGIN_FILE), array(), JETPACK__VERSION, true);
     if (!$is_dev_mode) {
         // Required for Analytics
         wp_enqueue_script('jp-tracks', '//stats.wp.com/w.js', array(), gmdate('YW'), true);
     }
     $localeSlug = explode('_', get_locale());
     $localeSlug = $localeSlug[0];
     // Collecting roles that can view site stats
     $stats_roles = array();
     $enabled_roles = function_exists('stats_get_option') ? stats_get_option('roles') : array('administrator');
     foreach (get_editable_roles() as $slug => $role) {
         $stats_roles[$slug] = array('name' => translate_user_role($role['name']), 'canView' => is_array($enabled_roles) ? in_array($slug, $enabled_roles, true) : false);
     }
     $response = rest_do_request(new WP_REST_Request('GET', '/jetpack/v4/module/all'));
     $modules = $response->get_data();
     // Preparing translated fields for JSON encoding by transforming all HTML entities to
     // respective characters.
     foreach ($modules as $slug => $data) {
         $modules[$slug]['name'] = html_entity_decode($data['name']);
         $modules[$slug]['description'] = html_entity_decode($data['description']);
         $modules[$slug]['short_description'] = html_entity_decode($data['short_description']);
         $modules[$slug]['long_description'] = html_entity_decode($data['long_description']);
     }
     // Add objects to be passed to the initial state of the app
     wp_localize_script('react-plugin', 'Initial_State', array('WP_API_root' => esc_url_raw(rest_url()), 'WP_API_nonce' => wp_create_nonce('wp_rest'), 'pluginBaseUrl' => plugins_url('', JETPACK__PLUGIN_FILE), 'connectionStatus' => array('isActive' => Jetpack::is_active(), 'isStaging' => Jetpack::is_staging_site(), 'devMode' => array('isActive' => $is_dev_mode, 'constant' => defined('JETPACK_DEV_DEBUG') && JETPACK_DEV_DEBUG, 'url' => site_url() && false === strpos(site_url(), '.'), 'filter' => apply_filters('jetpack_development_mode', false)), 'isPublic' => '1' == get_option('blog_public'), 'isInIdentityCrisis' => Jetpack::validate_sync_error_idc_option()), 'dismissedNotices' => $this->get_dismissed_jetpack_notices(), 'isDevVersion' => Jetpack::is_development_version(), 'currentVersion' => JETPACK__VERSION, 'happinessGravIds' => jetpack_get_happiness_gravatar_ids(), 'getModules' => $modules, 'showJumpstart' => jetpack_show_jumpstart(), 'rawUrl' => Jetpack::build_raw_urls(get_home_url()), 'adminUrl' => esc_url(admin_url()), 'stats' => array('data' => array('general' => false, 'day' => false, 'week' => false, 'month' => false), 'roles' => $stats_roles), 'settingNames' => array('jetpack_holiday_snow_enabled' => function_exists('jetpack_holiday_snow_option_name') ? jetpack_holiday_snow_option_name() : false), 'userData' => array('currentUser' => jetpack_current_user_data()), 'locale' => $this->get_i18n_data(), 'localeSlug' => $localeSlug, 'jetpackStateNotices' => array('messageCode' => Jetpack::state('message'), 'errorCode' => Jetpack::state('error'), 'errorDescription' => Jetpack::state('error_description')), 'tracksUserData' => Jetpack_Tracks_Client::get_connected_user_tracks_identity(), 'currentIp' => function_exists('jetpack_protect_get_ip') ? jetpack_protect_get_ip() : false));
 }
 /**
  * Delete a single post.
  *
  * @param WP_REST_Request $request Full details about the request.
  * @return WP_REST_Response|WP_Error
  */
 public function delete_item($request)
 {
     $id = (int) $request['id'];
     $force = (bool) $request['force'];
     $post = get_post($id);
     if (empty($id) || empty($post->ID) || $this->post_type !== $post->post_type) {
         return new WP_Error('rest_post_invalid_id', __('Invalid post id.'), array('status' => 404));
     }
     $supports_trash = EMPTY_TRASH_DAYS > 0;
     if ($post->post_type === 'attachment') {
         $supports_trash = $supports_trash && MEDIA_TRASH;
     }
     /**
      * Filter whether a post is trashable.
      *
      * Return false to disable trash support for the post.
      *
      * @param boolean $supports_trash Whether the post type support trashing.
      * @param WP_Post $post           The Post object being considered for trashing support.
      */
     $supports_trash = apply_filters('rest_post_trashable', $supports_trash, $post);
     if (!$this->check_delete_permission($post)) {
         return new WP_Error('rest_user_cannot_delete_post', __('Sorry, you are not allowed to delete this post.'), array('status' => rest_authorization_required_code()));
     }
     $request = new WP_REST_Request('GET', '/wp/v2/' . $this->get_post_type_base($this->post_type) . '/' . $post->ID);
     $request->set_param('context', 'edit');
     $response = rest_do_request($request);
     // If we're forcing, then delete permanently.
     if ($force) {
         $result = wp_delete_post($id, true);
         $status = 'deleted';
     } else {
         // If we don't support trashing for this type, error out.
         if (!$supports_trash) {
             return new WP_Error('rest_trash_not_supported', __('The post does not support trashing.'), array('status' => 501));
         }
         // Otherwise, only trash if we haven't already.
         if ('trash' === $post->post_status) {
             return new WP_Error('rest_already_deleted', __('The post has already been deleted.'), array('status' => 410));
         }
         // (Note that internally this falls through to `wp_delete_post` if
         // the trash is disabled.)
         $result = wp_trash_post($id);
         $status = 'trashed';
     }
     if (!$result) {
         return new WP_Error('rest_cannot_delete', __('The post cannot be deleted.'), array('status' => 500));
     }
     $data = $response->get_data();
     $data = array('data' => $data, $status => true);
     $response->set_data($data);
     /**
      * Fires after a single post is deleted or trashed via the REST API.
      *
      * @param object          $post    The deleted or trashed post.
      * @param array           $data    The response data.
      * @param WP_REST_Request $request The request sent to the API.
      */
     do_action('rest_delete_post', $post, $data, $request);
     return $response;
 }
 /**
  * Checks the site plan and deactivates modules that were active but are no longer included in the plan.
  *
  * @since 4.4.0
  *
  * @param $page
  *
  * @return bool|array
  */
 function check_plan_deactivate_modules($page)
 {
     if (Jetpack::is_development_mode() || !in_array($page->base, array('toplevel_page_jetpack', 'admin_page_jetpack_modules', 'jetpack_page_vaultpress', 'jetpack_page_stats', 'jetpack_page_akismet-key-config')) || true === self::$plan_checked) {
         return false;
     }
     self::$plan_checked = true;
     $previous = get_option('jetpack_active_plan', '');
     $response = rest_do_request(new WP_REST_Request('GET', '/jetpack/v4/site'));
     if (!is_object($response) || $response->is_error()) {
         // If we can't get information about the current plan we don't do anything
         self::$plan_checked = true;
         return;
     }
     $current = $response->get_data();
     $current = json_decode($current['data']);
     $to_deactivate = array();
     if (isset($current->plan->product_slug)) {
         if (empty($previous) || !isset($previous['product_slug']) || $previous['product_slug'] !== $current->plan->product_slug) {
             $active = Jetpack::get_active_modules();
             switch ($current->plan->product_slug) {
                 case 'jetpack_free':
                     $to_deactivate = array('seo-tools', 'videopress');
                     break;
                 case 'jetpack_personal':
                 case 'jetpack_personal_monthly':
                     $to_deactivate = array('seo-tools', 'videopress');
                     break;
                 case 'jetpack_premium':
                 case 'jetpack_premium_monthly':
                     $to_deactivate = array('seo-tools');
                     break;
             }
             $to_deactivate = array_intersect($active, $to_deactivate);
             if (!empty($to_deactivate)) {
                 Jetpack::update_active_modules(array_filter(array_diff($active, $to_deactivate)));
             }
         }
     }
     return array('previous' => $previous, 'current' => $current, 'deactivate' => $to_deactivate);
 }
 /**
  * Delete a single post
  *
  * @param WP_REST_Request $request Full details about the request
  * @return array|WP_Error
  */
 public function delete_item($request)
 {
     $id = (int) $request['id'];
     $force = (bool) $request['force'];
     $post = get_post($id);
     if (empty($id) || empty($post->ID) || $this->post_type !== $post->post_type) {
         return new WP_Error('rest_post_invalid_id', __('Invalid post ID.'), array('status' => 404));
     }
     $supports_trash = EMPTY_TRASH_DAYS > 0;
     if ($post->post_type === 'attachment') {
         $supports_trash = $supports_trash && MEDIA_TRASH;
     }
     /**
      * Filter whether the post type supports trashing.
      *
      * @param boolean $supports_trash Does the post type support trashing?
      * @param WP_Post $post Post we're attempting to trash.
      */
     $supports_trash = apply_filters('rest_post_type_trashable', $supports_trash, $post);
     if (!$this->check_delete_permission($post)) {
         return new WP_Error('rest_user_cannot_delete_post', __('Sorry, you are not allowed to delete this post.'), array('status' => 401));
     }
     $request = new WP_REST_Request('GET', '/wp/v2/' . $this->get_post_type_base($this->post_type) . '/' . $post->ID);
     $request->set_param('context', 'edit');
     $response = rest_do_request($request);
     // If we're forcing, then delete permanently
     if ($force) {
         $result = wp_delete_post($id, true);
     } else {
         // If we don't support trashing for this type, error out
         if (!$supports_trash) {
             return new WP_Error('rest_trash_not_supported', __('The post does not support trashing.'), array('status' => 501));
         }
         // Otherwise, only trash if we haven't already
         if ('trash' === $post->post_status) {
             return new WP_Error('rest_already_deleted', __('The post has already been deleted.'), array('status' => 410));
         }
         // (Note that internally this falls through to `wp_delete_post` if
         // the trash is disabled.)
         $result = wp_trash_post($id);
     }
     if (!$result) {
         return new WP_Error('rest_cannot_delete', __('The post cannot be deleted.'), array('status' => 500));
     }
     return $response;
 }
Example #6
0
 /**
  * Do a REST Request
  *
  * @param string $method
  * 
  */
 private function do_request($method, $route, $assoc_args)
 {
     if ('internal' === $this->scope) {
         $request = new \WP_REST_Request($method, $route);
         if (in_array($method, array('POST', 'PUT'))) {
             $request->set_body_params($assoc_args);
         } else {
             foreach ($assoc_args as $key => $value) {
                 $request->set_param($key, $value);
             }
         }
         $response = rest_do_request($request);
         if ($error = $response->as_error()) {
             WP_CLI::error($error);
         }
         return array($response->get_status(), $response->get_data(), $response->get_headers());
     } else {
         if ('http' === $this->scope) {
             $response = Utils\http_request($method, rtrim($this->api_url, '/') . $route, $assoc_args);
             $body = json_decode($response->body, true);
             if ($response->status_code >= 400) {
                 if (!empty($body['message'])) {
                     WP_CLI::error($body['message'] . ' ' . json_encode(array('status' => $response->status_code)));
                 } else {
                     switch ($response->status_code) {
                         case 404:
                             WP_CLI::error("No {$this->name} found.");
                             break;
                         default:
                             WP_CLI::error('Could not complete request.');
                             break;
                     }
                 }
             }
             return array($response->status_code, json_decode($response->body, true), $response->headers);
         }
     }
     WP_CLI::error('Invalid scope for REST command.');
 }
    /**
     * Do a REST Request
     *
     * @param string $method
     *
     */
    private function do_request($method, $route, $assoc_args)
    {
        if (!defined('REST_REQUEST')) {
            define('REST_REQUEST', true);
        }
        $request = new WP_REST_Request($method, $route);
        if (in_array($method, array('POST', 'PUT'))) {
            $request->set_body_params($assoc_args);
        } else {
            foreach ($assoc_args as $key => $value) {
                $request->set_param($key, $value);
            }
        }
        if (defined('SAVEQUERIES') && SAVEQUERIES) {
            $original_queries = is_array($GLOBALS['wpdb']->queries) ? array_keys($GLOBALS['wpdb']->queries) : array();
        }
        $response = rest_do_request($request);
        if (defined('SAVEQUERIES') && SAVEQUERIES) {
            $performed_queries = array();
            foreach ((array) $GLOBALS['wpdb']->queries as $key => $query) {
                if (in_array($key, $original_queries)) {
                    continue;
                }
                $performed_queries[] = $query;
            }
            usort($performed_queries, function ($a, $b) {
                if ($a[1] === $b[1]) {
                    return 0;
                }
                return $a[1] > $b[1] ? -1 : 1;
            });
            $query_count = count($performed_queries);
            $query_total_time = 0;
            foreach ($performed_queries as $query) {
                $query_total_time += $query[1];
            }
            $slow_query_message = '';
            if ($performed_queries && 'wc' === WP_CLI::get_config('debug')) {
                $slow_query_message .= '. Ordered by slowness, the queries are:' . PHP_EOL;
                foreach ($performed_queries as $i => $query) {
                    $i++;
                    $bits = explode(', ', $query[2]);
                    $backtrace = implode(', ', array_slice($bits, 13));
                    $seconds = round($query[1], 6);
                    $slow_query_message .= <<<EOT
{$i}:
- {$seconds} seconds
- {$backtrace}
- {$query[0]}
EOT;
                    $slow_query_message .= PHP_EOL;
                }
            } elseif ('wc' !== WP_CLI::get_config('debug')) {
                $slow_query_message = '. Use --debug=wc to see all queries.';
            }
            $query_total_time = round($query_total_time, 6);
            WP_CLI::debug("wc command executed {$query_count} queries in {$query_total_time} seconds{$slow_query_message}", 'wc');
        }
        if ($error = $response->as_error()) {
            WP_CLI::error($error);
        }
        return array($response->get_status(), $response->get_data(), $response->get_headers());
    }