Understanding the WordPress Loop
One of the most basic (and yet powerful) features inside WordPress is The Loop, this small piece of code that we use over and over again. And yet, I find people who called themselves a WordPress expert and don't know what it is, that's… sad.
Recently the company I work on bought another company overseas, and they asked me to interview a few people to make sure they know a bit about WordPress, PHP, Frontend and so on. My first interview went quite well, until I asked “How do we start The Loop in WordPress?”, the answer shocked me. He didn't know what the loop even was.
The Loop is a feature pretty easy to understand, so I decided to write a little bit about it.
What is a loop?
If you are a programmer, you surely know what a loop is, and if not… Really?
When we are writing code, sometimes we need some block of code to be used more than once, we could just write the same code over and over again but that's just a waste of time, in those cases we use a loop, so basically, a loop only repeats stuff. For example, if we want to display the numbers from one to ten, we could do this:
1echo "1n";2echo "2n";3echo "3n";4echo "4n";5echo "5n";6echo "6n";7echo "7n";8echo "8n";9echo "9n";10echo "10n";11
Just so you know, I wrote all that, and it was tiring… Instead, I should have just done this:
1for ( $number = 1; $number <= 10; $number++ ) {2 echo $number . "n";3}4
So much easier.
BTW I used a for
loop, there are several types of loops. WordPress,
for instance, uses a while
loop.
What is “The Loop”?
Now we know what a loop is, but what makes WordPress' loop so special that it makes it the loop? Well, without The Loop, WordPress wouldn't show us what we want to see, that being our posts.
The Loop performs a ton of actions under the hood so that we only worry about how to display our posts, and not about how to retrieve our posts. A very basic loop (taken from Twentythirteen) looks like this:
1<?php if ( have_posts() ) : ?>2 <?php /* The loop */ ?>3 <?php while ( have_posts() ) : the_post(); ?>4 <?php get_template_part( 'content', get_post_format() ); ?>5 <?php endwhile; ?>6 <?php twentythirteen_paging_nav(); ?>7<?php else : ?>8 <?php get_template_part( 'content', 'none' ); ?>9<?php endif; ?>10
Let's keep in mind that when we access any page in WordPress, there's a global
query taking place, that means WordPress already knows which page we are visiting
and there's already a $wp_query
object with all the information we need, now let's
see what the loop does.
if ( have_posts() ):
First of all, this functions checks the $wp_query object and returns true if the object has posts in it.while ( have_posts() ):
Now, this is the real start of the loop, as long ashave_posts()
is true, let's run the rest of the code inside.the_post()
: Now that we are inside the loop, we need to populate our$post
object, this function also firessetup_postdata()
which checks for things like the number of pages inside the post.get_template_part( 'content', get_post_format() )
: Now, we have our $post object complete, it's time to show it to the world, we could just insert the markup and functions likethe_title()
andthe_content()
right here, but it's a good practice to keep things clean by including a template (I plan on talking aboutget_template_part
in another post).endwhile
: We already included the template to display the posts, so we can just end the loop, remember, as long as there are posts in the query, the loop will be in action.twentythirteen_paging_nav()
: This function is specific to this theme, basically it just displays navigation links in case there's more posts in the page.else
: If the query was empty, or if have_posts returned false, then we should let the user know by including a special template for these embarrassing situations.endif
: Finish the if statement, completely finish the loop
Using The Loop with custom queries
Usually we use The Loop along with the main query, or the $wp_query
object, but
what happens if by any reason we need to use a custom query?
We could modify the query by using query_posts, but I don't recommend it because it in fact modifies the main query, and it usually brings more problems than solutions, the real solution is to just create a new query.
The get_posts method
The function get_posts
is a way to create small custom loops, it accepts all
the parameters of WP_Query
and returns an array with the result, that way we
can use a foreach
loop to work with the posts:
1$posts = get_posts( $args );2foreach ( $posts as $post ) :3 setup_postdata( $post );4?>5 <h2><?php the_title(); ?></h2>6 <?php the_content(); ?>7<?php8endforeach;9wp_reset_postdata();10
Notice how we need to fire setup_postdata
manually? That is because we don't
use the_post
in this loop.
The “new query” method
In my personal experience, I have had issues when using get_posts in bigger loops, that is why in those cases I prefer to use a new WP_Query. This creates a new query completely independent of the main query, and we can use the WordPress loop without any worries.
1$my_query = new WP_Query( $args );2if ( $my_query->have_posts() ):3 while ( $my_query->have_posts() ) : $my_query->the_post();4?>5 <h2><?php the_title(); ?></h2>6 <?php the_content(); ?>7<?php8 endwhile;9 wp_reset_postdata();10endif;11?>12
As you can see, it's pretty much the same loop as the one we use with the main
query, the difference being the constant use of $my_query
, this is necessary
because the functions have_posts
and the_post
are actually aliases that point to
the $wp_query
object, so when we call have_posts
we are actually calling $wp_query->have_posts
,
that's why we need to specify that we are calling the function in our new $my_query
object.
Outside The Loop
When reading tutorials and articles about WordPress, you often see the phrases “inside the loop” or “outside the loop”, what do these mean?
Inside the loop must be pretty obvious right now, everything between the
while
and endwhile
, or foreach
and endforeach
tags is inside the loop, that means
it uses either the main query, or a custom query, and that our $post
object is available.
Outside the loop, however, is everything outside those tags, it does not use
any query and the $post
object is not available. How could that be useful?
Well, let's say you have a custom sidebar in your posts, this sidebar must display a specific custom field called “mood” that belongs to the current post. But the sidebar is outside the loop, how can I access the post data?
Before, when I said that $post
is not available, I meant is not automatically
available, remember, when we access any page in WordPress, there's a main query
taking place. Even if we don't have a loop in the sidebar, we do have a $wp_query
and a $post
object somewhere, we just need to call them.
1<?php2 global $post;3 $mood = get_post_meta( $post->ID, 'mood', true );4?>5<p>I'm feeling <?php echo $mood; ?></p>6
Since $post
is a global variable, that means it's always available for us to
use, we just need to know how to call it, just like an old partner.
Conclusion
As you can see, The Loop is pretty easy to understand, and incredibly useful. You can be sure that no matter what page of WordPress are you in, there's always a loop in action. So I hope this small article helped you to understand a little more about our friend The Loop.