#
ドキュメント

Document

自分のための備忘録です。

メインクエリとサブクエリ

メインクエリ

WordPressは、リクエストに応じたメインクエリを作成します。
WordPressは、have_posts()the_post()などのメインクエリで取得した投稿を処理する関数が提供しています。

※1 下記サンプルコードは、アーカイブなどでよく使われるページネーションを表示するthe_posts_pagination()のコードも合わせて掲載しています。
※2 1ページあたりの投稿数は管理画面 Settings > Reading Settings > Blog pages show at mostに依存します。

<?php
    if ( have_posts() ) {
        echo '<ul>';
        while ( have_posts() ) {
            the_post();
            echo sprintf("<li><a href='%s'>%s</a></li>", get_the_permalink(), get_the_title());
        }
        echo '</ul>';
    }
     
    the_posts_pagination(
        array(
            'prev_text'          => __( 'Previous page', 'example' ),
            'next_text'          => __( 'Next page', 'example' ),
            'before_page_number' => '<span class="meta-nav screen-reader-text">' .
                                    __( 'Page', 'example' ) . ' </span>',
        )
    );
?>

$wp_query

グローバル変数$wp_queryは、メインクエリが格納されたおり、そのクエリで取得した投稿を保持しています。
下記コードは前述したコードとほぼ同じ働きをします。

※1 下記サンプルコードは、アーカイブなどでよく使われるページネーションを表示するthe_posts_pagination()のコードも合わせて掲載しています。
※2 1ページあたりの投稿数は管理画面 Settings > Reading Settings > Blog pages show at mostに依存します。

<?php
    global $wp_query;

    if ( $wp_query->have_posts() ) {
        echo '<ul>';
        while ( $wp_query->have_posts() ) {
            $wp_query->the_post();
            echo sprintf("<li><a href='%s'>%s</a></li>", get_the_permalink(), get_the_title());
        }
        echo '</ul>';
    }

    the_posts_pagination([
    'prev_text'          => __( 'Previous page', 'example-domain' ),
    'next_text'          => __( 'Next page', 'example-domain' ),
    'before_page_number' => '<span class="meta-nav screen-reader-text">' .
        __( 'Page', 'example-domain' ) . ' </span>',
    ]);
?>

WP_Query

メインクエリとは異なる条件に一致する投稿を表示したいときなどに使われます。 メインクエリに影響を与えることなく新しいクエリを作成します。

下記サンプルはexampleカテゴリの記事を表示します。
※投稿数は管理画面の影響を受ける点が、後述するget_posts()と異なります。

<?php
   // メインクエリ
   if ( have_posts() ) {
       echo '<ul>';
       while ( have_posts() ) {
           the_post();
           echo sprintf("<li><a href='%s'>%s</a></li>", get_the_permalink(), get_the_title());
       }
       echo '</ul>';
   }
   
   // サブクエリ
   $query = new WP_Query([
       'posts_per_page' => 10,
       'paged' => $paged,
       'tax_query' => [ 
           [
               'taxonomy' => 'category',
               'field'    => 'slug',
               'terms'    => 'example',
           ],
       ],

   ]);

   if ( $query->have_posts() ) {
       echo '<ul>';
       while ( $query->have_posts() ) {
           $query->the_post();
           echo sprintf("<li><a href='%s'>%s</a></li>", get_the_permalink(), get_the_title());
       }
       echo '</ul>';
   }
   wp_reset_postdata();

   $paged = ( get_query_var('paged') ) ? get_query_var('paged') : 1;
   the_posts_pagination([
       'prev_text'          => __( 'Previous page', 'example-domain' ),
       'next_text'          => __( 'Next page', 'example-domain' ),
       'before_page_number' => '<span class="meta-nav screen-reader-text">' .
           __( 'Page', 'example-domain' ) . ' </span>',
   ]);
?>

引数なしで作成した場合は、投稿を全く持ちません。

$query = new WP_Query();
$query->have_posts(); // false

get_posts()

上記のnew WP_Queryとほぼ同じように動作します。

get_posts()は引数で指定したクエリ条件に一致する投稿を取得します。 メインクエリとは異なる条件に一致する投稿を表示したいときなどに使われます。 メインクエリに影響を与えることなくあらたにクエリを作成します。

下記サンプルはexampleカテゴリの記事を表示します。

<?php
    // メインクエリ
    if ( have_posts() ) {
        echo '<ul>';
        while ( have_posts() ) {
            the_post();
            echo sprintf("<li><a href='%s'>%s</a></li>", get_the_permalink(), get_the_title());
        }
        echo '</ul>';
    }
    
    // サブクエリ
    $paged = ( get_query_var('paged') ) ? get_query_var('paged') : 1;
    $posts = get_posts([
        'posts_per_page' => 10,
        'paged' => $paged,
        `category_name` => 'example'
    ]);        

    foreach ($posts as $post) {
        setup_postdata($post);
        echo sprintf("<li><a href='%s'>%s</a></li>", get_the_permalink(), get_the_title());
    }
    wp_reset_postdata();
    
    the_posts_pagination([
        'prev_text'          => __( 'Previous page', 'example-domain' ),
        'next_text'          => __( 'Next page', 'example-domain' ),
        'before_page_number' => '<span class="meta-nav screen-reader-text">' .
                                __( 'Page', 'example-domain' ) . ' </span>',
    ]);
 ?>

サブクエリ

https://wpdocs.osdn.jp/%E9%96%A2%E6%95%B0%E3%83%AA%E3%83%95%E3%82%A1%E3%83%AC%E3%83%B3%E3%82%B9/paginate_links#.E7.94.A8.E4.BE.8B
↑のカスタムクエリを使用した例がそのまま使用できる。

ref. https://yuki.world/wp-main-sub-query-pagination/