mrjayviper
mrjayviper

Reputation: 2388

How to paginate using Zend2/Doctrine combo (using the Doctrine provided paginator adapter)?

I've been looking for examples/guides on how to do what I asked.

I've found several examples and "best" I've found yet is this one => http://blog.loftdigital.com/blog/doctrine-plus-zf2-tips-pagination

2 problems

  1. I'm not really sure if my paginator object contains the right number of records (I limited it to 5 records on my adapter object)

  2. I don't know how to traverse the paginator object in my view file. it seems very complex. I did a print_r on the object enclosing the thing in a pre HTML tag and it's easily 20+K lines on my text editor (after copy/paste)

Can you please help?

thank you very much


my controller code based from the example (not really working but no zend/doctrine errors too. problem is that it gives me all the records instead of just 10)

$directory->populate($form->getData());
$adapter = new DoctrineAdapter(new ORMPaginator($directoryDao->searchStaffDirectory($this->getEntityManager()->createQueryBuilder(), $directory)));
$adapter->getItems(0, 5);
//var_dump($adapter->getItems(0, 5)); **//display the corrent number of records**

$paginator = new Paginator($adapter);
$paginator->setDefaultItemCountPerPage(5);
$page = (int)$this->params()->fromQuery("page");
if($page) $paginator->setCurrentPageNumber($page);

return array('staffList' => $paginator);

my DirectoryDAO class (the relevant parts)

public function searchStaffDirectory(QueryBuilder $queryBuilder, DirectoryModel $directory) {
    $conditions = new Andx;

    $queryBuilder
            ->select('directory')
            ->from('Directory\Model\DirectoryModel', 'directory');
    if (strlen($directory->surnameSearch)) {
         $conditions->add($queryBuilder->expr()->like('directory.surnameSearch', "'".preg_replace('/\s+/', '', $directory->surnameSearch)."%'"));
    }
    if (strlen($directory->surnameSoundsSearch)) {
         $conditions->add($queryBuilder->expr()->like('directory.surnameSoundsSearch', preg_replace('/\s+/', '', $directory->surnameSoundsSearch)));
    }
    if (strlen($directory->firstnameSearch)) {
         $conditions->add($queryBuilder->expr()->like('directory.firsnameSearch', preg_replace('/\s+/', '', $directory->firstnameSearch)));
    }
    if (strlen($directory->telephoneNumber)) {
         $conditions->add($queryBuilder->expr()->like('directory.telephoneNumber', preg_replace('/\s+/', '', $directory->telephoneNumber)));
    }
    if (strlen($directory->departmentSearch)) {
         $conditions->add($queryBuilder->expr()->like('directory.departmentSearch', preg_replace('/\s+/', '', $directory->departmentSearch)));
    }
    if (strlen($directory->roleSearch)) {
         $conditions->add($queryBuilder->expr()->like('directory.roleSearch', preg_replace('/\s+/', '', $directory->roleSearch)));
    }
    if ($conditions->count()) {
            $queryBuilder->andWhere($conditions);
    }
    $queryBuilder
            ->orderBy('directory.surname');

    return $queryBuilder->getQuery();
}

my DirectoryModel class

<?php

namespace Directory\Model;

use Doctrine\ORM\Mapping;

use Zend\InputFilter\Factory;
use Zend\InputFilter\InputFilter;
use Zend\InputFilter\InputFilterAwareInterface;
use Zend\InputFilter\InputFilterInterface;

/**
 * @Mapping\Entity
 * @Mapping\Table(name="staffdirectory_vw")
 */
class DirectoryModel {
    /**
     * 
     * @Mapping\Id
     * @Mapping\Column(name="mytable_pk", type="integer", unique=true)
     */
    protected $pk;

    /**
     * 
     * @Mapping\Column(name="mytable_id", type="string")
     */
    protected $id;

    /**
     *
     * @Mapping\Column(name="mytable_parent_id", type="string")
     */
    protected $parentId;

    /**
     * 
     * @Mapping\Column(name="mytable_auth_code", type="string")
     */
    protected $fan;

    /**
     * 
     * @Mapping\Column(name="mytable_full_name", type="string")
     */
    protected $fullname;

    /**
     * 
     * @Mapping\Column(name="mytable_name_title", type="string")
     */
    protected $title;

    /**
     * 
     * @Mapping\Column(name="mytable_first_pref_name", type="string")
     */
    protected $firstname;

    /**
     * 
     * @Mapping\Column(name="mytable_surname", type="string")
     */
    protected $surname;

    /**
     * 
     * @Mapping\Column(name="mytable_bldg_long_desc", type="string")
     */
    protected $building;

    /**
     * 
     * @Mapping\Column(name="mytable_display_department", type="string")
     */
    protected $department;

    /**
     * 
     * @Mapping\Column(name="mytable_alias", type="string")
     */
    protected $email;

    /**
     * 
     * @Mapping\Column(name="mytable_alias_list", type="string")
     */
    protected $emailList;

    /**
     * 
     * @Mapping\Column(name="mytable_entity_type", type="string")
     */
    protected $entityType;

    /**
     * 
     * @Mapping\Column(name="mytable_org_heirarchy", type="string")
     */
    protected $organisationalHeirarchy;

    /**
     * 
     * @Mapping\Column(name="mytable_role", type="string")
     */
    protected $role;

    /**
     * 
     * @Mapping\Column(name="mytable_room", type="string")
     */
    protected $room;

    /**
     * 
     * @Mapping\Column(name="mytable_tele_number", type="string")
     */
    protected $telephoneNumber;

    /**
     * 
     * @Mapping\Column(name="mytable_tele_number_formats", type="string")
     */
    protected $telephoneNumberFormats;

    /**
     * 
     * @Mapping\Column(name="mytable_tele_rank", type="string")
     */
    protected $teleRank;

    /**
     * 
     * @Mapping\Column(name="mytable_url", type="string")
     */
    protected $url;

    /**
     * 
     * @Mapping\Column(name="mytable_search_surname", type="string")
     */
    protected $surnameSearch;

    /**
     * 
     * @Mapping\Column(name="mytable_surname_soundex", type="string")
     */
    protected $surnameSoundsSearch;

    /**
     * 
     * @Mapping\Column(name="mytable_search_first_name", type="string")
     */
    protected $firstnameSearch;

    /**
     * 
     * @Mapping\Column(name="mytable_search_department", type="string")
     */
    protected $departmentSearch;

    /**
     * 
     * @Mapping\Column(name="mytable_search_role", type="string")
     */
    protected $roleSearch;

    /**
     * 
     * @Mapping\Column(name="mytable_tele_directory", type="string")
     */
    protected $teleDirectory;

    protected $inputFilter;

    /**
     * Magic getter to expose protected properties.
     * 
     * @param string $property
     * @return mixed
     */
    public function __get($property) {
        return $this->$property;
    }

    /**
     * 
     * Magic setter to save protected properties.
     * 
     * @param string $property
     * @param mixed $value
     */
    public function __set($property, $value) {
        $this->$property = $value;
    }

    /**
     * Convert the object to an array.
     * 
     * @return array
     */
    public function getArrayCopy() {
        return get_object_vars($this);
    }

    /**
     * Populate from an array.
     * 
     * @param array $data
     */
    public function populate($data = array()) {
        $this->pk = isset($data['pk']) ? $data['pk'] : null;
        $this->id = isset($data['id']) ? $data['id'] : null;
        $this->fan = isset($data['fan']) ? $data['fan'] : null;
        $this->fullname = isset($data['fullname']) ? $data['fullname'] : null;
        $this->surname = isset($data['surname']) ? $data['surname'] : null;
        $this->building = isset($data['building']) ? $data['building'] : null;
        $this->department = isset($data['department']) ? $data['department'] : null;
        $this->email = isset($data['email']) ? $data['email'] : null;
        $this->emailList = isset($data['emailList']) ? $data['emailList'] : null;
        $this->entityType = isset($data['entityType']) ? $data['entityType'] : null;
        $this->organisationalHeirarchy = isset($data['organisationalHeirarchy']) ? $data['organisationalHeirarchy'] : null;
        $this->role = isset($data['role']) ? $data['role'] : null;
        $this->room = isset($data['room']) ? $data['room'] : null;
        $this->telephoneNumber = isset($data['telephoneNumber']) ? $data['telephoneNumber'] : null;
        $this->telephoneNumberFormats = isset($data['telephoneNumberFormats']) ? $data['telephoneNumberFormats'] : null;
        $this->teleRank = isset($data['teleRank']) ? $data['teleRank'] : null;
        $this->url = isset($data['url']) ? $data['url'] : null;
        $this->surnameSearch = isset($data['surnameSearch']) ? $data['surnameSearch'] : null;
        $this->surnameSoundsSearch = isset($data['surnameSoundsSearch']) ? $data['surnameSoundsSearch'] : null;
        $this->firstnameSearch = isset($data['firstnameSearch']) ? $data['firstnameSearch'] : null;
        $this->departmentSearch = isset($data['departmentSearch']) ? $data['departmentSearch'] : null;
        $this->roleSearch = isset($data['roleSearch']) ? $data['roleSearch'] : null;
        $this->teleDirectory = isset($data['teleDirectory']) ? $data['teleDirectory'] : null;
    }

    public function setInputFilter(InputFilterInterface $inputFilter) {
        throw new \Exception("Not used");
    }

    public function getInputFilter() {
        if (!$this->inputFilter) {
            $inputFilter = new InputFilter();
            $factory = new Factory();

            $inputFilter->add($factory->createInput(array(
                    'name'     => 'surnameSearch',
                    'required' => false,
                    'filters'  => array(
                            array('name' => 'StripTags'),
                            array('name' => 'StringToUpper'),
                            array('name' => 'StringTrim'),
                    ),
                    'validators' => array(
                            array(
                                    'name'    => 'StringLength',
                                    'options' => array(
                                            'encoding' => 'UTF-8',
                                            'min'      => 1,
                                            'max'      => 30,
                                    ),
                            ),
                    ),
            )));
            $inputFilter->add($factory->createInput(array(
                    'name'     => 'surnameSoundsSearch',
                    'required' => false,
                    'filters'  => array(
                            array('name' => 'StripTags'),
                            array('name' => 'StringToUpper'),
                            array('name' => 'StringTrim'),
                    ),
                    'validators' => array(
                            array(
                                    'name'    => 'StringLength',
                                    'options' => array(
                                            'encoding' => 'UTF-8',
                                            'min'      => 1,
                                            'max'      => 30,
                                    ),
                            ),
                    ),
            )));
            $inputFilter->add($factory->createInput(array(
                    'name'     => 'firstnameSearch',
                    'required' => false,
                    'filters'  => array(
                            array('name' => 'StripTags'),
                            array('name' => 'StringToUpper'),
                            array('name' => 'StringTrim'),
                    ),
                    'validators' => array(
                            array(
                                    'name'    => 'StringLength',
                                    'options' => array(
                                            'encoding' => 'UTF-8',
                                            'min'      => 1,
                                            'max'      => 30,
                                    ),
                            ),
                    ),
            )));
            $inputFilter->add($factory->createInput(array(
                    'name'     => 'telephoneNumberSearch',
                    'required' => false,
                    'filters'  => array(
                            array('name' => 'Int'),
                    ),
            )));
            $inputFilter->add($factory->createInput(array(
                    'name'     => 'departmentSearch',
                    'required' => false,
                    'filters'  => array(
                            array('name' => 'StripTags'),
                            array('name' => 'StringToUpper'),
                            array('name' => 'StringTrim'),
                    ),
                    'validators' => array(
                            array(
                                    'name'    => 'StringLength',
                                    'options' => array(
                                            'encoding' => 'UTF-8',
                                            'min'      => 1,
                                            'max'      => 30,
                                    ),
                            ),
                    ),
            )));
            $inputFilter->add($factory->createInput(array(
                    'name'     => 'roleeSearch',
                    'required' => false,
                    'filters'  => array(
                            array('name' => 'StripTags'),
                            array('name' => 'StringToUpper'),
                            array('name' => 'StringTrim'),
                    ),
                    'validators' => array(
                            array(
                                    'name'    => 'StringLength',
                                    'options' => array(
                                            'encoding' => 'UTF-8',
                                            'min'      => 1,
                                            'max'      => 30,
                                    ),
                            ),
                    ),
            )));

            $this->inputFilter = $inputFilter;
        }

        return $this->inputFilter;
    }
}

Upvotes: 2

Views: 1777

Answers (1)

Tomdarkness
Tomdarkness

Reputation: 3820

I assume DoctrineAdapter is actually DoctrineORMModule\Paginator\Adapter\DoctrinePaginator just you imported it with a different name. If not, then this is the class you should be using.

Your controller should be:

$directory->populate($form->getData());
$adapter = new DoctrineAdapter(new ORMPaginator($directoryDao->searchStaffDirectory($this->getEntityManager()->createQueryBuilder(), $directory)));

$paginator = new Paginator($adapter);
$paginator->setItemCountPerPage(5);
$page = (int)$this->params()->fromQuery("page");
$paginator->setCurrentPageNumber($page);

return array('staffList' => $paginator);

No need to call getItems and when you cast $page to int then it will automatically default to the first page if no page parameter is passed.

Using the paginator in the view is more complex. First you need to implement a view script that renders the paginator. There are a number of example scripts in the ZF2 documentation which you can either use outright or base your own paginator off:

http://framework.zend.com/manual/2.2/en/modules/zend.paginator.usage.html#example-pagination-controls

To use the paginator in your actual view, you can iterate over it like any other query result to display your items:

<?php foreach($staffList as $staff): ?>

    Firstname: <?php echo $staff->firstname; ?>

    etc.

<?php endforeach; ?>

This will only display items currently for the current page that the paginator is on, which is what you want.

To display the paginator controls:

<?php echo $this->paginationControl($staffList, '<paginator type>', '<my paginator view script>', array('route' => '<route name>')); ?>

Paginator type can be: All, Elastic, Jumping, Sliding and determines how and what page numbers are displayed on the paginator controls. Sliding is the default and is most likely the best choice.

Upvotes: 2

Related Questions