public function filter__posts_request($sql, $query) { global $wpdb; if (!$query->is_main_query() || !$query->is_search()) { return $sql; } $page = $query->get('paged') ? absint($query->get('paged')) : 1; // Start building the WP-style search query args // They'll be translated to ES format args later $es_wp_query_args = array('query' => $query->get('s'), 'posts_per_page' => $query->get('posts_per_page'), 'paged' => $page, 'orderby' => $query->get('orderby'), 'order' => $query->get('order')); // Look for query variables that match registered and supported facets foreach ($this->facets as $label => $facet) { switch ($facet['type']) { case 'taxonomy': $query_var = $this->get_taxonomy_query_var($this->facets[$label]['taxonomy']); if (!$query_var) { continue 2; } // switch() is considered a looping structure if ($query->get($query_var)) { $es_wp_query_args['terms'][$this->facets[$label]['taxonomy']] = explode(',', $query->get($query_var)); } // This plugon's custom "categery" isn't a real query_var, so manually handle it if ('category' == $query_var && !empty($_GET[$query_var])) { $slugs = explode(',', $_GET[$query_var]); foreach ($slugs as $slug) { $es_wp_query_args['terms'][$this->facets[$label]['taxonomy']][] = $slug; } } break; case 'post_type': if ($query->get('post_type') && 'any' != $query->get('post_type')) { $post_types_via_user = $query->get('post_type'); } elseif (!empty($_GET['post_type'])) { $post_types_via_user = explode(',', $_GET['post_type']); } else { $post_types_via_user = false; } $post_types = array(); // Validate post types, making sure they exist and are public if ($post_types_via_user) { foreach ((array) $post_types_via_user as $post_type_via_user) { $post_type_object = get_post_type_object($post_type_via_user); if (!$post_type_object || $post_type_object->exclude_from_search) { continue; } $post_types[] = $post_type_via_user; } } // Default to all non-excluded from search post types if (empty($post_types)) { $post_types = array_values(get_post_types(array('exclude_from_search' => false))); } $es_wp_query_args['post_type'] = $post_types; break; } } // Date if ($query->get('year')) { if ($query->get('monthnum')) { // Padding $date_monthnum = sprintf('%02d', $query->get('monthnum')); if ($query->get('day')) { // Padding $date_day = sprintf('%02d', $query->get('day')); $date_start = $query->get('year') . '-' . $date_monthnum . '-' . $date_day . ' 00:00:00'; $date_end = $query->get('year') . '-' . $date_monthnum . '-' . $date_day . ' 23:59:59'; } else { $days_in_month = date('t', mktime(0, 0, 0, $query->get('monthnum'), 14, $query->get('year'))); // 14 = middle of the month so no chance of DST issues $date_start = $query->get('year') . '-' . $date_monthnum . '-01 00:00:00'; $date_end = $query->get('year') . '-' . $date_monthnum . '-' . $days_in_month . ' 23:59:59'; } } else { $date_start = $query->get('year') . '-01-01 00:00:00'; $date_end = $query->get('year') . '-12-31 23:59:59'; } $es_wp_query_args['date_range'] = array('field' => 'date', 'gte' => $date_start, 'lte' => $date_end); } // Facets if (!empty($this->facets)) { $es_wp_query_args['facets'] = $this->facets; } // You can use this filter to modify the search query parameters, such as controlling the post_type. // These arguments are in the format for wpcom_search_api_wp_to_es_args(), i.e. WP-style. $es_wp_query_args = apply_filters('wpcom_elasticsearch_wp_query_args', $es_wp_query_args, $query); // Convert the WP-style args into ES args $es_query_args = wpcom_search_api_wp_to_es_args($es_wp_query_args); $es_query_args['fields'] = array('post_id', 'blog_id'); // Ask for a search suggestion (to catch typos) // See http://www.elasticsearch.org/guide/en/elasticsearch/reference/current/search-suggesters-phrase.html for options $suggest_beta_blogs = array(15797879, 12269838, 2235322); if (in_array(get_current_blog_id(), $suggest_beta_blogs)) { $es_query_args['suggest'] = array('text' => $query->get('s'), 'simple_phrase' => array('phrase' => array('field' => 'content', 'direct_generator' => array(array('field' => 'content', 'suggest_mode' => 'popular', 'prefix_len' => 3, 'max_term_freq' => 0.02))))); } // This filter is harder to use if you're unfamiliar with ES but it allows complete control over the query $es_query_args = apply_filters('wpcom_elasticsearch_query_args', $es_query_args, $query); // Do the actual search query! $this->search_result = es_api_search_index($es_query_args, 'blog-search'); if (is_wp_error($this->search_result) || !is_array($this->search_result) || empty($this->search_result['results']) || empty($this->search_result['results']['hits'])) { $this->found_posts = 0; return ''; } // Allow filtering of entire result set to modify it or to add / remove results $this->search_result = apply_filters('wpcom_elasticsearch_found_posts', $this->search_result); // Total number of results for paging purposes $this->found_posts = $this->search_result['results']['total']; // Don't select anything, posts are inflated by ES_WPCOM_SearchResult_Posts_Iterator in The Loop, // to account for multi site search return ''; }
/** * A wrapper for es_api_search_index() that accepts WP-style args * * This is a copy/paste, up to date as of WP.com r65003 (Jan 7th, 2013) * * @param array $args * @param string $stat_app_name Optional. * @return bool|string False if WP_Error, otherwise JSON string * @see wpcom_search_api_wp_to_es_args() for details */ function wpcom_search_api_query($args, $stat_app_name = 'blog-search') { $es_query_args = wpcom_search_api_wp_to_es_args($args); return es_api_search_index($es_query_args, $stat_app_name); }