Laravel przekierowuje wszystkie żądania do HTTPS

Cała nasza strona ma być obsługiwana przez https. Mam 'https' w każdej trasie. Jak jednak przekierować je na https, jeśli spróbują tego przez http?

Route::group(array('https'), function()
{
     // all of our routes
}
 58
Author: Sajan Parikh, 2013-11-14

15 answers

Korzystanie z aplikacji:: before

Możesz skorzystać z bloku App::before() w pliku app/filters.php.

Zmień blok, aby zawierał proste sprawdzenie, czy bieżące żądanie jest bezpieczne, a jeśli nie, przekieruj je.

App::before(function($request)
{
    if( ! Request::secure())
    {
        return Redirect::secure(Request::path());
    }
});

Korzystanie Z Filtrów

Inną opcją może być utworzenie takiego filtra. Ludzie zazwyczaj przechowują to również w app/filters.php.

Route::filter('force.ssl', function()
{
    if( ! Request::secure())
    {
        return Redirect::secure(Request::path());
    }

});

Możesz następnie wymusić ten nowy filtr na dowolnej trasie, grupie tras lub takie Kontrolery.

Trasa Indywidualna

Route::get('something', ['before' => 'force.ssl'], function()
{
    return "This will be forced SSL";
});

Grupa Trasy

Route::group(['before' => 'force.ssl'], function()
{
    // Routes here.
});

Controller

Musisz to zrobić w metodzie kontrolera __construct().

public function __construct()
{
    $this->beforeFilter('force.ssl');
}
 93
Author: Sajan Parikh,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-06-08 08:32:56

Inną odpowiedzią może być pozwolenie serwerowi www na to. Jeśli używasz Apache, możesz użyć funkcji RedirectSSL, aby upewnić się, że wszystkie żądania trafiają do wersji HTTPS Twojej witryny, a jeśli nie, przekieruj je. To się stanie, zanim Laravel dostanie prośbę.

Apache RedirectSSL

Jeśli korzystasz z NGINX, możesz to osiągnąć, posiadając dwa bloki serwerów. Jeden dla zwykłego HTTPS na porcie 80, a drugi dla HTTPS na porcie 443. Następnie skonfiguruj zwykły blok serwera, aby zawsze przekierować do wersji ssl.
server {
    listen 80;
    server_name mydomain.com;
    rewrite ^ https://$server_name$request_uri? permanent;
}

server {
    listen 443;
    server_name mydomain.com;
    ssl on;
    # other server config stuff here.
}

Osobiście wybrałbym tę opcję, ponieważ samo PHP nie musi niczego przetwarzać. Generalnie tańsze jest przetworzenie takiego czeku na poziomie serwera www.

 33
Author: Sajan Parikh,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-11-14 03:05:55

Dla użytkowników korzystających z Laravel 4/5 i Elastic Beanstalk, wymuszanie HTTPS jest trudne przy użyciu tych metod, ponieważ isSecure() zwróci false. Ponadto, użycie przekierowań .htaccess spowoduje pętlę przekierowań dla Chrome i opóźnione czasy ładowania strony w Firefoksie.

Ten zestaw jest dla

  • Laravel 5 i może pracować dla Laravel 3 / 4
  • Aplikacja załadowana Na Elastic Beanstalk z uruchomionymi instancjami serwera EC2
  • Route 53 używany dla DNS rozdzielczość
  • Cloudfront używany do globalnej sieci CDN wszystkich zasobów i wymuszania HTTPS]}
  • uruchamiam aws na komputerze z systemem Windows. Linux może się nieznacznie różnić?

Po wielu godzinach własnych prób, udało mi się przesłać wszystkie żądania HTTP do HTTPS, wykonując następujące kroki:

  1. Uzyskaj certyfikat SSL. Przewodniki i dostawcy są liczne i można je znaleźć za pomocą wyszukiwarki Google.

  2. Prześlij certyfikat do AWS za pomocą aws polecenie konsoli. Struktura polecenia to:

    aws iam upload-server-certificate --server-certificate-name CERTIFICATE_NAME --certificate-body "file://PATH_TO_CERTIFICATE.crt" --private-key "file://YOUR_PRIVATE_KEY.pem" --certificate-chain "file://YOUR_CERTIFICATE_CHAIN.ca-bundle" --path /cloudfront/
    
  3. Utwórz elastyczną aplikację łodygi fasoli. Przejdź przez proces konfiguracji. Po skonfigurowaniu aplikacji przejdź do konfiguracji -> warstwa sieci -> Load Balancing i kliknij ikonę koła zębatego .

  4. Wybierz Secure listener port jako 443. Wybierz protokół jako HTTPS . Wybierz CERTIFICATE_NAME z Krok 2 dla SSL identyfikator certyfikatu . Zapisz konfigurację.

  5. Przejdź do konsoli . Kliknij instancje EC2 . Kliknij Load Balancers . Kliknij w load balancers. Kliknij instancje i przewiń w dół, aby zobaczyć instancje EC2 przypisane do tego load balancer. Jeśli instancja EC2 ma taką samą nazwę jak adres URL aplikacji( lub coś podobnego), zwróć uwagę na nazwę DNS dla load balancer. Powinien być w formacie awseb-e-...

  6. Wróć do konsoli . Kliknij CloudFront . Kliknij Utwórz Dystrybucję. Wybierz dystrybucję Web.

  7. Ustaw dystrybucję. Ustaw nazwę domeny wyjściowej na nazwę DNS load balancer znalezioną w kroku 5 . Ustawia Politykę protokołu przeglądarki na przekierowanie HTTP do HTTPS. Ustaw Prześlij ciągi zapytań do tak . Set Alternate Domain Nazwy (CNAMEs) do adresów URL, których chcesz użyć w swojej aplikacji. Ustaw certyfikat SSL na CERTIFICATE_NAME, który przesłałeś w kroku 2 . Stwórz swoją dystrybucję.

  8. Kliknij nazwę swojej dystrybucji w CloudFront. Kliknij Origins , wybierz swoje pochodzenie i kliknij Edytuj . Upewnij się, że twoje Origin Protocol Policy to przeglądarka dopasowań . Wracaj. Kliknij Behaviors , wybierz swoje pochodzenie i kliknij Edytuj . Zmień Prześlij nagłówki do białej listy i dodaj Host . Zapisz.

  9. Przejdź do konsoli . Kliknij Route 53 . Kliknij Hosted Zones. Kliknij Utwórz Strefę Hostowaną . Skonfiguruj nazwę domeny. Po skonfigurowaniu kliknij Utwórz zestaw rekordów. Wpisz swój rekord A. Wybierz Alias jako tak . Twój Alias Target to twoja dystrybucja CloudFront. Zapisz płytę.

  10. Skonfiguruj swój serwery nazw dla Twojej domeny, aby wskazywały na serwery nazw Route 53. Poczekaj, aż wszystko się rozprzestrzeni, co może potrwać kilka godzin. Przejdź do swojego adresu URL. Zostaniesz automatycznie przekierowany do HTTPS.

  11. "ale czekaj, moje linki nie idą do HTTPS!?"Musisz obsłużyć nagłówek X-Forwarded-Proto, który przejdzie CloudFront. Dla Laravel 4, postępuj zgodnie z tym przewodnikiem . Dla Laravel 5 Uruchom to:

    php artisan make:middleware EB_SSL_Trust
    

A następnie dodaj to do pliku EB_SSL_Trust:

    public function handle($request, Closure $next)
    {
        $request->setTrustedProxies( [ $request->getClientIp() ] );
        return $next($request);
    }

I dodaj to do pliku App\Http\Kernel.php:

    protected $middleware = [
        ...
        'App\Http\Middleware\EB_SSL_Trust',
        ...
    ];

Uwaga: wszystkie zasoby, takie jak CSS, JS lub obrazy, muszą być wysyłane przez HTTPS. Jeśli używasz Laravel do tworzenia tych linków, użyj secure_asset(), aby utworzyć adres URL HTTPS w widoku.

 12
Author: Adam Link,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-03-20 17:40:47

Używam .htaccess Apache for laravel 4.2.X

Oryginalny Plik

<IfModule mod_rewrite.c>
    <IfModule mod_negotiation.c>
        Options -MultiViews
    </IfModule>

    RewriteEngine On

    # Redirect Trailing Slashes...
    RewriteRule ^(.*)/$ /$1 [L,R=301]

    # Handle Front Controller...
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^ index.php [L]
</IfModule>

Edycja pliku / public/.htaccess

 <IfModule mod_rewrite.c>
    <IfModule mod_negotiation.c>
        Options -MultiViews
    </IfModule>

    RewriteEngine On

    # Redirect Trailing Slashes...
    RewriteCond %{HTTPS} off 
    RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301] 


    # Handle Front Controller...
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^ index.php [L]
</IfModule>
 7
Author: urielOn,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-01-23 21:20:29

Stosowanie filtrów zostało wycofane w Laravel 5.1.*. To idealna praca dla MiddleWare.

Utwórz Middleware i w sekcji handle umieść

public function handle($request, Closure $next)
{
    if(! $request->secure()) {
        return redirect()->secure($request->path());
    }
    return $next($request);
}

Następnie po prostu zarejestruj swoje oprogramowanie pośredniczące w jądrze.php i używać go ze swoimi trasami lub kontrolerami.

 6
Author: prog_24,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-04-05 09:51:16

Łączenie poprzednich odpowiedzi i aktualizacja dla Laravel 4.2:

Route::filter('secure', function () {
    if (! Request::secure()) {
        return Redirect::secure(
            Request::path(),
            in_array(Request::getMethod(), ['POST', 'PUT', 'DELETE']) ? 307 : 302
        );
    }
});
Route::when('*', 'secure');
 5
Author: bishop,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-08-27 13:22:12

Jeśli chcesz przekierować na ten sam adres URL, ale używając https, powinieneś użyć Request::getRequestUri() zamiast Request::path():

App::before(function($request)
{
    if( ! Request::secure())
    {
         return Redirect::secure(Request::getRequestUri());
    }
});
 3
Author: ggonzal,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-09-02 15:24:56

Jeśli masz problem, gdzie z jakiegoś powodu Request::secure() zwraca false, nawet jeśli adres url to https, może to być spowodowane tym, że wartość $_SERVER['HTTPS'] nie istnieje.

To jest obejście:
App::before(function ($request){
    // Force https
    if(!Request::secure() && array_get($_SERVER, 'SERVER_PORT') != 443){
        return Redirect::secure(Request::path());
    }
});
 1
Author: Mārtiņš Briedis,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-06-26 08:34:12

Miałem problem z wymuszeniem ssl podczas wykonywania żądania POST. To zawsze przekierowywałoby, aby dostać. Dzieje się tak, ponieważ Redirect::secure() domyślnie używa przekierowania 302.

Aby upewnić się, że twoje żądanie postu jest poprawnie przekierowane, użyj czegoś takiego jak

return Redirect::secure("your/path/here", 307)

To sprawi, że twoje żądanie zachowa oryginalną metodę żądania po wystąpieniu przekierowania.

 1
Author: MikeWu,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-08-13 13:58:17

Nie rozumiem szczegółowo HTTP i HTTPS, więc przepraszam, jeśli ta odpowiedź nie jest zbyt dobra.

Rozumiem, że istnieje problem, że nawet jeśli klient i (określony klient) serwer używają HTTPS, Request::secure() może zwrócić false, ponieważ aplikacja może działać na innym serwerze, który prawdopodobnie nie odbiera żądania https.

Hostuję moją aplikację laravel w heroku i wydaje się, że to robi. My guess czy to podstawowy (klient serwer jest load balancer i gdy żądanie jest przekazywane, dociera do innego serwera jako normalne żądanie HTTP.

Gdy takie przekierowanie może się zdarzyć, nie należy sprawdzać, czy Request::secure() jest true. Zostałem polecony (przez kogoś w #laravel @ irc.freenode.com), aby również sprawdzić Request::server('HTTP_X_FORWARDED_PROTO'), aby sprawdzić, czy jest równa 'https'.

Więc jeśli zamierzasz postępować zgodnie z innymi wskazówkami tutaj i wykonać przekierowanie w przypadku niezabezpieczenia, spróbuj sprawdzić również ten parametr serwera.

 1
Author: Pedro Henrique A. Oliveira,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-08-26 22:06:44

Dla laravel 5.1 należy użyć podanego kodu w App\Http\Providers\RouteServiceProvider@boot

$router->filter('force.ssl', function () {
      if ( ! request()->secure() ) {
           return redirect()->secure(request()->path());
      }
});

Teraz możesz użyć tego w pliku routes.

Route::group(['before' => 'force.ssl'], function () {
    // Routes here
});

Możesz również dodać ['before' => 'force.ssl'] w $router->group() w

App\Http\Providers\RouteServiceProvider@map
 1
Author: Muhammad Abdullah,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-02-01 14:48:04

To działało dla mnie w Apache 2.4

Zmieniłem się .htaccess w głównym folderze Laravela

Od <IfModule mod_rewrite.c> RewriteEngine On RewriteRule ^(.*)$ public/$1 [L] </IfModule>

To <IfModule mod_rewrite.c> RewriteEngine On RewriteCond %{HTTPS} off RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301] RewriteRule ^(.*)$ public/$1 [L] </IfModule>

 1
Author: varun sharma,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-07-27 18:13:10

Jeśli za proxy i Request:: secure() nie działa.

App::before( function( $request )
{
  // set the current IP (REMOTE_ADDR) as a trusted proxy
  Request::setTrustedProxies( [ $request->getClientIp() ] );
});
 0
Author: Carsten Jonstrup,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-12-05 19:58:37

Łączenie poprzednich odpowiedzi z wykorzystaniem stałych i metod dostępnych w Laravel 4.2.

Trasy.php

Route::when('*', 'secure');

Filtry.php

use Illuminate\Http\Response as IlluminateResponse;

Route::filter('secure', function ()
{
    if ( ! Request::secure() && Request::getPort() != 443)
    {
        return Redirect::secure(
            Request::path(),
            in_array(Request::getMethod(), ['POST', 'PUT', 'DELETE'])
                ? IlluminateResponse::HTTP_TEMPORARY_REDIRECT
                : IlluminateResponse::HTTP_FOUND
        );
    }
});
 0
Author: user161875,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-01-20 19:57:27

Jeśli musisz użyć samego Laravela 4 do obsługi przekierowania (tak jak ja), wybrałbym następującą konfigurację (Wyjaśnienie jako komentarz w kodzie):

Filtr trasy:

// app/filters.php
Route::filter('ssl.force', function()
{
    if(App::environment('production') && !Request::secure())
    {
        // don't set a session cookie when redirecting to another scheme to 
        // avoid dropping the session when switching scheme
        Config::set('session.driver', 'array');
        // preserve query string while redirecting by using fullUrl()
        // instead of Redirect::secure + Request::path()
        $url = str_replace('http://', 'https://', Request::fullUrl());
        return Redirect::to($url, 302, array(), true);
    }

    // secure cookies for https
    Config::set('session.secure', Request::secure());
});

Następnie zastosuj filtr jako filtr przed do trasy lub grupy tras. eg:

// app/routes.php
Route::group(array('before' => 'ssl.force'), function () {
    // SSL routes
});
 0
Author: Jones03,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-05-11 04:02:06