Refer to the title, I'm trying to create a shortcode for Blog Post with Pagination. I'm able to show the blog post but the pagination is not working. I tried using the code below and the link to second page is www.mysite.com/postname/page/2 . But it goes back to www.mysite.com/postname/ when I click on the pagination link to second page.

$big = 999999999; 

    $pagination = paginate_links( array(
        'base' => str_replace( $big, '%#%', esc_url( get_pagenum_link( $big ) ) ),
        'format' => '?paged=%#%',
        'current' => max( 1, get_query_var('paged') ),
        'total' => $this->query->max_num_pages
    ) );

    $html .= $pagination;

enter image description here

enter image description here

  • $wp_query is your issue, this is the main query object global. You should use the variable used by your custom query Oct 7, 2015 at 17:47
  • Hi Pieter, I've edited the code. It should be like this. When I click on the second page, it goes back to first page.
    – KC Chai
    Oct 7, 2015 at 17:53

3 Answers 3


It is still somewhat a mystery what you need looking at all the comments and the question content.

Here are two approaches that should work


I have written a complete function that will paginate any (or almost any) query except on single post pages. It also works out of the box for static front pages. I'm not going to go into details regarding the get_paginated_numbers() pagination function. Everything you need to know is discussed in my answer here, so feel free to check it out. And don't forget to modify it to suit your exact needs.

Here is a basic shortcode to showcase the usage

add_shortcode( 'paginate_shortcode', function ()
    if ( get_query_var('paged') ) { 
        $current_page = get_query_var('paged'); 
    }elseif ( get_query_var('page') ) { 
        $current_page = get_query_var('page'); 
        $current_page = 1; 

    $q = new WP_Query( ['posts_per_page' => 1, 'paged' => $current_page] );
    return $q->posts[0]->post_title . '</br>' . get_paginated_numbers( ['query' => $q] );

You can use [paginate_shortcode] on any page, it will display something like this

enter image description here

Note that the post title changes as the links changes


Single posts with paginated sub queries are not really meant to be. If you are going to use your shortcode on a single post page (which I discourage) like for related posts, you can use the approach that I posted in this answer. It is quite extensive, so I'm not going to repost it here. Feel free to check it out and modify as needed


paged is the query var for archive pagination, and /page/n/ is the format for archive pagination URLs. Single posts use page and the format is /postname/n/, where n is the page number. Your links are redirecting because they are an invalid format.

  • hi Milo, could you probably provide a code sample on how to fix this issue? Thanks
    – KC Chai
    Oct 10, 2015 at 10:24
  • Single posts have pagination? I was unaware of that. What might be the possible use case?
    – Sisir
    Oct 10, 2015 at 17:44
  • @KCChai - the simplest solution is to use wp_link_pages to generate the pagination links. you can see how it works in source.
    – Milo
    Oct 10, 2015 at 18:18
  • @Sisir i I suppose for long posts you want split across multiple pages. If you insert the <!--nextpage--> quicktag and view the post in one of the core themes, you will see the pagination links they generate.
    – Milo
    Oct 10, 2015 at 18:22
  • 1
    @KCChai - perhaps you should edit your question and add The Loop code so that we know what's going on in your loop. Also it is necessary to insert <!--nextpage--> tag through 'Text' mode of the editor. So please confirm on that too. Oct 11, 2015 at 4:41

Ok buddy add this code to your functions.php

//This function is responsible for splitting posts and pages using <!--nexpage-->
function my_link_pages() {
$paged_page_nav = wp_link_pages(
            'before' => '<div class="page-navigation"><ul><li class="pages">' . esc_html__( 'Pages:', 'domain' ) . '</li>',
            'after' => '</ul></div>',
            'link_before' => '<span>',
            'link_after' => '</span>',
            'echo' => false

//Add "current" and "page_divide" classes to our links
//READ: http://wordpress.stackexchange.com/questions/17421/wp-link-page-wrap-current-page-element
// Now let's wrap the nav inside <li>-elements
$current_class = 'current';
$classes = 'page_divide';
$paged_page_nav = str_replace( '<a', '<li class="'. $classes .'"><a' ,$paged_page_nav );
$paged_page_nav = str_replace( '</span></a>', '</a></li>', $paged_page_nav );
$paged_page_nav = str_replace( '"><span>', '">', $paged_page_nav );
//Add "current" class
$paged_page_nav = str_replace( '<span>', '<li class="'. $current_class .'">', $paged_page_nav );
$paged_page_nav = str_replace( '</span>', '</li>', $paged_page_nav );
echo  $paged_page_nav ;

Then call it in your single.php like so:

<?php my_link_pages(); ?>

Make sure that you add <!--nexpage--> on your Post Edit screen (Select Text NOT Visual)

Your Answer

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

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