cmsx / navigator
CMSx Navigator 组件
Requires
- php: >=5.3.0
- cmsx/db: dev-master
- cmsx/url: dev-master
- symfony/http-kernel: dev-master
This package is not auto-updated.
Last update: 2024-09-14 15:47:36 UTC
README
组件允许自动化或简化列表元素的分页、排序和筛选操作。
工作从初始化 Navigator 对象开始,该对象接受 Request 和 URL 对象。
$navi = new Navigator($request, $url);
分页
Navigator 对象提供了一系列方法,用于获取第一页、最后一页、下一页、上一页,以及快速生成对应页面的 URL 对象。
$navi->getPage(); // получение номера текущей страницы
$navi->getFirstPage(); // номер первой страницы
$navi->getLastPage(); // номер последней страницы
$navi->getNextPage(); // следующая страница от текущей
$navi->getPrevPage(); // предыдущая страница от текущей
类似地,所有方法都有获取相应 URL 对象的选项。
$navi->getPageUrl(42); // URL с номером страницы 42
$navi->getFirstPageUrl(); // URL с первой страницей
...
分页功能要求 Navigator 知道选择中元素的总数以及每页元素的数量。
$navi->setOnpage(10); // Указываем количество элементов на странице
$navi->setTotal(42); // Указываем количество элементов в выборке
echo $navi->getTotalPages(); // Результат - количество страниц: 5
排序
Navigator 允许指定排序的允许选项,并生成直接和反向排序的链接。
$navi = new Navigator($request, new URL('hello'));
$navi->addOrderBy('id'); // Именование и в БД, и в URL совпадает
$navi->addOrderBy('total', 'Количество', 'count(*)'); // В URL будет параметр вида orderby:total, в SQL `count(*)`
添加后,可以获取完整的排序选项列表,或单独的项目,用于生成界面中的选项或链接。每个排序选项都是一个 OrderBy 对象。
$o = $navi->getOrderByOption('total'); // Получили объект
$o->asUrlParameter(); // Значение для подстановки в URL: total - сортировка по-возрастанию
$o->asUrlParameter(false); // _total - сортировка по убыванию
$o->asSQL(); // SQL выражение для сортировки, в данном случае count(*) ASC
$o->asUrl(); // Объект URL
如果地址中包含排序参数,例如 .../orderby:_total/,可以获取当前的排序顺序。
$navi->getOrderBy();
如果地址中没有排序选项,方法将返回 false 或默认排序方式,如果通过方法 $navi->setDefaultOrderBy() 指定了默认排序方式。
选择元素,记录数量统计
Navigator 可以立即处理排序、过滤和分页数据,应用它们并获取选择中元素的数量,自动计算页数并返回相应的对象。
如果不需要复杂的过滤逻辑,可以使用设置或从类继承并重写相应的方法。
$navi->setClass('MyItem'); // Указываем, что используем модель MyItem
$navi->getTotal(); // Получение общего количества элементов в выборке
$navi->setOnpage(10); // Указываем количество элементов на странице
$navi->getItems(); // Получаем нужный набор элементов, с учетом сортировки и текущей страницы
为了扩展功能,可以重写用于计数和获取元素的功能(默认为 MyItem::Count() 和 MyItem::Find())。
$navi->setFuncCount('CountSome'); // Для вызова MyItem::CountSome()
$navi->setFuncFind('FindSome'); // Для вызова MyItem::FindSome()
默认情况下,这些方法将传递与基类 Item 签名一致的参数。如果需要调用具有不同参数集的方法,可以在继承时重写 countTotal() 和 getItems() 方法。
过滤
过滤机制通过分配 Filter 对象来实现。基本预定义了三个过滤器 - Equal、Between 和 Like,执行直接匹配、范围选择和 LIKE 条件过滤。如果需要实现更复杂的逻辑,可以添加任意过滤器,使用匿名函数或通过继承 Filter 类创建自己的过滤器。
以下是一个示例
$navi->addFilterEqual('one', 'is_numeric'); // Валидация может выполняться с помощью callable-выражений
$navi->addFilterEqual('two', '/^[a-z]+$/'); // Валидация может выполняться регулярными выражениями
$navi->addFilterBetween('date'); // На свой страх и риск можно обойтись и без валидации
$navi->addFilter(
'some',
null,
function(Navigator $navi, Filter $filter) {
if ($val = $filter->getCleanValue()) {
$navi->addCondition('... some complicated expression ...');
}
}
); // Произвольный фильтр
在形成一组规则后,可以使用过滤器自动处理请求并获得“纯净”数据。
// .../one:42/
echo $navi->getFilter('one')->getCleanValue(); // Результат: 42
// .../one:two/
echo $navi->getFilter('one')->getCleanValue(); // Результат: false
或者可以通过 processFilters() 方法获取用于 SQL 查询的已形成条件集合 Where。
过滤器中指定的回调允许自动化创建选择条件。函数接收 Navigator 和 Filter 对象作为参数。在验证和处理数据后,回调函数应准备 Where 条件并将其通过 addCondition() 方法传递给 Navigator。
因此,通过所有过滤器的操作,可以得到一个准备好的条件集,可以手动使用或在 getItems() 和 countTotal() 方法中自动使用。
如果需要,可以使用 addDefaultCondition() 指定一个不依赖于过滤器的静态条件。
预定义的 Equal、Between 和 Like 过滤器是最常用的选项。
- Equal: field = value 的直接匹配
- Between: field >= column_from 和 field <= column_to 的范围选择
- 如:生成条件 [column] LIKE ("[value]%")
对于上述规则集,URL 和结果将如下所示
URL: /hello/one:1/two:three/date_from:01.01.2014/date_to:31.12.2014/
Результат: array('one' => 1, 'two' => 'three', '`date` >= "01.01.2014"', '`date` <= "31.12.2014"');
重要!Between 过滤器和自定义过滤器的值将直接插入查询中,需要验证或屏蔽输入数据。
纯 URL
Navigator 的重要优点是所有导航都通过 "纯地址" 进行。也就是说,如果导航器设置为参数 one 和 two,而地址中包含垃圾参数,则分页器和排序链接中不会出现多余参数。
$navi = new Navigator($request, new URL('hello', array('one' => 1, 'two' => 2, test'=>'me'));
$navi->addFilterEqual('one');
$navi->addFilterEqual('two');
$navi->setPage(42);
echo $navi->getUrlClean()->toString(); // /hello/one:1/two:2/page:42/
生成界面元素
对于排序和过滤,除了可以简单地获取 URL 对象外,还提供了生成界面 HTML 元素的方法。过滤器将根据当前过滤器和排序值渲染,并考虑这些数据的有效性。
生成选择排序的 SELECT 方法
$navi->getOrderByAsSelectOptions(); // Генерация списка тегов <option>
$navi->getOrderByAsSelect(); // Генерация тега <select> с полным списком опций
对于过滤器,可以生成输入字段 INPUT,也可以生成 SELECT 或选项集 OPTIONS,如果已指定选项选择 $f->setOptions(array(...))
$f = $navi->getFilter('one'); // Получаем объект Filter
$f->asInput(); // Генерация тега <input>
$f->asSelectOptions(); // Генерация списка тегов <option>
$f->asSelect(); // Генерация тега <select> с полным списком опций