Laravel自定义分页-链式伪静态分页SEO分页
Song •
797 次浏览 •
0个评论 •
2021年10月11日
Laravel自带的simplePaginate
和paginate
方法的分页方式都为http://test.com?page=*
格式;对于SEO不是很友好;我们尝试修改为http://test.com/page/1
这种不带问号的伪静态分页链接格式;我们根据文档Laravel分页-手动创建分页
有时你可能希望手动创建分页,并传递一个包含数据的数组给它。这可以通过手动创建Illuminate\Pagination\Paginator
或者Illuminate\Pagination\LengthAwarePaginator
实例来实现,这取决于你的需要。
一、创建文件app/Utils/AcademyPaginator.php
<?php
namespace App\Utils;
use Illuminate\Container\Container;
use Illuminate\Database\Eloquent\Builder;
use Illuminate\Support\Str;
use Illuminate\Pagination\Paginator;
use Illuminate\Pagination\LengthAwarePaginator as BasePaginator;
class AcademyPaginator extends BasePaginator
{
/**
* 重写页面 URL 实现代码,去掉分页中的问号,实现伪静态链接
* @param int $page
* @return string
*/
public function url($page)
{
if ($page <= 0) {
$page = 1;
}
// 移除路径尾部的/
$path = rtrim($this->path, '/');
// 如果路径中包含分页信息则正则替换页码,否则将页码信息追加到路径末尾
if (preg_match('/\/page\/\d+/', $path)) {
$path = preg_replace('/\/page\/\d+/', '/page/' . $page, $path);
} else {
$path .= '/page/' . $page;
}
$this->path = $path;
if ($this->query) {
$url = $this->path . (Str::contains($this->path, '?') ? '&' : '?')
. http_build_query($this->query, '', '&')
. $this->buildFragment();
} elseif ($this->fragment) {
$url = $this->path . $this->buildFragment();
} else {
$url = $this->path;
}
return $url;
}
/**
* 重写当前页设置方法
*
* @param int $currentPage
* @param string $pageName
* @return int
*/
protected function setCurrentPage($currentPage, $pageName)
{
if (!$currentPage && preg_match('/\/page\/(\d+)/', $this->path, $matches)) {
$currentPage = $matches[1];
}
return $this->isValidPageNumber($currentPage) ? (int) $currentPage : 1;
}
/**
* 将新增的分页方法注册到查询构建器中,以便在模型实例上使用
* 注册方式:
* 在 AppServiceProvider 的 boot 方法中注册:AcademyPaginator::rejectIntoBuilder();
* 使用方式:
* 将之前代码中在模型实例上调用 paginate 方法改为调用 seoPaginate 方法即可:
* Article::where('status', 1)->seoPaginate(15, ['*'], 'page', page);
*/
public static function injectIntoBuilder()
{
/*
* $perPage 每页显示多少条
* $columns 查询的字段
* $pageName 翻页链接的参数名
* $page 当前页数
* */
Builder::macro('seoPaginate', function ($perPage, $columns, $pageName, $page) {
$perPage = $perPage ?: $this->model->getPerPage();
$items = ($total = $this->toBase()->getCountForPagination())
? $this->forPage($page, $perPage)->get($columns)
: $this->model->newCollection();
$options = [
'path' => Paginator::resolveCurrentPath(),
'pageName' => $pageName,
];
return Container::getInstance()->makeWith(AcademyPaginator::class, compact(
'items', 'total', 'perPage', 'page', 'options'
));
});
}
}
二、在 app/Providers/AppServiceProvider 的 boot 方法中全局调用这个注入:
// 为查询构建器注入自己实现的分页器方法
AcademyPaginator::injectIntoBuilder();
这样,在模型实例上调用seoPaginate
方法,将通过 AcademyPaginator
进行分页。接下来,就可以在自己的代码中编写以下这种代码实现伪静态分页链接了:
# 每页数量
$pageSize = 20;
$page = 1;
$articles = Article::orderBy('id', 'desc')->seoPaginate($pageSize, ['*'], 'page', $page);
参考文档:https://laravelacademy.org/post/9661.html
其他文章
用户评论
当前暂无评价,快来发表您的观点吧...
更多相关好文
当前暂无更多相关好文推荐...
-
laravel中distinct()的使用方法与去重 2017-09-11
-
Laravel将view缓存为静态html,laravel页面静态缓存 2021-10-09
-
[ laravel爬虫实战--基础篇 ] guzzle描述与安装 2017-11-01
-
[ 配置教程 ] 在ubuntu16.04中部署LNMP环境(php7+maridb且开启maridb远程以及nginx多域名访问 )并配置laravel环境 2017-07-18
-
花生壳绑定ubuntu服务器? 2024-08-23
热门文章
-
花生壳绑定ubuntu服务器? 2024-08-23
-
Laravel模型更新全表如何实现? 2024-03-11
-
php图片转为二进制数据的方法 2023-10-23
-
Jquery如何监听动态创建元素的点击事件? 2023-09-08
-
所以SheetJS实现table导出数据为Excel 2023-09-05
提交评论