web-dev-qa-db-ja.com

PagerDefaultによって拡張されたクエリから結果の全数を取得できますか

PagerDefaultによって拡張されたクエリがあります。結果の総数を取得して、「合計100の結果があり、現在は21から40を表示している」のように表示する必要があります。 PagerDefaultを使用しない実行する別のクエリを作成しないと、その番号をどこで取得できるかわかりません。

最初に見たのはtheme_pager()で、これは既にtemplate.phpでオーバーライドしています。結果の総数はそこには渡されず、現在のページだけが渡されます(_$variables['element']_として)。

_includes/pager.inc_内のpager_default_initialize()内では、現在のページ番号のみが_theme_pager_に送信されますが、その関数に合計アイテムが渡されます。 (とても近い!)

次に、クエリを複製できると思いましたが、条件を追加する前にクエリを拡張する必要があるため、機能しません。これも理想的ではないことに注意してください。理想的には、2回のdbヒットなしでこの合計数を取得できるためです(ユーザーがページネーションをナビゲートするたびにカウントにヒットするため)。

だから、誰かが合計数を取得するための最良の方法を知っていますか?

ありがとう!

5
Chris Rockwell

既存のページャークラスでは、countクエリを再度実行しないとそのデータを取得できないと思います。合計数は直接照会され、pager_default_initialize()...に渡される前にローカル変数に保存されます。どこにも保存されません。

1つのオプションは、デフォルトクラスを拡張し、それをポケットベルクエリに使用することです。これはテストされていませんが、トリックを実行すると思います

class MyPager extends PagerDefault {

  /**
   * Overrides PagerDefault::execute().
   */
  public function execute() {
    // Add convenience tag to mark that this is an extended query. We have to
    // do this in the constructor to ensure that it is set before preExecute()
    // gets called.
    if (!$this->preExecute($this)) {
      return NULL;
    }

    // A NULL limit is the "kill switch" for pager queries.
    if (empty($this->limit)) {
      return;
    }
    $this->ensureElement();

    // Get the total items from our new statically cached function.
    $total_items = $this->getTotalItemCount();

    $current_page = pager_default_initialize($total_items, $this->limit, $this->element);
    $this->range($current_page * $this->limit, $this->limit);

    // Now that we've added our pager-based range instructions, run the query normally.
    return $this->query->execute();
  }

  /**
   * Cache the results of PagerDefault::getCountQuery().
   */
  public function getTotalItemCount() {
    static $total_items = NULL;

    if ($total_items === NULL) {
      $total_items = $this->getCountQuery()->execute()->fetchField();
    }

    return $total_items;
  }

}

その後、次のようなクエリを作成できます

$query = db_select('table', 't')
  ->fields('t')
  ->condition('foo', 'bar')
  ->extend('MyPager');

$current_items = $query->execute();
$total_items = $query->getTotalItemCount();

もっと簡単な方法があるかもしれませんが、私はそれを見ることができません。

6
Clive

PagerDefaultを拡張するクエリを実行した後は、その後(いつでも異なる関数間でも)、合計製品数を格納するグローバルを呼び出すことができます。

// $results = $paged_query->execute();
// OR
// $results = some_function_that_executes_a_paged_query();
global $pager_total_items;
$count = $pager_total_items[0];

これはDrupal 7で私の知る限りでは7で機能し、合計カウントが必要な検索やページ付けされたディスプレイを使用する前にも使用する必要がありました。これにより、 2番目の個別のクエリ全体。

これは、Drupalから入手した最も「正式なドキュメント」です。 https://api.drupal.org/api/drupal/developer%21globals.php/global/pager_total_items/7.xhttps://api.drupal.org/api/ drupal/core!globals.api.php/global/pager_total_items/8.2.x

1
JPMC

PagerDefaultで拡張されたクエリの合計数を取得するには

  $num_rows = $query->countQuery()->execute()->fetchField();

このクエリは、ページャーを使用してすべてのノードをフェッチし、ノードの総数をカウントします

function _test() {
  $query = db_select('node', 'n')
          ->extend('PagerDefault');
  $query->addField('n', 'nid');
  $num_rows = $query->countQuery()->execute()->fetchField();
  $results = $query->execute();
  foreach ($results as $result) {
    drupal_set_message($result->nid); // print each row
    // do fancier stuff here
  }
  drupal_set_message($num_rows); // print total rows
  return 'test';
}
0
batigolix