プラグインを使わずに、検索範囲にカスタムフィールドを含める

プラグインを使わずに、検索範囲にカスタムフィールドを含める

1、search.phpに検索用のソースを用意する。

<?php
  // // 検索結果表示用
  global $wpdb;
  // If you use a custom search form
  // $keyword = sanitize_text_field( $_POST['keyword'] );
  // If you use default WordPress search form
  $keyword = get_search_query();
  $keyword = '%' . $wpdb->esc_like( $keyword ) . '%'; // Thanks Manny Fleurmond
  // Search in all custom fields
  $post_ids_meta = $wpdb->get_col( $wpdb->prepare( "
      SELECT DISTINCT post_id FROM {$wpdb->postmeta}
      WHERE meta_value LIKE '%s'
  ", $keyword ) );
  // Search in post_title and post_content
  $post_ids_post = $wpdb->get_col( $wpdb->prepare( "
      SELECT DISTINCT ID FROM {$wpdb->posts}
      WHERE post_title LIKE '%s'
      OR post_content LIKE '%s'
  ", $keyword, $keyword ) );
  $post_ids = array_merge( $post_ids_meta, $post_ids_post );
  // Query arguments
  $args = array(
    'post_type'   => 'post',
    'posts_per_page' => -1,
    'order'          => 'DESC',
    'post_status'    => 'publish',
    'orderby' => 'meta_value_num',
    'meta_key' => 'product_txt_sortno',
    'order' => 'asc',
    'post__in'    => $post_ids,
  );
  $s_query = new WP_Query( $args );
?>

2、検索結果を出力する

<?php if( (!($post_ids)) || (isset($_GET['s']) && empty($_GET['s'])) ) :?>
	<!-- 検索条件にヒットしなかった場合 または 検索条件が指定されていない場合 -->
<?php else: ?>
	<!-- 検索がHitした場合 -->
	<?php if(have_posts()): while(have_posts()): the_post(); ?>
	//ここにループさせる内容
	<?php endwhile; else: ?>
	//ここに検索キーワードと一致する記事がない場合の表示
	<?php endif; ?>
<?php endif; ?>

———————————-

■カスタマイズ
▽Query argumentsで検索の詳細を設定出来る。
例)投稿、固定ページ、カスタム投稿タイプ「movie」、「book」に限定する場合
  ’post_type’ => array( ‘post’, ‘page’, ‘movie’, ‘book’ )

▽検索するカスタムフィールドの範囲を絞る
// Search in all custom fields の項目を編集
例)1つのカスタムフィールドに絞る 

$post_ids_meta = $wpdb->get_col( $wpdb->prepare( "
      SELECT DISTINCT post_id FROM {$wpdb->postmeta}
      WHERE 1=1
      AND (meta_key = 'hoge_field' AND meta_value LIKE '%s')
  ", $keyword ) );

例)複数のカスタムフィールドに絞る

WHERE 1=1 AND ( (hoge_Field_1) OR (hoge_Field_2) )

———————————-

■ページャーを使用する場合(上記のソースを元にカスタマイズされている/未検証)

<?php
  global $wpdb;

  // If you use a custom search form
  // $keyword = sanitize_text_field( $_POST['keyword'] );
  // If you use default WordPress search form
  $keyword = get_search_query();
  $keyword = '%' . like_escape( $keyword ) . '%'; // Thanks Manny Fleurmond

  // Search in all custom fields
  $post_ids_meta = $wpdb->get_col( $wpdb->prepare( "
    SELECT DISTINCT post_id FROM {$wpdb->postmeta}
    WHERE meta_value LIKE '%s'
    ", $keyword ) );

  // Search in post_title and post_content
  $post_ids_post = $wpdb->get_col( $wpdb->prepare( "
    SELECT DISTINCT ID FROM {$wpdb->posts}
    WHERE post_title LIKE '%s'
    OR post_content LIKE '%s'
    ", $keyword, $keyword ) );
  $post_ids = array_merge( $post_ids_meta, $post_ids_post );

  // ページネーションのために、現在のpage番号が必要だが、
  // $paged = (get_query_var('paged')) ? get_query_var('paged') : 1;
  // のコードでは上手くいかなかったので、get_query_var('page')も追加
  if ( get_query_var('paged') ) {
    $paged = get_query_var('paged');
  } else if ( get_query_var('page') ) {
    $paged = get_query_var('page');
  } else {
    $paged = 1;
  }

  // Query arguments
  $args = array(
    'post_type'   => 'any', // 必要であれば適宜変える。
    'posts_per_page' => 10, // 指定追加
    'paged' => $paged,      // 指定追加
    'post_status' => 'publish',
    'post__in'    => $post_ids,
    'order'=>'DESC',  // 条件は適宜追加
    'orderby'=>'date' // 条件は適宜追加
  );

  $query = new WP_Query( $args );

  // 後の件数表示に使いたいので、ここで取得している
  if ( (!($post_ids)) || (isset($_GET['s']) && empty($_GET['s'])) ) {
    $get_num = 0;
    $all_num = 0;
  } else {
    $get_num = $query -> post_count;
    $all_num = $query -> found_posts;
  }

?>

参考サイト

Welcart カスタマイズ ブログ
プラグインなしでカスタムフィールドの値を検索範囲に反映させる方法
http://welcustom.net/extend-custom-fields-in-search/
Deluxe Blog Tips
Search ALL Custom Fields in WordPress
http://www.deluxeblogtips.com/search-all-custom-fields/
Qiita
【WordPress】カスタムフィールドの値を検索範囲に反映させる方法(の補足)
http://qiita.com/WW-AT/items/16e63fb27aa3147d8cdb