WordPressの起動3 – WP_Queryクラスのカスタマイズ

wp-blog-header.phpで環境設定や重要なオブジェクトを$GROBALSに格納したあとwp関数が実行されますが、内部では$wp->query_postsメソッド、$wp_query->get_postsメソッド、$wp_query->parse_queryメソッドが順番に呼ばれて実行されます。

WPクラスとWP_Queryクラス

$wp、$wp_the_query、$wp_queryなどのクラスのオブジェクトは、wp-settings.phpの中で実体化され、スーパーグローバル変数$GLOBALSに格納されています。

  1. wp()
  2. $wp->main()
  3. —-$wp->parse_request():①URLをパース(文法に従って分析)しクエリを特定
  4. —-$wp->query_posts()
  5. ——–$wp_query->query()
  6. ————$wp_query->get_posts():③投稿データを$posts配列に格納
  7. —————-$wp_query->parse_query():②条件分岐タグで使用されるすべてのis_変数を設定

URLからクエリを特定し、条件分岐タグを使えるための値をセットして、wp_postsテーブルなどから必要な投稿データをグローバル変数$postsに格納する3つの処理は、コンテンツを表示するループの中で使われる処理です。

query_posts関数とget_posts関数

上記のようにquery_posts関数はメインクエリを取得するための関数でありwp-includes/query.php内に以下のように定義されていますが、Codexには「この関数はプラグインまたはテーマの中で使われることを想定されていません。」と書いてあります。

つまりquery_posts関数はテンプレートタグ(テンプレートの中で使う関数)ではないわけで、処理の実態はWP_Queryクラス内のメインクエリ取得のための関数です。

一方でget_posts関数はwp-includes/post.phpで以下のように定義されています。

ややこしいですがWP_Queryクラス内でグローバル変数$postsに投稿データを格納するメソッドもget_posts()ですが、別モノですから要注意。

このテンプレートタグであるget_posts()のほうが、WP_Queryからメインクエリとは別のクエリを生成していることから、カスタムクエリでのデータ取得にはget_query()テンプレートタグが使われてきましたが、最近は以下のようにWP_Queryクラスからカスタムループ用クエリを使うためのインスタンスを生成して使うのが主流です。

カスタムループ作成はWP_Queryクラスで

WordPressのメインループは、WP_Queryクラスの$wp_queryインスタンスからメソッドを実行し、適切な投稿データを取得しますが、メインループ以外で独自の条件でクエリを実行する場合は、$wp_query2みたいに別途インスタンスを生成する必要があります。

いつものWordPressループを$wp_query2のメソッドとして実行します。

メインループの変更はpre_get_postsフックで

投稿を取得するクエリのコアであるget_postsメソッドの中で、$this->parse_query()を実行した後に、pre_get_postsというアクションフックが仕込んであり、WP_Queryのパラメータを配列引数array( &$this )でプラグイン側に送りますので、プラグイン関数側で$queryという配列型オブジェクトとして受け取り、パラメータを書き換えることで、メインクエリの動きを調整します。

functions.php内で、プラグイン関数とpre_get_postsフックをadd_action関数でマッピングしてあげれば、メインクエリを操作できます。

プラグイン関数ではWP_Queryのパラメータを配列オブジェクト$queryとして受け取り、setメソッドで値を書き換えます。

$query->set(‘パラメータ名’, ‘値’);

最新情報
お届けします

Twitter で