Quellcode durchsuchen

Merge pull request #2656 from pulzarraider/simplepager

Added SimplePager from SonataDoctrinePhpcrAdminBundle
Thomas vor 10 Jahren
Ursprung
Commit
d2131003b4
37 geänderte Dateien mit 583 neuen und 7 gelöschten Zeilen
  1. 28 0
      Admin/Admin.php
  2. 2 0
      Datagrid/Pager.php
  3. 174 0
      Datagrid/SimplePager.php
  4. 25 2
      DependencyInjection/Compiler/AddDependencyCallsCompilerPass.php
  5. 1 0
      DependencyInjection/Configuration.php
  6. 52 0
      Resources/doc/cookbook/recipe_improve_performance_large_datasets.rst
  7. 1 0
      Resources/doc/index.rst
  8. 4 0
      Resources/translations/SonataAdminBundle.ar.xliff
  9. 4 0
      Resources/translations/SonataAdminBundle.bg.xliff
  10. 4 0
      Resources/translations/SonataAdminBundle.ca.xliff
  11. 4 0
      Resources/translations/SonataAdminBundle.cs.xliff
  12. 4 0
      Resources/translations/SonataAdminBundle.de.xliff
  13. 4 0
      Resources/translations/SonataAdminBundle.en.xliff
  14. 4 0
      Resources/translations/SonataAdminBundle.es.xliff
  15. 4 0
      Resources/translations/SonataAdminBundle.eu.xliff
  16. 4 0
      Resources/translations/SonataAdminBundle.fa.xliff
  17. 4 0
      Resources/translations/SonataAdminBundle.fr.xliff
  18. 4 0
      Resources/translations/SonataAdminBundle.hr.xliff
  19. 4 0
      Resources/translations/SonataAdminBundle.hu.xliff
  20. 4 0
      Resources/translations/SonataAdminBundle.it.xliff
  21. 4 0
      Resources/translations/SonataAdminBundle.ja.xliff
  22. 4 0
      Resources/translations/SonataAdminBundle.lb.xliff
  23. 4 0
      Resources/translations/SonataAdminBundle.lt.xliff
  24. 4 0
      Resources/translations/SonataAdminBundle.nl.xliff
  25. 4 0
      Resources/translations/SonataAdminBundle.pl.xliff
  26. 4 0
      Resources/translations/SonataAdminBundle.pt.xliff
  27. 4 0
      Resources/translations/SonataAdminBundle.pt_BR.xliff
  28. 4 0
      Resources/translations/SonataAdminBundle.ro.xliff
  29. 4 0
      Resources/translations/SonataAdminBundle.ru.xliff
  30. 4 0
      Resources/translations/SonataAdminBundle.sk.xliff
  31. 4 0
      Resources/translations/SonataAdminBundle.sl.xliff
  32. 4 0
      Resources/translations/SonataAdminBundle.uk.xliff
  33. 4 0
      Resources/translations/SonataAdminBundle.zh_CN.xliff
  34. 31 0
      Resources/views/Pager/simple_pager_results.html.twig
  35. 122 0
      Tests/Datagrid/SimplePagerTest.php
  36. 42 5
      Tests/DependencyInjection/Compiler/AddDependencyCallsCompilerPassTest.php
  37. 1 0
      Tests/DependencyInjection/ConfigurationTest.php

+ 28 - 0
Admin/Admin.php

@@ -47,6 +47,7 @@ use Knp\Menu\FactoryInterface as MenuFactoryInterface;
 use Knp\Menu\ItemInterface as MenuItemInterface;
 
 use Doctrine\Common\Util\ClassUtils;
+use Sonata\AdminBundle\Datagrid\Pager;
 
 abstract class Admin implements AdminInterface, DomainObjectInterface
 {
@@ -217,6 +218,13 @@ abstract class Admin implements AdminInterface, DomainObjectInterface
      */
     protected $perPageOptions = array(16, 32, 64, 128, 192);
 
+    /**
+     * Pager type
+     *
+     * @var string
+     */
+    protected $pagerType = Pager::TYPE_DEFAULT;
+
     /**
      * The code related to the admin
      *
@@ -2746,6 +2754,26 @@ abstract class Admin implements AdminInterface, DomainObjectInterface
         return $this->perPageOptions;
     }
 
+    /**
+     * Set pager type
+     *
+     * @param string $pagerType
+     */
+    public function setPagerType($pagerType)
+    {
+        $this->pagerType = $pagerType;
+    }
+
+    /**
+     * Get pager type
+     *
+     * @return string
+     */
+    public function getPagerType()
+    {
+        return $this->pagerType;
+    }
+
     /**
      * Returns true if the per page value is allowed, false otherwise
      *

+ 2 - 0
Datagrid/Pager.php

@@ -17,6 +17,8 @@ namespace Sonata\AdminBundle\Datagrid;
  */
 abstract class Pager implements \Iterator, \Countable, \Serializable, PagerInterface
 {
+    const TYPE_DEFAULT = 'default';
+    const TYPE_SIMPLE = 'simple';
 
     protected $page = 1;
     protected $maxPerPage = 0;

+ 174 - 0
Datagrid/SimplePager.php

@@ -0,0 +1,174 @@
+<?php
+
+/*
+ * This file is part of the Sonata package.
+ *
+ * (c) Thomas Rabaix <thomas.rabaix@sonata-project.org>
+ *
+ * For the full copyright and license information, please view the LICENSE
+ * file that was distributed with this source code.
+ */
+
+namespace Sonata\AdminBundle\Datagrid;
+
+use Doctrine\ORM\QueryBuilder;
+use Doctrine\Common\Collections\ArrayCollection;
+
+/**
+ * Simple pager
+ *
+ * @author Lukas Kahwe Smith <smith@pooteeweet.org>
+ * @author Sjoerd Peters <sjoerd.peters@gmail.com>
+ */
+class SimplePager extends Pager
+{
+    /**
+     * @var  boolean
+     */
+    protected $haveToPaginate;
+
+    /**
+     * How many pages to look forward to create links to next pages.
+     *
+     * @var int
+     */
+    protected $threshold;
+
+    /**
+     * @var int
+     */
+    protected $thresholdCount;
+
+    /**
+     * The threshold parameter can be used to determine how far ahead the pager
+     * should fetch results.
+     *
+     * If set to 1 which is the minimal value the pager will generate a link to the next page
+     * If set to 2 the pager will generate links to the next two pages
+     * If set to 3 the pager will generate links to the next three pages
+     * etc.
+     *
+     * @param integer $maxPerPage Number of records to display per page
+     * @param int     $threshold
+     */
+    public function __construct($maxPerPage = 10, $threshold = 1)
+    {
+        parent::__construct($maxPerPage);
+        $this->setThreshold($threshold);
+    }
+
+    /**
+     * Returns the exact count when there is only one page or when the current
+     * equals the last page.
+     *
+     * In all other cases an estimate of the total count is returned.
+     *
+     * @return integer
+     */
+    public function getNbResults()
+    {
+        $n = ceil(($this->getLastPage() -1) * $this->getMaxPerPage());
+        if ($this->getLastPage() == $this->getPage()) {
+            return $n + $this->thresholdCount;
+        }
+
+        return $n;
+    }
+
+    /**
+     * Get all the results for the pager instance
+     *
+     * @param mixed $hydrationMode A hydration mode identifier
+     *
+     * @return array
+     */
+    public function getResults($hydrationMode = null)
+    {
+        if ($this->results) {
+            return $this->results;
+        }
+
+        $this->results = $this->getQuery()->execute(array(), $hydrationMode);
+        $this->thresholdCount = count($this->results);
+        if (count($this->results) > $this->getMaxPerPage()) {
+            $this->haveToPaginate = true;
+
+            if ($this->results instanceof ArrayCollection) {
+                $this->results = new ArrayCollection($this->results->slice(0, $this->getMaxPerPage()));
+            } else {
+                $this->results = new ArrayCollection(array_slice($this->results, 0, $this->getMaxPerPage()));
+            }
+
+        } else {
+            $this->haveToPaginate = false;
+        }
+
+        return $this->results;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public function haveToPaginate()
+    {
+        return $this->haveToPaginate || $this->getPage() > 1;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    protected function resetIterator()
+    {
+        parent::resetIterator();
+        $this->haveToPaginate = false;
+    }
+
+    /**
+     * {@inheritDoc}
+     *
+     * @throws \RuntimeException the QueryBuilder is uninitialized.
+     */
+    public function init()
+    {
+        if (!$this->getQuery()) {
+            throw new \RuntimeException('Uninitialized QueryBuilder');
+        }
+        $this->resetIterator();
+
+        if (0 == $this->getPage() || 0 == $this->getMaxPerPage()) {
+            $this->setLastPage(0);
+            $this->getQuery()->setFirstResult(0);
+            $this->getQuery()->setMaxResults(0);
+        } else {
+            $offset = ($this->getPage() - 1) * $this->getMaxPerPage();
+            $this->getQuery()->setFirstResult($offset);
+
+            $maxOffset = $this->getThreshold() > 0
+                ? $this->getMaxPerPage() * $this->threshold + 1 : $this->getMaxPerPage() + 1;
+
+            $this->getQuery()->setMaxResults($maxOffset);
+            $this->initializeIterator();
+
+            $t = (int) ceil($this->thresholdCount / $this->getMaxPerPage()) + $this->getPage() - 1;
+            $this->setLastPage($t);
+        }
+    }
+
+    /**
+     * Set how many pages to look forward to create links to next pages.
+     *
+     * @param int $threshold
+     */
+    public function setThreshold($threshold)
+    {
+        $this->threshold = (int) $threshold;
+    }
+
+    /**
+     * @return int
+     */
+    public function getThreshold()
+    {
+        return $this->threshold;
+    }
+}

+ 25 - 2
DependencyInjection/Compiler/AddDependencyCallsCompilerPass.php

@@ -17,6 +17,7 @@ use Symfony\Component\DependencyInjection\Compiler\CompilerPassInterface;
 use Symfony\Component\DependencyInjection\Reference;
 use Symfony\Component\DependencyInjection\ContainerInterface;
 use Sonata\AdminBundle\Admin\BaseFieldDescription;
+use Sonata\AdminBundle\Datagrid\Pager;
 
 /**
  * Add all dependencies to the Admin class, this avoid to write too many lines
@@ -226,8 +227,18 @@ class AddDependencyCallsCompilerPass implements CompilerPassInterface
             }
         }
 
-        if (isset($service['label'])) {
-            $label = $service['label'];
+        if (isset($overwriteAdminConfiguration['pager_type'])) {
+            $pagerType = $overwriteAdminConfiguration['pager_type'];
+        } elseif (isset($attributes['pager_type'])) {
+            $pagerType = $attributes['pager_type'];
+        } else {
+            $pagerType = Pager::TYPE_DEFAULT;
+        }
+
+        $definition->addMethodCall('setPagerType', array($pagerType));
+
+        if (isset($overwriteAdminConfiguration['label'])) {
+            $label = $overwriteAdminConfiguration['label'];
         } elseif (isset($attributes['label'])) {
             $label = $attributes['label'];
         } else {
@@ -279,6 +290,18 @@ class AddDependencyCallsCompilerPass implements CompilerPassInterface
                 continue;
             }
 
+            // set template for simple pager if it is not already overwritten
+            if ($method[0] === 'setPagerType'
+                && $method[1][0] === Pager::TYPE_SIMPLE
+                && (
+                    !isset($definedTemplates['pager_results'])
+                    || $definedTemplates['pager_results'] === 'SonataAdminBundle:Pager:results.html.twig'
+                )
+            ) {
+
+                $definedTemplates['pager_results'] = 'SonataAdminBundle:Pager:simple_pager_results.html.twig';
+            }
+
             $methods[$pos] = $method;
             $pos++;
         }

+ 1 - 0
DependencyInjection/Configuration.php

@@ -157,6 +157,7 @@ class Configuration implements ConfigurationInterface
                             ->scalarNode('menu_factory')->defaultValue(null)->end()
                             ->scalarNode('route_builder')->defaultValue(null)->end()
                             ->scalarNode('label_translator_strategy')->defaultValue(null)->end()
+                            ->scalarNode('pager_type')->defaultValue(null)->end()
                             ->arrayNode('templates')
                                 ->addDefaultsIfNotSet()
                                 ->children()

+ 52 - 0
Resources/doc/cookbook/recipe_improve_performance_large_datasets.rst

@@ -0,0 +1,52 @@
+Improve performance of large datasets
+=====================================
+
+If your database table contains thousands of records, the database queries generated
+by SonataAdmin may become very slow. Here are tips how to improve the performance of your admin.
+
+
+Change default Pager to SimplePager
+-------------------------------------
+
+Default `Pager` is counting all rows in the table, so user can easily navigate
+to any page in the Datagrid. But counting thousands or milions of records
+can be slow operation. If you don't need to know the number of all records,
+you can use `SimplePager` instead. It doesn't count all rows, but gives user only
+information if there is next page or not.
+
+To use SimplePager in your admin just define `pager_type` inside the service definition:
+
+.. configuration-block::
+
+    .. code-block:: xml
+
+       <!-- Acme/DemoBundle/Resources/config/admin.xml -->
+       <container xmlns="http://symfony.com/schema/dic/services"
+           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+           xsi:schemaLocation="http://symfony.com/schema/dic/services/services-1.0.xsd">
+           <services>
+              <service id="sonata.admin.post" class="Acme\DemoBundle\Admin\PostAdmin">
+                 <tag name="sonata.admin" manager_type="orm" group="Content" label="Post" pager_type="simple" />
+                 <argument />
+                 <argument>Acme\DemoBundle\Entity\Post</argument>
+                 <argument />
+             </service>
+          </services>
+       </container>
+
+
+    .. code-block:: yaml
+
+       # Acme/DemoBundle/Resources/config/admin.yml
+       services:
+           sonata.admin.post:
+               class: Acme\DemoBundle\Admin\PostAdmin
+               tags:
+                   - { name: sonata.admin, manager_type: orm, group: "Content", label: "Post", pager_type: "simple" }
+               arguments:
+                   - ~
+                   - Acme\DemoBundle\Entity\Post
+                   - ~
+
+
+.. note:: The `pager_results` template is automatically changed to `SonataAdminBundle:Pager:simple_pager_results.html.twig` if it's not already overloaded.

+ 1 - 0
Resources/doc/index.rst

@@ -62,3 +62,4 @@ Cookbook
    cookbook/recipe_custom_action
    cookbook/recipe_customizing_a_mosaic_list
    cookbook/recipe_overwrite_admin_configuration
+   cookbook/recipe_improve_performance_large_datasets

+ 4 - 0
Resources/translations/SonataAdminBundle.ar.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>عرض مراجعة</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>%count% النتائج</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.bg.xliff

@@ -318,6 +318,10 @@
                 <source>label_view_revision</source>
                 <target>Преглед на версията</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>Един резултат|%count% резултата</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.ca.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Mostrar revisió</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 resultat|%count% resultats</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.cs.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Zobrazit revizi</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>alespoň</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 záznam|%count% záznamy|%count% záznamů</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.de.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Version anzeigen</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>mehr als</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>{1}1 Ergebnis|]1,Inf] %count% Ergebnisse</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.en.xliff

@@ -330,6 +330,10 @@
                 <source>label_compare_revision</source>
                 <target>Compare revision</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>at least</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 result|%count% results</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.es.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Ver Revisión</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 resultado|%count% resultados</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.eu.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Rebisioa erakutsi</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>Emaitza bat|%count% emaitza</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.fa.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>دیدن اصلاحیه</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>یک نتیجه|%count% نتیحه</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.fr.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Afficher la révision</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>au moins</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 résultat|%count% résultats</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.hr.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Vidi reviziju</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>%count% rezultat|%count% rezultata|%count% rezultata</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.hu.xliff

@@ -330,6 +330,10 @@
                 <source>label_compare_revision</source>
                 <target>Összehasonlítás ezzel a verzióval</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 eredmény|%count% eredmény</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.it.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Visualizza revisione</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>almeno</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 risultato|%count% risultati</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.ja.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>リビジョンを見る</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>%count%件</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.lb.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Versioune weisen</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 Resultat|%count% Resultater</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.lt.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Peržiūrėti reviziją</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 rezultatas|%count% resultatai|%count% resultatų</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.nl.xliff

@@ -330,6 +330,10 @@
                 <source>label_compare_revision</source>
                 <target>Vergelijk revisie</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 resultaat|%count% resultaten</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.pl.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Pokaż wersję</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>%count% wynik|%count% wyniki|%count% wyników</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.pt.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Ver Revisão</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 resultado|%count% resultados</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.pt_BR.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Ver revisão</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 resultado|%count% resultados</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.ro.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Vezi Modificările</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 rezultat|%count% rezultate|%count% rezultate</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.ru.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Просмотр изменений</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>{0} Нет данных |{1} Всего %count% запись |{2,3,4} Всего %count% записи |[5,Inf] Всего %count% записей</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.sk.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Zobraziť revíziu</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>aspoň</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 záznam|%count% záznamy|%count% záznamov</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.sl.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Poglej revizijo</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>vsaj</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 rezultat|%count% rezultata|%count% rezultati|%count% rezultatov</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.uk.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>Перегляд змін</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>{0} Данні відсутні |{1} Всього %count% запис |{2,3,4} Всього %count% записи |[5,Inf] Всього %count% записів</target>

+ 4 - 0
Resources/translations/SonataAdminBundle.zh_CN.xliff

@@ -322,6 +322,10 @@
                 <source>label_view_revision</source>
                 <target>查看版本</target>
             </trans-unit>
+            <trans-unit id="list_results_count_prefix">
+                <source>list_results_count_prefix</source>
+                <target>list_results_count_prefix</target>
+            </trans-unit>
             <trans-unit id="list_results_count">
                 <source>list_results_count</source>
                 <target>1 条数据|%count% 条数据</target>

+ 31 - 0
Resources/views/Pager/simple_pager_results.html.twig

@@ -0,0 +1,31 @@
+{#
+
+This file is part of the Sonata package.
+
+(c) Thomas Rabaix <thomas.rabaix@sonata-project.org>
+
+For the full copyright and license information, please view the LICENSE
+file that was distributed with this source code.
+
+#}
+
+{% extends 'SonataAdminBundle:Pager:base_results.html.twig' %}
+
+{% block num_results %}
+    {% if admin.datagrid.pager.lastPage != admin.datagrid.pager.page %}
+        {{ 'list_results_count_prefix' | trans({}, 'SonataAdminBundle') }}
+    {% endif %}
+    {% transchoice admin.datagrid.pager.nbresults with {'%count%': admin.datagrid.pager.nbresults} from 'SonataAdminBundle' %}list_results_count{% endtranschoice %}
+    &nbsp;-&nbsp;
+{% endblock %}
+
+{% block num_pages %}
+    {{ admin.datagrid.pager.page }}
+    /
+    {% if admin.datagrid.pager.lastPage != admin.datagrid.pager.page %}
+        ?
+    {% else %}
+        {{ admin.datagrid.pager.lastpage }}
+    {% endif %}
+    &nbsp;-&nbsp;
+{% endblock %}

+ 122 - 0
Tests/Datagrid/SimplePagerTest.php

@@ -0,0 +1,122 @@
+<?php
+
+/*
+ * This file is part of the Sonata package.
+ *
+ * (c) Thomas Rabaix <thomas.rabaix@sonata-project.org>
+ *
+ * For the full copyright and license information, please view the LICENSE
+ * file that was distributed with this source code.
+ *
+ */
+
+namespace Sonata\AdminBundle\Tests\Datagrid;
+
+use Sonata\AdminBundle\Datagrid\SimplePager;
+use Doctrine\Common\Collections\ArrayCollection;
+
+/**
+ * Simple pager
+ *
+ * @author Lukas Kahwe Smith <smith@pooteeweet.org>
+ * @author Sjoerd Peters <sjoerd.peters@gmail.com>
+ */
+class SimplePagerTest extends \PHPUnit_Framework_TestCase
+{
+    public function setUp()
+    {
+        $this->pager = new SimplePager(10, 2);
+        $this->proxyQuery = $this->getMockBuilder('Sonata\AdminBundle\Datagrid\ProxyQueryInterface')
+            ->disableOriginalConstructor()
+            ->getMock();
+    }
+
+    public function testInitNumPages()
+    {
+        $pager = new SimplePager(10, 2);
+        $this->proxyQuery->expects($this->once())
+                ->method('execute')
+                ->with(array(), null)
+                ->will($this->returnValue(new ArrayCollection(range(0, 12))));
+
+        $this->proxyQuery->expects($this->once())
+            ->method('setMaxResults')
+            ->with($this->equalTo(21));
+
+        $this->proxyQuery->expects($this->once())
+            ->method('setFirstResult')
+            ->with($this->equalTo(0));
+
+        $pager->setQuery($this->proxyQuery);
+        $pager->init();
+
+        $this->assertEquals(2, $pager->getLastPage());
+    }
+
+    public function testInitOffset()
+    {
+        $this->proxyQuery->expects($this->once())
+            ->method('execute')
+            ->with(array(), null)
+            ->will($this->returnValue(new ArrayCollection(range(0, 12))));
+
+        $this->proxyQuery->expects($this->once())
+            ->method('setMaxResults')
+            ->with($this->equalTo(21));
+
+        // Asserting that the offset will be set correctly
+        $this->proxyQuery->expects($this->once())
+            ->method('setFirstResult')
+            ->with($this->equalTo(10));
+
+        $this->pager->setQuery($this->proxyQuery);
+        $this->pager->setPage(2);
+        $this->pager->init();
+
+        $this->assertEquals(3, $this->pager->getLastPage());
+    }
+
+    public function testNoPagesPerConfig()
+    {
+        $this->proxyQuery->expects($this->once())
+            ->method('setMaxResults')
+            ->with($this->equalTo(0));
+
+        $this->proxyQuery->expects($this->once())
+            ->method('setFirstResult')
+            ->with($this->equalTo(0));
+
+        $this->pager->setQuery($this->proxyQuery);
+
+        // Max per page 0 means no pagination
+        $this->pager->setMaxPerPage(0);
+        $this->pager->init();
+
+        $this->assertEquals(0, $this->pager->getLastPage());
+    }
+
+    public function testNoPagesForNoResults()
+    {
+        $this->proxyQuery->expects($this->once())
+            ->method('execute')
+            ->with(array(), null)
+            ->will($this->returnValue(array()));
+
+        $this->proxyQuery->expects($this->once())
+            ->method('setMaxResults')
+            ->with($this->equalTo(21));
+        $this->proxyQuery->expects($this->once())
+            ->method('setFirstResult')
+            ->with($this->equalTo(0));
+
+        $this->pager->setQuery($this->proxyQuery);
+        $this->pager->init();
+        $this->AssertEquals(0, $this->pager->getLastPage());
+    }
+
+    public function testInitNoQuery()
+    {
+        $this->setExpectedException('RuntimeException');
+        $this->pager->init();
+    }
+}

+ 42 - 5
Tests/DependencyInjection/Compiler/AddDependencyCallsCompilerPassTest.php

@@ -192,16 +192,46 @@ class AddDependencyCallsCompilerPassTest extends \PHPUnit_Framework_TestCase
         $compilerPass = new AddDependencyCallsCompilerPass();
         $compilerPass->process($container);
 
-        $calls = $container->getDefinition('sonata_post_admin')->getMethodCalls();
+        $callsPostAdmin = $container->getDefinition('sonata_post_admin')->getMethodCalls();
 
-        foreach ($calls as $call) {
+        foreach ($callsPostAdmin as $call) {
             list($name, $parameters) = $call;
 
-            if ($name !== 'setTemplates') {
-                continue;
+            switch ($name) {
+                case 'setTemplates':
+                    $this->assertEquals('foobar.twig.html', $parameters[0]['user_block']);
+                    $this->assertEquals('SonataAdminBundle:Pager:results.html.twig', $parameters[0]['pager_results']);
+                    break;
+
+                case 'setLabel':
+                    $this->assertEquals('-', $parameters[0]);
+                    break;
+
+                case 'setPagerType':
+                    $this->assertEquals('default', $parameters[0]);
+                    break;
             }
+        }
+
+        $callsNewsAdmin = $container->getDefinition('sonata_news_admin')->getMethodCalls();
+
+        foreach ($callsNewsAdmin as $call) {
+            list($name, $parameters) = $call;
+
+            switch ($name) {
+                case 'setTemplates':
+                    $this->assertEquals('foo.twig.html', $parameters[0]['user_block']);
+                    $this->assertEquals('SonataAdminBundle:Pager:simple_pager_results.html.twig', $parameters[0]['pager_results']);
+                    break;
+
+                case 'setLabel':
+                    $this->assertEquals('Foo', $parameters[0]);
+                    break;
 
-            $this->assertEquals('foobar.twig.html', $parameters[0]['user_block']);
+                case 'setPagerType':
+                    $this->assertEquals('simple', $parameters[0]);
+                    break;
+            }
         }
     }
 
@@ -231,6 +261,13 @@ class AddDependencyCallsCompilerPassTest extends \PHPUnit_Framework_TestCase
                     'templates' => array(
                         'view' => array('user_block' => 'foobar.twig.html')
                     )
+                ),
+                'sonata_news_admin' => array(
+                    'label' => 'Foo',
+                    'pager_type' => 'simple',
+                    'templates'  => array(
+                        'view' => array('user_block' => 'foo.twig.html')
+                    )
                 )
             )
         );

+ 1 - 0
Tests/DependencyInjection/ConfigurationTest.php

@@ -84,6 +84,7 @@ class ConfigurationTest extends \PHPUnit_Framework_TestCase
             'menu_factory' => null,
             'route_builder' => null,
             'label_translator_strategy' => null,
+            'pager_type' => null,
             'templates' => array(
                 'form' => array(),
                 'filter' => array(),