1

I have a custom page template defined and working properly. On this specific page, I want to list a lot of links, and paginate them, to display 100 links per page.

Here is the code in my template file, working exactly like I want

<div class="container">
<ul class="row listing-items">
    <?php
        $paged = ( get_query_var('paged') ) ? get_query_var('paged') : 1;
        $custom_args = array(
            'post_type' => 'page',
            'posts_per_page' => 90,
            'paged' => $paged,
            'order' => 'ASC',
            'orderby' => 'title',
            'post__not_in' => array('6','6371','9522','5038','6380','9521','6385','9276','4159','4087','4085','4082'),
            'post_parent__in' => array('13', '154', '127', '162', '123', '167', '159', '121','18675','18676','18677','18678','18679','18680','18681','18682','18683','18684','18685','18687','18688','18689','18690','18691','18692','18693','18695','18696','18697','18699','18700','18701','18702','18703','18704','18694','18709','18705','18710','18706','18707','18718','18719','18720','18721','18722','18723','18724','18725','18726','18711','18727','18728','18729','18730','18731','18732','18716','18733','18734','18712','18735','18736','18737','18738','18739','18740','18741','18742','18743','18744','18745','18746','18717','18747','18686','18708','18748','18713','18749','18750','18751','18714','18752','18698','18753','18754','18755','18757','18758','18759','18760','18715','18761','18762','18756'),
        );
        $wp_query = new WP_Query( $custom_args );
        if ( $wp_query->have_posts() ) {
            while ( $wp_query->have_posts() ) : $wp_query->the_post();
                echo '<li class="listing-item col-12 col-sm-12 col-md-12 col-lg-6 col-xl-6">';
                echo '<a href="'.get_the_permalink().'">Voiture '.get_the_title().'</a></li>';
            endwhile;
            wp_reset_postdata();
        }
    ?>
</ul>

Now, for SEO purposes, I want to add in my header rel Next and Prev, so Google understand the pagination and can understand which page is the current one, and which page is next and prev.

Here is my code in functions.php

function rel_next_prev() {
global $paged;

if ( get_previous_posts_link() ) {
    echo '<link rel="prev" href="'.get_pagenum_link( $paged - 1 ).'" />';
}
if ( get_next_posts_link() ) {
    echo '<link rel="next" href="'.get_pagenum_link( $paged + 1 ).'" />';
}
}
add_action( 'wp_head', 'rel_next_prev' );

Unfortunately, this is partially working. I always get the Rel Prev link in the header, but is not currently based on the query I did. Let me explain:

When my query is set, I have 19 pages, under this format:

http://localhost:3000/villes/page/2/

So If I change the URL to be (404)

    http://localhost:3000/villes/page/222/

I still get rel Prev with 221 in the header.

So to resume:

How do I properly set rel next/prev in the header based on the current query I'm doing?

Thanks!

2 Answers 2

2

After a huge night overthinking this, and thanks to Joost de Valk (Yoast SEO plugin author), I found the solution.

As per this thread: https://github.com/Yoast/wordpress-seo/issues/437 , what I want to achieve the way I do, is undoable, or at least, a very bad practice.

If you want your custom query to have the default pagination and rel next prev in the header, you need to call it before get_header();

THEORIC SOLUTION

To make your custom query work with default WP and Yoast functions, you need to:

  1. Put your query BEFORE get_header();
  2. Be sure your query has the default name provided by WP, which is $wp_query
  3. That being said, you will need to create a specific page template for your query, so you can set your query before getting the header.

PRACTIC SOLUTION

For the previous code I had, which was working with get_template_part();.

  1. Create a custom page-template, refering to the page ID or the page slug. More on this here: https://developer.wordpress.org/themes/template-files-section/page-template-files/

  2. Set your custom query before the get_header(); function.

  3. Be sure to re-adapt your code, so it displays the way you want.

Here is my code, which is working as expected. Be sure to keep the rel_next_prev(); function I placed in my functions.php

Final Result:

<?php
$paged = ( get_query_var('paged') ) ? get_query_var('paged') : 1;
$custom_args = array(
    'post_type' => 'page',
    'posts_per_page' => 90,
    'paged' => $paged,
    'order' => 'ASC',
    'orderby' => 'title',
    'post__not_in' => array('6','6371','9522','5038','6380','9521','6385','9276','4159','4087','4085','4082'),
    'post_parent__in' => array('13', '154', '127', '162', '123', '167', '159', '121','18675','18676','18677','18678','18679','18680','18681','18682','18683','18684','18685','18687','18688','18689','18690','18691','18692','18693','18695','18696','18697','18699','18700','18701','18702','18703','18704','18694','18709','18705','18710','18706','18707','18718','18719','18720','18721','18722','18723','18724','18725','18726','18711','18727','18728','18729','18730','18731','18732','18716','18733','18734','18712','18735','18736','18737','18738','18739','18740','18741','18742','18743','18744','18745','18746','18717','18747','18686','18708','18748','18713','18749','18750','18751','18714','18752','18698','18753','18754','18755','18757','18758','18759','18760','18715','18761','18762','18756'),
);
$wp_query = new WP_Query( $custom_args );
get_header();
get_template_part('template-parts/headers/header', 'listing');
?>

<div class="container">
    <ul class="row listing-items">
        <?php
        if ( $wp_query->have_posts() ) {
            while ( $wp_query->have_posts() ) :
                $wp_query->the_post();
                ?>
                <li class="listing-item col-12 col-sm-12 col-md-12 col-lg-6 col-xl-6">
                    <a href="<?php get_the_permalink(); ?>">Serrurier <?php the_title();?></a></li>
            <?php
            endwhile;
            wp_reset_postdata(); // reset the query
        }
        ?>
    </ul>

    <div class="row pagination">
        <?php $paginationArgs = array(
            'base'            => get_pagenum_link(1) . '%_%',
            'format'          => 'page/%#%/',
            'total'           => $wp_query->max_num_pages,
            'current'         => $paged,
            'show_all'        => true,
            'end_size'        => 1,
            'mid_size'        => 1,
            'prev_next'       => True,
            'prev_text'       => __('&laquo;'),
            'next_text'       => __('&raquo;'),
            'type'            => 'plain',
            'add_args'        => false,
            'add_fragment'    => ''
        );
        ?>
        <div class="col-12 heading">
            <span>Page <?php echo $paged; ?> sur <?php echo $wp_query->max_num_pages; ?></span>
        </div>

        <div class="col-12 items">
            <?php echo paginate_links($paginationArgs); ?>
        </div>
    </div>


</div>

<?php
get_footer();
?>
0

I've been looking at the same thing but in my case I was not able to call the query before get_header() so I've found another solution here: https://easywpcode.com/wordpress-add-rel-prev-next-meta-tags-for-custom-query-loop/

I'm pasting it here in case is removed for some reason:

When we use custom query loop in wordpress, we lose SEO befenits such as the rel prev/next meta tags that’s in the and improves how Google reads our website.

This code will read the custom query pagination and will display those tags in the head section of the pages.

Paste this into your theme’s functions.php and edit the following attributes:

Instead of “22” (the first “if”) – change to your custom blog page. “posts_per_page” is now “10”. Change this number according to your posts_per_page pagination links in your custom blog page. (Optional) If our custom query reads another post type but the regular “post”, change the “post_type” parameter to your cpt name instead of “post”.

add_action( 'wp_head', 'rel_next_prev' );
function rel_next_prev(){
     
    global $paged;
     
    if ( get_the_ID() == 22 )
    {
        $paged = (get_query_var('paged')) ? get_query_var('paged') : 1;
 
        $data= new WP_Query(array(
            'post_type'=>'post', // your post type name
            'posts_per_page' => 10, // post per page
            'paged' => $paged,
        ));
 
        if($data->have_posts()) {
              
            $total_pages = $data->max_num_pages;
             
            if ($total_pages > 1){
                $current_page = max(1, get_query_var('paged'));
            }
             
            if ($total_pages > $paged) { $next_num = $paged + 1; }
            if ($paged > 1) { $prev_num = $paged - 1; }
             
            if ( $prev_num ) { ?>
             
            <link rel="prev" href="<?php echo get_pagenum_link( $paged - 1 ); ?>" />
            <?php } if ( $next_num ) { ?>
             
            <link rel="next" href="<?php echo get_pagenum_link( $paged +1 ); ?>" />
            <?php
            }
             
        }
         
    }
}

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.