Paginacja wyników bazy danych
Podczas tworzenia aplikacji internetowych często spotkasz się z wymogiem ograniczenia liczby elementów wyszczególnionych na stronie.
Zaczynamy od stanu, w którym wypisujemy wszystkie dane bez paginacji. Do wybierania danych z bazy mamy klasę
ArticleRepository, która oprócz konstruktora zawiera metodę findPublishedArticles
, która zwraca wszystkie
opublikowane artykuły posortowane w porządku malejącym według daty publikacji.
Następnie wstrzykujemy klasę modelu w prezenterze i w metodzie render żądamy opublikowanych artykułów do przekazania do szablonu:
Szablon default.latte
zajmie się następnie listą artykułów:
W ten sposób możemy wymienić wszystkie artykuły, ale spowoduje to problemy, gdy liczba artykułów wzrośnie. Wtedy właśnie przydaje się implementacja mechanizmu paginacji.
Dzięki temu wszystkie artykuły zostaną podzielone na wiele stron, a my wyświetlimy tylko artykuły z jednej bieżącej strony. Paginator sam obliczy całkowitą liczbę stron i podział artykułów, w zależności od tego ile mamy artykułów w sumie i ile artykułów na stronę chcemy wyświetlić.
W pierwszym kroku modyfikujemy metodę pobierania artykułów w klasie repozytorium tak, aby zwracała ona artykuły tylko dla jednej strony. Dodamy też metodę, która pozwoli nam uzyskać całkowitą liczbę artykułów w bazie, co będzie nam potrzebne do skonfigurowania Paginatora:
Następnie zabierzemy się do pracy nad modyfikacją prezentera. Do metody render przekażemy numer aktualnie wyświetlanej strony. W przypadku, gdy ten numer nie jest częścią adresu URL, ustawimy domyślną wartość pierwszej strony.
Następnie rozszerzymy również metodę render, aby uzyskać instancję Paginatora, skonfigurować ją i wybrać odpowiednie artykuły do wyświetlenia w szablonie. HomePresenter po modyfikacjach będzie wyglądał tak:
Szablon już iteruje po tylko artykułach jednej strony, musimy tylko dodać linki paginacji:
W ten sposób dodaliśmy do strony paginację Paginator. W przypadku, gdy jako warstwy bazy danych użyjemy Nette Database Explorer
zamiast Nette Database Core, jesteśmy w stanie zaimplementować paginację
bez użycia Paginatora. Klasa Nette\Database\Table\Selection
zawiera metodę page z logiką paginacji zaczerpniętą
z Paginatora.
Repozytorium będzie wyglądać tak z tą implementacją:
Nie musimy tworzyć Paginatora w prezenterze, zamiast tego używamy metody klasy Selection
zwracanej przez
repozytorium:
Ponieważ nie wysyłamy teraz Paginatora do szablonu, wyedytujemy część pokazującą linki paginacji:
W ten sposób zaimplementowaliśmy mechanizm paginacji bez użycia Paginatora.