0

I'm having an issue with pagination. On my site I'm using the plugin "Daisycon affiliate marketing plugin". I would like display the products that are stored in a custom database table (created by the plugin) on my website.

This is working, but I have an issue with the pagination to work correctly. The stupid thing is that I had it working, but suddenly it seems to be broken and I can't detect what has changed since then.

The problem is that the URLs that are used in the page links, are only correct on the first page. So from there you can nicely navigate to pagenum=2, pagenum=3 etc. However: if you then are on pagenum=2 (for example), all the page links that are shown then are linking to the current page, so to pagenum=2. To see what I mean, see for example http://www.online-medicijnen-bestellen.nl/afslanken-overgewicht/ and try to navigate to the next pages.

Below is my code. Does anyone see what is causing this? I already spent a few hours looking for the problem. I'm a relative newbie when it comes to PHP, so please be gentle and patient ;)

<form action="#" method="get" name="sorteer">
<select style="width:200px; float:right; margin-bottom:20px;" name="sortorder" onchange="this.form.submit()">
    <option value="">Sorteer op...</option>
    <option value="title ASC">Titel A-Z</option>
    <option value="price DESC">Hoogste prijs</option>
    <option value="price ASC">Laagste prijs</option>
</select>
</form>

<?php

global $wpdb;
// Nodig om de Wordpress database aan te kunnen spreken

$category   =   get_post_meta(get_queried_object_id(), 'Category', true);
// De property Category van de pagina op basis waarvan de producten van die categorie worden opgevraagd

$sort       =   $_GET['sortorder'];

// Haalt de gekozen optie van sortering op als URL-parameter

if ( empty($sort) ) {
$sortorder = "";
            } else {
$sortorder = "ORDER BY " . $sort;
            }
// Als er geen sorteeroptie is gekozen, sorteer dan niet, anders op basis van de gekozen sorteeroptie

$pagenum = isset( $_GET['pagenum'] ) ? absint( $_GET['pagenum'] ) : 1;
// Haal het pagina-nummer op als URL-parameter

$limit = 20;
// Dit bepaalt het aantal producten per pagina

$offset = ( $pagenum - 1 ) * $limit;
// Dit bepaalt welk product als eerste wordt getoond op de pagina

$prepared   =   $wpdb->prepare("SELECT * FROM productfeed WHERE category LIKE '$category' ". $sortorder ." LIMIT $offset, $limit");
// Beschermt de query tegen SQL-injectie

$entries = $wpdb->get_results($prepared);
// De SQL-query die de producten ophaalt (van de juiste categorie, op de gekozen manier gesorteerd en op basis van het pagina-nummer de juiste subset)

echo "<table class=product-list>";
foreach($entries as $product) {
    echo "<tr style=cursor:pointer onclick=window.open('".$product->link."')>";
        echo "<td class=buy-image><img src='".$product->image."'/></td>";
        echo "<td class=buy-text><button type=button class=buy-button>€ ".str_replace(".",",",$product->price)."</button><p class=title>".$product->title."</p><p>".$product->description."</p></td>";
    echo "</tr>"; 
}
echo "</table>";
// Hier wordt de tabel opgebouwd die de producten toont

$prepared2  =   $wpdb->prepare("SELECT COUNT(title) FROM productfeed WHERE category LIKE '$category'");
// Beschermt de query tegen SQL-injectie

$total = $wpdb->get_var($prepared2);
// Dit berekent het totaal aantal producten in deze categorie

$num_of_pages = ceil( $total / $limit );
// Dit berekent op basis van het totaal aantal producten en het aantal producten per pagina, hoeveel pagina's er moeten komen

$page_links = paginate_links( array(
'base' => add_query_arg( 'pagenum', '%#%' ),
'format' => '',
'prev_text' => __( '← Vorige', 'aag' ),
'next_text' => __( 'Volgende →', 'aag' ),
'total' => $num_of_pages,
'current' => $pagenum
) );
// Deze array bevat alle pagina-links en bijbehorende attributen

if ( $page_links ) {
echo '<div class="tablenav"><div class="tablenav-pages" style="margin: 1em 0">' . $page_links . '</div></div>';
}
// Als er pagina-links zijn, zet ze dan op deze manier neer.

?>

edit:

@Milo thanks for your tip about using prepare the right way. I changed it. However, it's still not solving the problem. The code I use now is:

<form action="#" method="get" name="sorteer">
<select style="width:200px; float:right; margin-bottom:20px;" name="sortorder" onchange="this.form.submit()">
    <option value="">Sorteer op...</option>
    <option value="title ASC">Titel A-Z</option>
    <option value="price DESC">Hoogste prijs</option>
    <option value="price ASC">Laagste prijs</option>
</select>
</form>

<?php

global $wpdb;
// Nodig om de Wordpress database aan te kunnen spreken

$category   =   get_post_meta(get_queried_object_id(), 'Category', true);
// De property Category van de pagina op basis waarvan de producten van die categorie worden opgevraagd

$sort       =   $_GET['sortorder'];
// Haalt de gekozen optie van sortering op als URL-parameter

if ( empty($sort) ) {
$sortorder = "title ASC";
            } else {
$sortorder = $sort;
            }
// Als er geen sorteeroptie is gekozen, sorteer dan niet, anders op basis van de gekozen sorteeroptie

$pagenum = isset( $_GET['pagenum'] ) ? absint( $_GET['pagenum'] ) : 1;
// Haal het pagina-nummer op als URL-parameter

$limit = 20;
// Dit bepaalt het aantal producten per pagina

$offset = ( $pagenum - 1 ) * $limit;
// Dit bepaalt welk product als eerste wordt getoond op de pagina

$prepared   =   $wpdb->prepare( "SELECT * FROM productfeed WHERE category LIKE %s ORDER BY %s LIMIT %d, %d", $category, $sortorder, $offset, $limit);
// Beschermt de query tegen SQL-injectie

$entries = $wpdb->get_results($prepared);
// De SQL-query die de producten ophaalt (van de juiste categorie, op de gekozen manier gesorteerd en op basis van het pagina-nummer de juiste subset)

echo "<table class=product-list>";
foreach($entries as $product) {
    echo "<tr style=cursor:pointer onclick=window.open('".$product->link."')>";
        echo "<td class=buy-image><img src='".$product->image."'/></td>";
        echo "<td class=buy-text><button type=button class=buy-button>€ ".str_replace(".",",",$product->price)."</button><p class=title>".$product->title."</p><p>".$product->description."</p></td>";
    echo "</tr>"; 
}
echo "</table>";
// Hier wordt de tabel opgebouwd die de producten toont

$prepared2  =   $wpdb->prepare( "SELECT COUNT(title) FROM productfeed WHERE category LIKE %s", $category);
// Beschermt de query tegen SQL-injectie

$total = $wpdb->get_var($prepared2);
// Dit berekent het totaal aantal producten in deze categorie

$num_of_pages = ceil( $total / $limit );
// Dit berekent op basis van het totaal aantal producten en het aantal producten per pagina, hoeveel pagina's er moeten komen

$page_links = paginate_links( array(
'base' => add_query_arg( 'pagenum', '%#%' ),
'format' => '',
'prev_text' => __( '← Vorige', 'aag' ),
'next_text' => __( 'Volgende →', 'aag' ),
'total' => $num_of_pages,
'current' => $pagenum
) );
// Deze array bevat alle pagina-links en bijbehorende attributen

if ( $page_links ) {
echo '<div class="tablenav"><div class="tablenav-pages" style="margin: 1em 0">' . $page_links . '</div></div>';
}
// Als er pagina-links zijn, zet ze dan op deze manier neer.

?>
2
  • Do you have debugging enabled? Your code uses prepare incorrectly which will trigger an error.
    – Milo
    Commented Dec 31, 2014 at 16:24
  • Enabling debugging doesn't give me any errors... Commented Dec 31, 2014 at 16:46

1 Answer 1

1

I was actually dealing with this same issue earlier today. I compared the code I'd written for a site using paginate_links() a few weeks prior ( where it worked ) and the site I was working on today ( where it didn't work ) and found the deal-breaker: when you associate the page number in either the base or format param with a url param, you have to define add_args in your arguments.

It can be as simple as assigning an empty array to add_args. The code below will work for you.

$page_links = paginate_links( array(
    'base'      => add_query_arg( 'pagenum', '%#%' ),
    'format'    => '',
    'prev_text' => __( '← Vorige', 'aag' ),
    'next_text' => __( 'Volgende →', 'aag' ),
    'total'     => $num_of_pages,
    'current'   => $pagenum,
    'add_args'  => array(),
) );

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.