如何使用WP_QUERY将此数据库查询作为搜索结果运行?

时间:2012-08-17 作者:Brent

我创建了一个带有4个选项的下拉框的搜索框,用于自定义搜索:

常规默认搜索,无过滤器,仅根据自定义帖子类型的帖子标题进行自定义搜索我构建了搜索框来处理这个问题。在函数中看起来是这样的。php文件:

function r3_search_form( $form ) {
    $form = \'<form role="search" method="get" id="top_nav_search" action="\' . home_url( \'/\' ) . \'" >
    <div>

        <label class="screen-reader-text" for="type">\' . __(\'Type of Search:\') . \'</label>
        <select name="type" id="ic_search_type" >
            <option value="all">General Search |search full site contents|</option>
            <option value="name">Mineral Name |search the approved name for the mineral|</option>
            <option value="loc">Locality |search by mine name, district, state, or country|</option>
            <option value="detail">Description |search the description of the mineral|</option>
        </select>
        <label class="screen-reader-text" for="s">\' . __(\'Search Form:\') . \'</label>
        <input type="text" value="\' . get_search_query() . \'" name="s" id="s" />
        <input type="submit" id="searchsubmit" value="\'. esc_attr__(\'Search\') .\'" />
    </div>
    </form>\';

    return $form;
}

add_filter( \'get_search_form\', \'r3_search_form\' );
使用该搜索框返回一个URL,该URL末尾有一个查询字符串,如下所示:?type=loc&s=Arizona . 您会注意到,我只添加了一个附加参数type 默认搜索将返回的内容。

这就是我要做的。根据搜索结果,我需要更改主查询,使其行为类似于以下MySQL查询之一:

从wp\\u posts、wp\\u postmeta和wp\\u posts中选择*。ID=wp\\U后到达时间。post_id和wp_Posteta。meta\\u key=“\\u custom\\u meta\\u key”和wp\\u postmeta。meta\\u值,如“%$search\\u term%”和wp\\u posts。post\\U类型=“自定义post类型”按wp\\U posts排序。post\\u日期描述

  • 从wp\\U POST(wp\\U POST所在的位置)中选择*。post\\u标题,如“%$search\\u term%”和wp\\u帖子。post\\U类型=“自定义post类型”ORDERBY wp\\U posts。post\\u日期描述

    我两年前在WordPress论坛上发现了这篇帖子:http://wordpress.org/support/topic/query-posts-by-custom-fields-value

    这与我想要实现的目标非常接近,但我的问题是,是否有一种方法可以在WP\\u查询循环中专门实现这一点,而不使用WP数据库类($wpdb)。

    我已经建立了一个pre-get-post 根据type 函数中的参数。php文件来处理此请求,但我无法使用WP\\u query类按上述方式运行查询。能做到吗?谢谢

  • 2 个回复
    最合适的回答,由SO网友:Brent 整理而成

    那么,也许在WP_Query 为我想完成的事情上课。下面是我插入函数的最后一段代码。php文件。我最终找到了WP_Query 在中找到类wp_includes/query.php 文件我发现有许多过滤器访问点,可以跳入其中并修改查询。我发现有posts_search 允许我修改发送到数据库的MySQL查询的搜索部分的过滤器。还有一个更具包容性的posts_where 允许我修改更多MySQL查询的过滤器。

    感谢Google Groups上的@Scribu over建议对传入查询进行var\\u转储,以查看我使用的过滤器是否允许我访问我想要修改的查询部分。

    然而,我最终决定访问全能的posts_request 过滤器,它为我提供了完整的MySQL查询字符串,并允许我提取查询请求的核心,并根据我需要执行的三个不同查询之一进行替换。我修剪了查询的开始和结束并将其存储在变量中,这样就不会破坏查询动态设置的能力。

    以下是搜索表单:

    function my_search_form( $form ) {
        (isset($_REQUEST[\'type\']))? $ic_sType = $_REQUEST[\'type\'] : $ic_sType = \'\';
    
    
        $ic_selectOpts = array(
            \'all\' =>\'General Search [search full site contents]\',
            \'name\'=>\'Mineral Name [search the approved name for the mineral]\',
            \'detail\'=>\'Description [search the description of the mineral]\',
            \'loc\'=>\'Locality [search by mine name, district, state, or country]\'
        );
    
        $form = \'<form role="search" method="get" id="top_nav_search" action="\' . home_url( \'/\' ) . \'" >
        <div>
    
    
            <label class="screen-reader-text" for="type">\' . __(\'Type of Search:\') . \'</label>
    
            <select name="type" id="my_search_type" >\';
            foreach($my_selectOpts as $myso_key => $myso_val){
                $form .= "<option value=\'$myso_key\'";
                if($myso_key === $my_sType) $form .= "selected=\'selected\'";
                $form .= ">$myso_val</option>";
            }
    
            $form .= \'</select>
            <label class="screen-reader-text" for="s">\' . __(\'Search Form:\') . \'</label>
            <input type="text" value="\' . get_search_query() . \'" name="s" id="s" />
            <input type="submit" id="searchsubmit" value="\'. esc_attr__(\'Search\') .\'" />
        </div>
        </form>\';
    
        return $form;
    }
    
    add_filter( \'get_search_form\', \'my_search_form\' );
    
    这是搜索结果过滤器:

    function my_search_results($query){
    
        if(isset($_REQUEST[\'type\']) && isset($_REQUEST[\'s\']) && ($_REQUEST[\'type\'] !== \'all\')){
    
            $myType = $_REQUEST[\'type\'];
            $mySearch = $_REQUEST[\'s\'];
    
            $qBegin = str_replace(strstr($query, "FROM" ), \'\', $query). \' FROM\';
    
            //echo \'<br>the qBegin string: \'. $qBegin;
    
            $qEnd = strrchr($query, "ORDER BY" );
            //echo \'<br>the qEnd string:\' . $qEnd;
    
            switch ($myType){
    
                case \'name\': //Title search
    
                    $query = $qBegin. \' wp_posts WHERE 1=1 AND wp_posts.post_title LIKE "%\'.$icSearch.\'%" AND wp_posts.post_type = "mineral" AND (wp_posts.post_password = "") AND(wp_posts.post_status = "publish") \'.$qEnd;
    
                    break;
    
                case \'loc\': //Location Search
    
                    $query = $qBegin. \' wp_posts,wp_postmeta WHERE wp_posts.ID = wp_postmeta.post_id AND 1=1 AND wp_postmeta.meta_key = "_location_meta" AND wp_postmeta.meta_value LIKE "%\'.$icSearch.\'%" AND wp_posts.post_type = "mineral" AND (wp_posts.post_password = "") AND(wp_posts.post_status = "publish") \'.$qEnd;
    
                    break;
    
                case \'detail\': //Details Search
    
                    $query = $qBegin. \' wp_posts WHERE 1=1 AND wp_posts.post_content LIKE "%\'.$icSearch.\'%" AND wp_posts.post_type = "mineral" AND (wp_posts.post_password = "") AND(wp_posts.post_status = "publish") \'.$qEnd;
    
                    break;
    
                default: 
    
                    break;
            }
    
        } 
    
        return $query;
    
    }
    add_filter( \'posts_request\', \'my_search_results\');
    
    希望这能帮助其他人。

    SO网友:xiarnousx

    在执行之前,您可以使用操作挂钩格式化wp\\u查询看看Action reference pre get post您需要在[meta\\u query]中添加自定义字段过滤器选项,以了解有关签出wp\\u query codex函数文档的更多详细信息。

    修改了codex中的示例:

        function meta_add( &$query ) {
        if ( /*search result page */ ) {
            $query->set( \'meta_query\', array(/*assoc of the filter */) );
        }
    }
    add_action( \'pre_get_posts\', \'meta_add\' );
    
    希望能帮到你

    结束