从 HTTP 重定向到 HTTPS正确地当 URL 为以下任一类型时:
http://example.com
>>https://example.com
[确定]http://www.example.com
>>https://example.com
[确定]http://www.example.com/login
>>https://example.com/login
[确定]
但是重定向到 HTTPS失败当 URL 如下时:
http://example.com/login
>> 错误(见截图)
请指教如何解决。
下面是代码和配置。提前谢谢您...
其他详情:
- Ubuntu 16.04
- Apache 2.4
- mod_rewrite 已启用
- Laravel 5.3
- 清除浏览器缓存
.htaccess 文件
<IfModule mod_rewrite.c>
<IfModule mod_negotiation.c>
Options -MultiViews
</IfModule>
RewriteEngine On
# Allow Blog in Sub-Directory
RewriteCond $1 !^(blog)
#Redirect to non-WWW
RewriteCond %{HTTP_HOST} ^www.example.com$
RewriteRule ^(.*) https://example.com/$1 [QSA,L,R=301]
# Redirect Trailing Slashes If Not A Folder...
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)/$ /$1 [L,R=301]
# Handle Front Controller...
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^ index.php [L]
# Handle Authorization Header
RewriteCond %{HTTP:Authorization} .
RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]
</IfModule>
虚拟主机配置
(例如.com.conf)
<VirtualHost *:80>
ServerName example.com
ServerAlias example.com
ServerAdmin [email protected]
DocumentRoot /var/www/example.com_dev/public
<Directory "/var/www/example.com_dev/public">
DirectoryIndex index.php
AllowOverride All
Order allow,deny
Allow from all
</Directory>
ErrorLog ${APACHE_LOG_DIR}/error.log
CustomLog ${APACHE_LOG_DIR}/access.log combined
</VirtualHost>
<VirtualHost *:80>
ServerName example.com
ServerAlias www.example.com
ServerAdmin [email protected]
DocumentRoot /var/www/example.com_dev/public
<Directory "/var/www/example.com_dev/public">
DirectoryIndex index.php
AllowOverride All
Order allow,deny
Allow from all
</Directory>
ErrorLog ${APACHE_LOG_DIR}/error.log
CustomLog ${APACHE_LOG_DIR}/access.log combined
</VirtualHost>
虚拟主机配置
(例如-ssl.com.conf)
<IfModule mod_ssl.c>
<VirtualHost _default_:443>
ServerAdmin [email protected]
ServerName example.com
ServerAlias example.com
DocumentRoot /var/www/example.com_dev/public
ErrorLog ${APACHE_LOG_DIR}/error.log
CustomLog ${APACHE_LOG_DIR}/access.log combined
SSLEngine on
SSLCertificateFile /etc/apache2/ssl/example_com.crt
SSLCertificateKeyFile /etc/apache2/ssl/example_com.key
SSLCertificateChainFile /etc/apache2/ssl/example_com.ca-bundle
<FilesMatch "\.(cgi|shtml|phtml|php)$">
SSLOptions +StdEnvVars
</FilesMatch>
<Directory /usr/lib/cgi-bin>
SSLOptions +StdEnvVars
</Directory>
<Directory "/var/www/example.com_dev/public">
DirectoryIndex index.php
AllowOverride All
Order allow,deny
Allow from all
</Directory>
BrowserMatch "MSIE [2-6]" \
nokeepalive ssl-unclean-shutdown \
downgrade-1.0 force-response-1.0
BrowserMatch "MSIE [17-9]" ssl-unclean-shutdown
</VirtualHost>
</IfModule>
<IfModule mod_ssl.c>
<VirtualHost _default_:443>
ServerAdmin [email protected]
ServerName example.com
ServerAlias www.example.com
DocumentRoot /var/www/example.com_dev/public
ErrorLog ${APACHE_LOG_DIR}/error.log
CustomLog ${APACHE_LOG_DIR}/access.log combined
SSLEngine on
SSLCertificateFile /etc/apache2/ssl/example_com.crt
SSLCertificateKeyFile /etc/apache2/ssl/example_com.key
SSLCertificateChainFile /etc/apache2/ssl/example_com.ca-bundle
<FilesMatch "\.(cgi|shtml|phtml|php)$">
SSLOptions +StdEnvVars
</FilesMatch>
<Directory /usr/lib/cgi-bin>
SSLOptions +StdEnvVars
</Directory>
<Directory "/var/www/example.com_dev/public">
DirectoryIndex index.php
AllowOverride All
Order allow,deny
Allow from all
</Directory>
BrowserMatch "MSIE [2-6]" \
nokeepalive ssl-unclean-shutdown \
downgrade-1.0 force-response-1.0
BrowserMatch "MSIE [17-9]" ssl-unclean-shutdown
</VirtualHost>
</IfModule>
// 应用程序级重定向
(应用程序/Http/middleware/HttpsProtocol.php-Laravel 5.3)
<?php
namespace App\Http\Middleware;
use Closure;
class HttpsProtocol
{
/**
* Handle an incoming request.
*
* @param \Illuminate\Http\Request $request
* @param \Closure $next
* @return mixed
*/
public function handle($request, Closure $next)
{
if(!$request->secure()){
return redirect()->secure($request->getRequestUri());
}
return $next($request);
}
}
应用程序级 HTTP 内核
(应用程序/Http/Kernel.php-Laravel 5.3)
<?php
namespace App\Http;
use Illuminate\Foundation\Http\Kernel as HttpKernel;
class Kernel extends HttpKernel
{
/**
* The application's global HTTP middleware stack.
*
* These middleware are run during every request to your application.
*
* @var array
*/
protected $middleware = [
\Illuminate\Foundation\Http\Middleware\CheckForMaintenanceMode::class,
];
/**
* The application's route middleware groups.
*
* @var array
*/
protected $middlewareGroups = [
'web' => [
\App\Http\Middleware\EncryptCookies::class,
\Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse::class,
\Illuminate\Session\Middleware\StartSession::class,
\Illuminate\View\Middleware\ShareErrorsFromSession::class,
\App\Http\Middleware\VerifyCsrfToken::class,
\Illuminate\Routing\Middleware\SubstituteBindings::class,
\App\Http\Middleware\HttpsProtocol::class,
],
'api' => [
'throttle:60,1',
'bindings',
],
];
/**
* The application's route middleware.
*
* These middleware may be assigned to groups or used individually.
*
* @var array
*/
protected $routeMiddleware = [
'auth' => \Illuminate\Auth\Middleware\Authenticate::class,
'auth.basic' => \Illuminate\Auth\Middleware\AuthenticateWithBasicAuth::class,
'bindings' => \Illuminate\Routing\Middleware\SubstituteBindings::class,
'can' => \Illuminate\Auth\Middleware\Authorize::class,
'guest' => \App\Http\Middleware\RedirectIfAuthenticated::class,
'throttle' => \Illuminate\Routing\Middleware\ThrottleRequests::class,
];
}
答案1
解决了。问题原来是000-default.conf
虚拟主机仍然处于活动状态(启用),并拦截了类似 的请求http://example.com/*
。禁用后,使用:
a2dissite 000-default.conf
一切都开始按照预期进行。
答案2
http://example.com
>>https://example.com
[确定]http://example.com/login
>> 错误(见截图)
从您的代码转储中我实际上看不出这两种情况是如何处理的(尽管您说第一种情况可以正常进行)?
由于您似乎正在执行 www 重定向.htaccess
:
#Redirect to non-WWW RewriteCond %{HTTP_HOST} ^www.example.com$ RewriteRule ^(.*) https://example.com/$1 [QSA,L,R=301]
然后您可以尝试将其更改为:
RewriteCond %{HTTPS} off [OR]
RewriteCond %{HTTP_HOST} ^www\.example\.com
RewriteRule (.*) https://example.com/$1 [R=301,L]
这包括对 HTTP 的检查。因此,如果 HTTP或者 www
然后重定向到 HTTPS没有 www
。
您需要在测试之前清除所有缓存,因为错误的 301 会被浏览器严重缓存。
您似乎已为端口 80 和 443 复制了两个虚拟主机?这可能是导致您出现问题的原因。您只需VirtualHost
为端口 80 复制一个虚拟主机,为端口 443 复制一个虚拟主机:
ServerName example.com
ServerAlias example.com
应该:
ServerName example.com
ServerAlias www.example.com
就像你对复制。(然后删除重复项。)