Search code examples
pythonpaginationpylonsgenshiturbogears2

How to keep query parameters during pagination with webhelpers.paginate


I look an example of paginating from http://rapidprototype.ch/bg2docs/tg2pagination.html for my Turbogears 2 project and it works great but, I have a problem regarding my query parameters when I change the page I'm looking.

This is what I have in my controller when listing.

def list(self, page=1, **kw):
    q = ""

    if kw.has_key('q'):
        log.debug("searching %s" % kw)
        q = kw['q']

    if kw.has_key('all'):
        q = ""

    products = DBSession.query(model.Product).filter(
        or_(model.Product.name.like('%%%s%%' % q),
            model.Product.description.like('%%%s%%' % q),
            model.Product.model.like('%%%s%%' % q),
            model.Product.code.like('%%%s%%' % q))).all()

    def get_link(product):
        return Markup("""<a href="form?id=%s">%s</a>""" % (product.id, product.id))

    product_fields = [
        (Markup("""<a href="?s=id">Id</a>"""), get_link),
        (u'Name', 'name'),
        (u'Model', 'model'),
        (u'Code', 'code'),
        (u'Description', 'description')]

    product_grid = MyDataGrid(fields = product_fields)

    currentPage = paginate.Page(products, page, items_per_page=50)

    return dict(currentPage=currentPage, 
        title=u'Products List', item=u'product', items=u'products',
        data=currentPage.items, 
        grid=product_grid,
        page=u'Search %s results' % q,
        q=q,
        hits=len(products))

This is the html template fragment

<h1>List of ${items}</h1>
<form action="list" method="get">
   <input name="q" type="text" value="${value_of('q', default='')}"/>
   <input type="submit" value="Search"/> <input type="submit" name="all" value="All"/>
</form>
${hits} ${items} found
<p class="pagelist">${currentPage.pager(format='$link_first ~3~ $link_last')}</p>
<div>
  ${grid(data)}
</div>
<p><a href="${tg.url('form')}">Add a ${item}</a></p>

The searches works fine resulting in links like this '/list?q=cable' but when I click some of the paginating pages "1,2...8,9" turns to '/list?page=2'

How do I add my previous query parameter or any other parameters to the link?


Solution

  • After experimenting on the shell for a while I think I found a solution.

    There's a kwargs dictionary defined in currentPage (after being assigned from paginate.Page), so I made some experiments sending parameters and it worked. This is how.

    currentPage = paginate.Page(products, page, items_per_page=50)
    
    currentPage.kwargs['q'] = q
    
    return dict(currentPage=currentPage, 
        title=u'Products List', item=u'product', items=u'products',
        data=currentPage.items, 
        grid=product_grid,
        page=u'Search %s results' % q,
        q=q,
        hits=len(products))
    

    now I get this kind of links: '/list?q=cable&page=2' still wondering if it is the best solution or the best practice