laravel + haproxy + https 后生成分页 url 非 h…
2018-06-22 05:38:19来源:未知 阅读 ()
更合适的解决办法:在AppServiceProvider
boot
方法中使用\URL::forceScheme('https');
即可。
背景
近日对所有的客户都上线了 https ,本来在 beta 环境中是没有任何问题,都测试通过了,但是在正式上线后,发现后台管理系统中的 laravel 分页生成的 url 是非 https 的,但是其他地方(路由,静态资源)等生成的都是正常的 https 链接,遂找原因解决。
解决
laravel 的分页服务 Illuminate\Pagination\PaginationServiceProvider::class
找到该 ServiceProvider 源码中 register() 中的代码
Paginator::currentPathResolver(function () {
return $this->app['request']->url();
});
可以看到分页链接生成的时候,是根据当前请求的 url 来设置分页类的 url path.
接着找到 Illuminate\Http\Request::class
中的 url()
public function url()
{
return rtrim(preg_replace('/\?.*/', '', $this->getUri()), '/');
}
在这里我们可以发现 laravel 的 Request 类是继承自 Symfony 的 Request,通过不断地位我们可以找到如下代码:
public function isSecure()
{
if ($this->isFromTrustedProxy() && self::$trustedHeaders[self::HEADER_CLIENT_PROTO] && $proto = $this->headers->get(self::$trustedHeaders[self::HEADER_CLIENT_PROTO])) {
return in_array(strtolower(current(explode(',', $proto))), array('https', 'on', 'ssl', '1'));
}
$https = $this->server->get('HTTPS');
return !empty($https) && 'off' !== strtolower($https);
}
看到这段源码后,我们打印了生产环境中的 phpinfo
通过源码对比发现,Symfony 中默认读取的是 X_FORWARDED_PROTO and X_FORWARDED_PORT,但是我们 php 环境中是 HTTP_X_FORWARDED_PROTO and HTTP_X_FORWARDED_PORT,我们在源码中发现了如下方法:
/**
* Sets the name for trusted headers.
*
* The following header keys are supported:
*
* * Request::HEADER_CLIENT_IP: defaults to X-Forwarded-For (see getClientIp())
* * Request::HEADER_CLIENT_HOST: defaults to X-Forwarded-Host (see getHost())
* * Request::HEADER_CLIENT_PORT: defaults to X-Forwarded-Port (see getPort())
* * Request::HEADER_CLIENT_PROTO: defaults to X-Forwarded-Proto (see getScheme() and isSecure())
*
* Setting an empty value allows to disable the trusted header for the given key.
*
* @param string $key The header key
* @param string $value The header name
*
* @throws \InvalidArgumentException
*/
public static function setTrustedHeaderName($key, $value)
{
if (!array_key_exists($key, self::$trustedHeaders)) {
throw new \InvalidArgumentException(sprintf('Unable to set the trusted header name for key "%s".', $key));
}
self::$trustedHeaders[$key] = $value;
}
可以发现这是一个静态方法,因此我们只需要在 AppServiceProvider 中加入如下代码即可
Request::setTrustedHeaderName(Request::HEADER_CLIENT_PORT,'HTTP_X_FORWARDED_PORT');
Request::setTrustedHeaderName(Request::HEADER_CLIENT_PROTO,'HTTP_X_FORWARDED_PROTO');
标签:
版权申明:本站文章部分自网络,如有侵权,请联系:west999com@outlook.com
特别注意:本站所有转载文章言论不代表本站观点,本站所提供的摄影照片,插画,设计作品,如需使用,请与原作者联系,版权归原作者所有
上一篇:博客园的第一篇随记
下一篇:关于PHP中的SESSION技术
- laravel实现批量更新多条记录的方法示例 2020-02-19
- Laravel中七个非常有用但很少人知道的Carbon方法 2020-02-15
- Laravel如何使用数据库事务及捕获事务失败后的异常详解 2020-02-08
- Laravel 中 “规范” 的开发短信验证码发送功能 2020-02-08
- Laravel中获取路由参数Route Parameters的五种方法示例 2020-02-07
IDC资讯: 主机资讯 注册资讯 托管资讯 vps资讯 网站建设
网站运营: 建站经验 策划盈利 搜索优化 网站推广 免费资源
网络编程: Asp.Net编程 Asp编程 Php编程 Xml编程 Access Mssql Mysql 其它
服务器技术: Web服务器 Ftp服务器 Mail服务器 Dns服务器 安全防护
软件技巧: 其它软件 Word Excel Powerpoint Ghost Vista QQ空间 QQ FlashGet 迅雷
网页制作: FrontPages Dreamweaver Javascript css photoshop fireworks Flash