get() returns the WordPress query object. Most of the time you want something simpler, so every query class has terminal methods that run the query with the arguments that fit their purpose.
- Overview
- How terminals behave
first()ids(),names(),slugs()andpluck()count()exists()- Fields
- Pagination and limits
| Method | Returns | PostQuery |
TermQuery |
UserQuery |
CommentQuery |
SiteQuery |
NetworkQuery |
|---|---|---|---|---|---|---|---|
getArguments() |
array of arguments |
✓ | ✓ | ✓ | ✓ | ✓ | ✓ |
get() |
WP_Query, WP_Term_Query, WP_User_Query, WP_Comment_Query, WP_Site_Query, WP_Network_Query |
✓ | ✓ | ✓ | ✓ | ✓ | ✓ |
first() |
the first match, or null |
✓ | ✓ | ✓ | ✓ | ✓ | ✓ |
ids() |
int[] |
✓ | ✓ | ✓ | ✓ | ✓ | ✓ |
count() |
int, the total number of matches |
✓ | ✓ | ✓ | ✓ | ✓ | ✓ |
exists() |
bool |
✓ | ✓ | ✓ | ✓ | ✓ | ✓ |
names(), slugs() |
string[] |
✓ | |||||
pluck($field) |
string[], one column |
✓ |
use Pollora\Query\PostQuery;
$post = PostQuery::select()->postType('page')->postSlug('about')->first(); // WP_Post|null
$ids = PostQuery::select()->postType('post')->limit(10)->ids(); // [42, 41, 39, ...]
$total = PostQuery::select()->postType('post')->postStatus('publish')->count();
$exists = PostQuery::select()->postType('page')->postSlug('about')->exists();A terminal method:
- works on a copy of the builder, so the builder keeps its own arguments and you can call another terminal (or
get()) afterwards; - overrides only what it needs (a limit of 1, the
fields, the count flag) and keeps your filters, order and meta/tax/date queries; - ignores the pagination that would make the result wrong (see each method).
$query = PostQuery::select()->postType('product')->limit(10)->paged(3);
$query->count(); // total number of products, not 10
$query->first(); // the first product of the query, not the first of page 3
$query->get(); // still the third page of 10 productsRuns the query with a limit of 1 and returns the first record, or null when nothing matches. It resets the offset and the page, and skips the total count.
| Class | Returns |
|---|---|
PostQuery |
WP_Post, an ID with fields('ids'), a partial object with fields('id=>parent') |
TermQuery |
WP_Term, or the first value of the fields() you chose ('ids', 'names'…). With fields('count') it returns a WP_Term: a count has no "first". |
UserQuery |
WP_User, or the first value of the fields() you chose |
CommentQuery |
WP_Comment, an ID with fields('ids') |
SiteQuery, NetworkQuery |
WP_Site, WP_Network, an ID with fields('ids') |
first() does not add an order: add one (latest(), orderBy()…) if "first" must mean something.
Return a plain list of scalars, and ask WordPress for that column only (no full objects).
ids()on every class:int[].TermQuery::names()andslugs():string[].UserQuery::pluck('user_email'): any single user column amongID,display_name,user_login,user_nicename,user_email,user_url,user_registered,user_pass,user_activation_key,user_status(andspam,deletedon multisite).pluck('all')throws aQueryException: useget().
They keep your limit, offset and page: limit(20)->ids() returns at most 20 IDs. Without a limit, WordPress' default applies (see Pagination and limits), so call limit() or, for posts, noPaging() if you need every ID.
Returns the total number of matches, whatever the limit, offset or page set on the builder (found_posts, a count query, get_total()… depending on the class). It forces the total to be computed even if you called noFoundRows().
PostQuery::select()->postType('post')->postStatus('publish')->count();
UserQuery::select()->role('subscriber')->count();
CommentQuery::select()->postId(42)->pending()->count();true when at least one record matches. It fetches a single ID, which is cheaper than count() > 0.
fields() controls what a query returns. It validates its value and throws a QueryException for anything else.
| Class | Accepted values |
|---|---|
PostQuery |
'all' (or '*'), 'ids', 'id=>parent' |
TermQuery |
'all' (or '*'), 'all_with_object_id', 'ids', 'tt_ids', 'names', 'slugs', 'count', 'id=>parent', 'id=>name', 'id=>slug' |
UserQuery |
'all' (or '*'), or one field, or an array of fields: 'ID', 'display_name', 'user_login', 'user_nicename', 'user_email', 'user_url', 'user_registered', 'user_pass', 'user_activation_key', 'user_status', 'spam', 'deleted' |
CommentQuery, SiteQuery, NetworkQuery |
'all' (or '*'), 'ids' |
select('ids') is a shortcut for select()->fields('ids'):
$ids = PostQuery::select('ids')->postType('page')->get()->posts; // WP_Query::$posts is int[]
$mails = UserQuery::select(['ID', 'user_email'])->get()->get_results(); // objects with those two fieldsEach WordPress query has its own limit behaviour, and the builders do not hide it:
| Class | Without limit() |
Notes |
|---|---|---|
PostQuery |
WordPress' Posts per page setting (10 by default) | noPaging() returns everything. paged() selects the page. |
TermQuery |
every term | |
UserQuery |
every user | paged() works with limit(). |
CommentQuery |
every comment | noFoundRows is true by default in WordPress: call noFoundRows(false) to get found_comments and max_num_pages from get(). |
SiteQuery |
every site (number => 0, WordPress alone stops at 100) |
|
NetworkQuery |
every network |
For terms, users, comments, sites and networks, WordPress applies offset only together with a limit: use skip() with limit().