So you’ve made a custom template of some sort, or you’ve tried to exclude a category from your home page. You used query_posts because that’s what all the cool kids are doing. But now when you click to go to the next page of your site, it says page 2, but you see all the same posts as page 1. Why is WordPress lying to you? Let’s take a look!
Now honestly, WordPress isn’t lying to you, it’s doing exactly what you said to do! There are a variety of ways to modify a WordPress query, some safer than others. We’ll go more in depth on the benefits and usage of each in another article, the point of this article is going to be to save your butt once you already have query_posts in place.
This article is a kind of update to one I wrote previously on my blog. WordPress changed how things worked a little, so I need to refresh the old article.
See, the thing with query_posts is, it smushes your original query. So WordPress is already set up to do certain things on certain templates. It’s got a groove. Using query_posts, you upset the groove just a little. You told WordPress what you wanted to do, but not everything. Let’s get that groove back.
First up, one possible, and common, way to write a query:
<?php // All strung together query_posts('posts_per_page=5&cat=10'); ?>
That works absolutely fine. That query says to show 5 posts per page from category 10. Let’s take a look at another way to write that out:
<?php query_posts( array ( 'posts_per_page' => 5, 'cat' => '10', )); ?>
That does the EXACT same thing. We just put all of our parameters into a nice array. Now, you may not see the benefit imediately, but imagine you a writing a complex query with fifteen parameters, can you see the benefit now? Everything in a nice list, one parameter per line.
OK, now the fix I promised. With the above code, if you have more than 5 posts, there is no way to get to them. Your older posts link will go to the next page, but your query only says to get the first five posts, you never told it you had pages! So we will add some pagination into that query.
October 2012 (WP 3.4 and later) UPDATE: It would seem that the information below is one again not accurate! These things are hard to keep up with. You can see how everything works now by reading the codex entry linked below. But in a nutshell, take a look at the 2 examples below. The first example is the one that will normally work for you now. In most circumstances you would use the ‘paged’ parameter to get your pagination working. You would use the ‘page’ variable (the second example) when running a query from a page you have set as your static front page, or from within a single post/page view which has multiple pages (using nextpage tag).
This is how we did it in my old article, this works PREVIOUS to version 3.0.2 (See the codex note).
<?php $paged = get_query_var( 'paged' ) ? get_query_var( 'paged' ) : 1; query_posts( array( 'posts_per_page' => 5, 'cat' => '10', 'paged' => $paged )); ?>
Try that one on for size, I DARE YOU! We’ve just informed WordPress that we do, in fact, have multiple pages of posts we would like it to use. And quite simply, that is it!
Now, for WordPress versions 3.0.2 and later, there has been a slight change:
<?php $paged = get_query_var( 'page' ) ? get_query_var( 'page' ) : 1; query_posts( array( 'posts_per_page' => 5, 'cat' => '10', 'paged' => $paged )); ?>
Can you spot the difference? When we set up our $paged variable, we just changed out paged for page. Done!
There you have your pagination fix. The important thing to remember here is that if you are going to use query_posts, you are totally smushing WP’s original query. As such, you have to explicitly tell WP what you want. If we’re lucky, WP 3.4 will ship with mind reading capabilities, which will certainly make these queries much easier!